mips.c (build_mips16_call_stub): On 64-bit targets, combine an SC return value into...
[official-gcc.git] / gcc / builtins.c
blobbb43ab61b3d4e209f25379a02eab3e52257788fd
1 /* Expand builtin functions.
2 Copyright (C) 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007
4 Free Software Foundation, Inc.
6 This file is part of GCC.
8 GCC is free software; you can redistribute it and/or modify it under
9 the terms of the GNU General Public License as published by the Free
10 Software Foundation; either version 3, or (at your option) any later
11 version.
13 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
14 WARRANTY; without even the implied warranty of MERCHANTABILITY or
15 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 for more details.
18 You should have received a copy of the GNU General Public License
19 along with GCC; see the file COPYING3. If not see
20 <http://www.gnu.org/licenses/>. */
22 #include "config.h"
23 #include "system.h"
24 #include "coretypes.h"
25 #include "tm.h"
26 #include "machmode.h"
27 #include "real.h"
28 #include "rtl.h"
29 #include "tree.h"
30 #include "tree-gimple.h"
31 #include "flags.h"
32 #include "regs.h"
33 #include "hard-reg-set.h"
34 #include "except.h"
35 #include "function.h"
36 #include "insn-config.h"
37 #include "expr.h"
38 #include "optabs.h"
39 #include "libfuncs.h"
40 #include "recog.h"
41 #include "output.h"
42 #include "typeclass.h"
43 #include "toplev.h"
44 #include "predict.h"
45 #include "tm_p.h"
46 #include "target.h"
47 #include "langhooks.h"
48 #include "basic-block.h"
49 #include "tree-mudflap.h"
50 #include "tree-flow.h"
51 #include "value-prof.h"
52 #include "diagnostic.h"
54 #ifndef PAD_VARARGS_DOWN
55 #define PAD_VARARGS_DOWN BYTES_BIG_ENDIAN
56 #endif
58 /* Define the names of the builtin function types and codes. */
59 const char *const built_in_class_names[4]
60 = {"NOT_BUILT_IN", "BUILT_IN_FRONTEND", "BUILT_IN_MD", "BUILT_IN_NORMAL"};
62 #define DEF_BUILTIN(X, N, C, T, LT, B, F, NA, AT, IM, COND) #X,
63 const char * built_in_names[(int) END_BUILTINS] =
65 #include "builtins.def"
67 #undef DEF_BUILTIN
69 /* Setup an array of _DECL trees, make sure each element is
70 initialized to NULL_TREE. */
71 tree built_in_decls[(int) END_BUILTINS];
72 /* Declarations used when constructing the builtin implicitly in the compiler.
73 It may be NULL_TREE when this is invalid (for instance runtime is not
74 required to implement the function call in all cases). */
75 tree implicit_built_in_decls[(int) END_BUILTINS];
77 static const char *c_getstr (tree);
78 static rtx c_readstr (const char *, enum machine_mode);
79 static int target_char_cast (tree, char *);
80 static rtx get_memory_rtx (tree, tree);
81 static int apply_args_size (void);
82 static int apply_result_size (void);
83 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
84 static rtx result_vector (int, rtx);
85 #endif
86 static void expand_builtin_update_setjmp_buf (rtx);
87 static void expand_builtin_prefetch (tree);
88 static rtx expand_builtin_apply_args (void);
89 static rtx expand_builtin_apply_args_1 (void);
90 static rtx expand_builtin_apply (rtx, rtx, rtx);
91 static void expand_builtin_return (rtx);
92 static enum type_class type_to_class (tree);
93 static rtx expand_builtin_classify_type (tree);
94 static void expand_errno_check (tree, rtx);
95 static rtx expand_builtin_mathfn (tree, rtx, rtx);
96 static rtx expand_builtin_mathfn_2 (tree, rtx, rtx);
97 static rtx expand_builtin_mathfn_3 (tree, rtx, rtx);
98 static rtx expand_builtin_interclass_mathfn (tree, rtx, rtx);
99 static rtx expand_builtin_sincos (tree);
100 static rtx expand_builtin_cexpi (tree, rtx, rtx);
101 static rtx expand_builtin_int_roundingfn (tree, rtx, rtx);
102 static rtx expand_builtin_int_roundingfn_2 (tree, rtx, rtx);
103 static rtx expand_builtin_args_info (tree);
104 static rtx expand_builtin_next_arg (void);
105 static rtx expand_builtin_va_start (tree);
106 static rtx expand_builtin_va_end (tree);
107 static rtx expand_builtin_va_copy (tree);
108 static rtx expand_builtin_memchr (tree, rtx, enum machine_mode);
109 static rtx expand_builtin_memcmp (tree, rtx, enum machine_mode);
110 static rtx expand_builtin_strcmp (tree, rtx, enum machine_mode);
111 static rtx expand_builtin_strncmp (tree, rtx, enum machine_mode);
112 static rtx builtin_memcpy_read_str (void *, HOST_WIDE_INT, enum machine_mode);
113 static rtx expand_builtin_strcat (tree, tree, rtx, enum machine_mode);
114 static rtx expand_builtin_strncat (tree, rtx, enum machine_mode);
115 static rtx expand_builtin_strspn (tree, rtx, enum machine_mode);
116 static rtx expand_builtin_strcspn (tree, rtx, enum machine_mode);
117 static rtx expand_builtin_memcpy (tree, rtx, enum machine_mode);
118 static rtx expand_builtin_mempcpy (tree, rtx, enum machine_mode);
119 static rtx expand_builtin_mempcpy_args (tree, tree, tree, tree, rtx,
120 enum machine_mode, int);
121 static rtx expand_builtin_memmove (tree, rtx, enum machine_mode, int);
122 static rtx expand_builtin_memmove_args (tree, tree, tree, tree, rtx,
123 enum machine_mode, int);
124 static rtx expand_builtin_bcopy (tree, int);
125 static rtx expand_builtin_strcpy (tree, tree, rtx, enum machine_mode);
126 static rtx expand_builtin_strcpy_args (tree, tree, tree, rtx, enum machine_mode);
127 static rtx expand_builtin_stpcpy (tree, rtx, enum machine_mode);
128 static rtx expand_builtin_strncpy (tree, rtx, enum machine_mode);
129 static rtx builtin_memset_gen_str (void *, HOST_WIDE_INT, enum machine_mode);
130 static rtx expand_builtin_memset (tree, rtx, enum machine_mode);
131 static rtx expand_builtin_memset_args (tree, tree, tree, rtx, enum machine_mode, tree);
132 static rtx expand_builtin_bzero (tree);
133 static rtx expand_builtin_strlen (tree, rtx, enum machine_mode);
134 static rtx expand_builtin_strstr (tree, rtx, enum machine_mode);
135 static rtx expand_builtin_strpbrk (tree, rtx, enum machine_mode);
136 static rtx expand_builtin_strchr (tree, rtx, enum machine_mode);
137 static rtx expand_builtin_strrchr (tree, rtx, enum machine_mode);
138 static rtx expand_builtin_alloca (tree, rtx);
139 static rtx expand_builtin_unop (enum machine_mode, tree, rtx, rtx, optab);
140 static rtx expand_builtin_frame_address (tree, tree);
141 static rtx expand_builtin_fputs (tree, rtx, bool);
142 static rtx expand_builtin_printf (tree, rtx, enum machine_mode, bool);
143 static rtx expand_builtin_fprintf (tree, rtx, enum machine_mode, bool);
144 static rtx expand_builtin_sprintf (tree, rtx, enum machine_mode);
145 static tree stabilize_va_list (tree, int);
146 static rtx expand_builtin_expect (tree, rtx);
147 static tree fold_builtin_constant_p (tree);
148 static tree fold_builtin_expect (tree, tree);
149 static tree fold_builtin_classify_type (tree);
150 static tree fold_builtin_strlen (tree);
151 static tree fold_builtin_inf (tree, int);
152 static tree fold_builtin_nan (tree, tree, int);
153 static tree rewrite_call_expr (tree, int, tree, int, ...);
154 static bool validate_arg (const_tree, enum tree_code code);
155 static bool integer_valued_real_p (tree);
156 static tree fold_trunc_transparent_mathfn (tree, tree);
157 static bool readonly_data_expr (tree);
158 static rtx expand_builtin_fabs (tree, rtx, rtx);
159 static rtx expand_builtin_signbit (tree, rtx);
160 static tree fold_builtin_sqrt (tree, tree);
161 static tree fold_builtin_cbrt (tree, tree);
162 static tree fold_builtin_pow (tree, tree, tree, tree);
163 static tree fold_builtin_powi (tree, tree, tree, tree);
164 static tree fold_builtin_cos (tree, tree, tree);
165 static tree fold_builtin_cosh (tree, tree, tree);
166 static tree fold_builtin_tan (tree, tree);
167 static tree fold_builtin_trunc (tree, tree);
168 static tree fold_builtin_floor (tree, tree);
169 static tree fold_builtin_ceil (tree, tree);
170 static tree fold_builtin_round (tree, tree);
171 static tree fold_builtin_int_roundingfn (tree, tree);
172 static tree fold_builtin_bitop (tree, tree);
173 static tree fold_builtin_memory_op (tree, tree, tree, tree, bool, int);
174 static tree fold_builtin_strchr (tree, tree, tree);
175 static tree fold_builtin_memchr (tree, tree, tree, tree);
176 static tree fold_builtin_memcmp (tree, tree, tree);
177 static tree fold_builtin_strcmp (tree, tree);
178 static tree fold_builtin_strncmp (tree, tree, tree);
179 static tree fold_builtin_signbit (tree, tree);
180 static tree fold_builtin_copysign (tree, tree, tree, tree);
181 static tree fold_builtin_isascii (tree);
182 static tree fold_builtin_toascii (tree);
183 static tree fold_builtin_isdigit (tree);
184 static tree fold_builtin_fabs (tree, tree);
185 static tree fold_builtin_abs (tree, tree);
186 static tree fold_builtin_unordered_cmp (tree, tree, tree, enum tree_code,
187 enum tree_code);
188 static tree fold_builtin_n (tree, tree *, int, bool);
189 static tree fold_builtin_0 (tree, bool);
190 static tree fold_builtin_1 (tree, tree, bool);
191 static tree fold_builtin_2 (tree, tree, tree, bool);
192 static tree fold_builtin_3 (tree, tree, tree, tree, bool);
193 static tree fold_builtin_4 (tree, tree, tree, tree, tree, bool);
194 static tree fold_builtin_varargs (tree, tree, bool);
196 static tree fold_builtin_strpbrk (tree, tree, tree);
197 static tree fold_builtin_strstr (tree, tree, tree);
198 static tree fold_builtin_strrchr (tree, tree, tree);
199 static tree fold_builtin_strcat (tree, tree);
200 static tree fold_builtin_strncat (tree, tree, tree);
201 static tree fold_builtin_strspn (tree, tree);
202 static tree fold_builtin_strcspn (tree, tree);
203 static tree fold_builtin_sprintf (tree, tree, tree, int);
205 static rtx expand_builtin_object_size (tree);
206 static rtx expand_builtin_memory_chk (tree, rtx, enum machine_mode,
207 enum built_in_function);
208 static void maybe_emit_chk_warning (tree, enum built_in_function);
209 static void maybe_emit_sprintf_chk_warning (tree, enum built_in_function);
210 static tree fold_builtin_object_size (tree, tree);
211 static tree fold_builtin_strcat_chk (tree, tree, tree, tree);
212 static tree fold_builtin_strncat_chk (tree, tree, tree, tree, tree);
213 static tree fold_builtin_sprintf_chk (tree, enum built_in_function);
214 static tree fold_builtin_printf (tree, tree, tree, bool, enum built_in_function);
215 static tree fold_builtin_fprintf (tree, tree, tree, tree, bool,
216 enum built_in_function);
217 static bool init_target_chars (void);
219 static unsigned HOST_WIDE_INT target_newline;
220 static unsigned HOST_WIDE_INT target_percent;
221 static unsigned HOST_WIDE_INT target_c;
222 static unsigned HOST_WIDE_INT target_s;
223 static char target_percent_c[3];
224 static char target_percent_s[3];
225 static char target_percent_s_newline[4];
226 static tree do_mpfr_arg1 (tree, tree, int (*)(mpfr_ptr, mpfr_srcptr, mp_rnd_t),
227 const REAL_VALUE_TYPE *, const REAL_VALUE_TYPE *, bool);
228 static tree do_mpfr_arg2 (tree, tree, tree,
229 int (*)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t));
230 static tree do_mpfr_arg3 (tree, tree, tree, tree,
231 int (*)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t));
232 static tree do_mpfr_sincos (tree, tree, tree);
233 #if MPFR_VERSION >= MPFR_VERSION_NUM(2,3,0)
234 static tree do_mpfr_bessel_n (tree, tree, tree,
235 int (*)(mpfr_ptr, long, mpfr_srcptr, mp_rnd_t),
236 const REAL_VALUE_TYPE *, bool);
237 static tree do_mpfr_remquo (tree, tree, tree);
238 static tree do_mpfr_lgamma_r (tree, tree, tree);
239 #endif
241 /* Return true if NODE should be considered for inline expansion regardless
242 of the optimization level. This means whenever a function is invoked with
243 its "internal" name, which normally contains the prefix "__builtin". */
245 static bool called_as_built_in (tree node)
247 const char *name = IDENTIFIER_POINTER (DECL_NAME (node));
248 if (strncmp (name, "__builtin_", 10) == 0)
249 return true;
250 if (strncmp (name, "__sync_", 7) == 0)
251 return true;
252 return false;
255 /* Return the alignment in bits of EXP, a pointer valued expression.
256 But don't return more than MAX_ALIGN no matter what.
257 The alignment returned is, by default, the alignment of the thing that
258 EXP points to. If it is not a POINTER_TYPE, 0 is returned.
260 Otherwise, look at the expression to see if we can do better, i.e., if the
261 expression is actually pointing at an object whose alignment is tighter. */
264 get_pointer_alignment (tree exp, unsigned int max_align)
266 unsigned int align, inner;
268 /* We rely on TER to compute accurate alignment information. */
269 if (!(optimize && flag_tree_ter))
270 return 0;
272 if (!POINTER_TYPE_P (TREE_TYPE (exp)))
273 return 0;
275 align = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
276 align = MIN (align, max_align);
278 while (1)
280 switch (TREE_CODE (exp))
282 case NOP_EXPR:
283 case CONVERT_EXPR:
284 case NON_LVALUE_EXPR:
285 exp = TREE_OPERAND (exp, 0);
286 if (! POINTER_TYPE_P (TREE_TYPE (exp)))
287 return align;
289 inner = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
290 align = MIN (inner, max_align);
291 break;
293 case POINTER_PLUS_EXPR:
294 /* If sum of pointer + int, restrict our maximum alignment to that
295 imposed by the integer. If not, we can't do any better than
296 ALIGN. */
297 if (! host_integerp (TREE_OPERAND (exp, 1), 1))
298 return align;
300 while (((tree_low_cst (TREE_OPERAND (exp, 1), 1))
301 & (max_align / BITS_PER_UNIT - 1))
302 != 0)
303 max_align >>= 1;
305 exp = TREE_OPERAND (exp, 0);
306 break;
308 case ADDR_EXPR:
309 /* See what we are pointing at and look at its alignment. */
310 exp = TREE_OPERAND (exp, 0);
311 inner = max_align;
312 if (handled_component_p (exp))
314 HOST_WIDE_INT bitsize, bitpos;
315 tree offset;
316 enum machine_mode mode;
317 int unsignedp, volatilep;
319 exp = get_inner_reference (exp, &bitsize, &bitpos, &offset,
320 &mode, &unsignedp, &volatilep, true);
321 if (bitpos)
322 inner = MIN (inner, (unsigned) (bitpos & -bitpos));
323 if (offset && TREE_CODE (offset) == PLUS_EXPR
324 && host_integerp (TREE_OPERAND (offset, 1), 1))
326 /* Any overflow in calculating offset_bits won't change
327 the alignment. */
328 unsigned offset_bits
329 = ((unsigned) tree_low_cst (TREE_OPERAND (offset, 1), 1)
330 * BITS_PER_UNIT);
332 if (offset_bits)
333 inner = MIN (inner, (offset_bits & -offset_bits));
334 offset = TREE_OPERAND (offset, 0);
336 if (offset && TREE_CODE (offset) == MULT_EXPR
337 && host_integerp (TREE_OPERAND (offset, 1), 1))
339 /* Any overflow in calculating offset_factor won't change
340 the alignment. */
341 unsigned offset_factor
342 = ((unsigned) tree_low_cst (TREE_OPERAND (offset, 1), 1)
343 * BITS_PER_UNIT);
345 if (offset_factor)
346 inner = MIN (inner, (offset_factor & -offset_factor));
348 else if (offset)
349 inner = MIN (inner, BITS_PER_UNIT);
351 if (DECL_P (exp))
352 align = MIN (inner, DECL_ALIGN (exp));
353 #ifdef CONSTANT_ALIGNMENT
354 else if (CONSTANT_CLASS_P (exp))
355 align = MIN (inner, (unsigned)CONSTANT_ALIGNMENT (exp, align));
356 #endif
357 else if (TREE_CODE (exp) == VIEW_CONVERT_EXPR
358 || TREE_CODE (exp) == INDIRECT_REF)
359 align = MIN (TYPE_ALIGN (TREE_TYPE (exp)), inner);
360 else
361 align = MIN (align, inner);
362 return MIN (align, max_align);
364 default:
365 return align;
370 /* Compute the length of a C string. TREE_STRING_LENGTH is not the right
371 way, because it could contain a zero byte in the middle.
372 TREE_STRING_LENGTH is the size of the character array, not the string.
374 ONLY_VALUE should be nonzero if the result is not going to be emitted
375 into the instruction stream and zero if it is going to be expanded.
376 E.g. with i++ ? "foo" : "bar", if ONLY_VALUE is nonzero, constant 3
377 is returned, otherwise NULL, since
378 len = c_strlen (src, 1); if (len) expand_expr (len, ...); would not
379 evaluate the side-effects.
381 The value returned is of type `ssizetype'.
383 Unfortunately, string_constant can't access the values of const char
384 arrays with initializers, so neither can we do so here. */
386 tree
387 c_strlen (tree src, int only_value)
389 tree offset_node;
390 HOST_WIDE_INT offset;
391 int max;
392 const char *ptr;
394 STRIP_NOPS (src);
395 if (TREE_CODE (src) == COND_EXPR
396 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
398 tree len1, len2;
400 len1 = c_strlen (TREE_OPERAND (src, 1), only_value);
401 len2 = c_strlen (TREE_OPERAND (src, 2), only_value);
402 if (tree_int_cst_equal (len1, len2))
403 return len1;
406 if (TREE_CODE (src) == COMPOUND_EXPR
407 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
408 return c_strlen (TREE_OPERAND (src, 1), only_value);
410 src = string_constant (src, &offset_node);
411 if (src == 0)
412 return NULL_TREE;
414 max = TREE_STRING_LENGTH (src) - 1;
415 ptr = TREE_STRING_POINTER (src);
417 if (offset_node && TREE_CODE (offset_node) != INTEGER_CST)
419 /* If the string has an internal zero byte (e.g., "foo\0bar"), we can't
420 compute the offset to the following null if we don't know where to
421 start searching for it. */
422 int i;
424 for (i = 0; i < max; i++)
425 if (ptr[i] == 0)
426 return NULL_TREE;
428 /* We don't know the starting offset, but we do know that the string
429 has no internal zero bytes. We can assume that the offset falls
430 within the bounds of the string; otherwise, the programmer deserves
431 what he gets. Subtract the offset from the length of the string,
432 and return that. This would perhaps not be valid if we were dealing
433 with named arrays in addition to literal string constants. */
435 return size_diffop (size_int (max), offset_node);
438 /* We have a known offset into the string. Start searching there for
439 a null character if we can represent it as a single HOST_WIDE_INT. */
440 if (offset_node == 0)
441 offset = 0;
442 else if (! host_integerp (offset_node, 0))
443 offset = -1;
444 else
445 offset = tree_low_cst (offset_node, 0);
447 /* If the offset is known to be out of bounds, warn, and call strlen at
448 runtime. */
449 if (offset < 0 || offset > max)
451 warning (0, "offset outside bounds of constant string");
452 return NULL_TREE;
455 /* Use strlen to search for the first zero byte. Since any strings
456 constructed with build_string will have nulls appended, we win even
457 if we get handed something like (char[4])"abcd".
459 Since OFFSET is our starting index into the string, no further
460 calculation is needed. */
461 return ssize_int (strlen (ptr + offset));
464 /* Return a char pointer for a C string if it is a string constant
465 or sum of string constant and integer constant. */
467 static const char *
468 c_getstr (tree src)
470 tree offset_node;
472 src = string_constant (src, &offset_node);
473 if (src == 0)
474 return 0;
476 if (offset_node == 0)
477 return TREE_STRING_POINTER (src);
478 else if (!host_integerp (offset_node, 1)
479 || compare_tree_int (offset_node, TREE_STRING_LENGTH (src) - 1) > 0)
480 return 0;
482 return TREE_STRING_POINTER (src) + tree_low_cst (offset_node, 1);
485 /* Return a CONST_INT or CONST_DOUBLE corresponding to target reading
486 GET_MODE_BITSIZE (MODE) bits from string constant STR. */
488 static rtx
489 c_readstr (const char *str, enum machine_mode mode)
491 HOST_WIDE_INT c[2];
492 HOST_WIDE_INT ch;
493 unsigned int i, j;
495 gcc_assert (GET_MODE_CLASS (mode) == MODE_INT);
497 c[0] = 0;
498 c[1] = 0;
499 ch = 1;
500 for (i = 0; i < GET_MODE_SIZE (mode); i++)
502 j = i;
503 if (WORDS_BIG_ENDIAN)
504 j = GET_MODE_SIZE (mode) - i - 1;
505 if (BYTES_BIG_ENDIAN != WORDS_BIG_ENDIAN
506 && GET_MODE_SIZE (mode) > UNITS_PER_WORD)
507 j = j + UNITS_PER_WORD - 2 * (j % UNITS_PER_WORD) - 1;
508 j *= BITS_PER_UNIT;
509 gcc_assert (j <= 2 * HOST_BITS_PER_WIDE_INT);
511 if (ch)
512 ch = (unsigned char) str[i];
513 c[j / HOST_BITS_PER_WIDE_INT] |= ch << (j % HOST_BITS_PER_WIDE_INT);
515 return immed_double_const (c[0], c[1], mode);
518 /* Cast a target constant CST to target CHAR and if that value fits into
519 host char type, return zero and put that value into variable pointed to by
520 P. */
522 static int
523 target_char_cast (tree cst, char *p)
525 unsigned HOST_WIDE_INT val, hostval;
527 if (!host_integerp (cst, 1)
528 || CHAR_TYPE_SIZE > HOST_BITS_PER_WIDE_INT)
529 return 1;
531 val = tree_low_cst (cst, 1);
532 if (CHAR_TYPE_SIZE < HOST_BITS_PER_WIDE_INT)
533 val &= (((unsigned HOST_WIDE_INT) 1) << CHAR_TYPE_SIZE) - 1;
535 hostval = val;
536 if (HOST_BITS_PER_CHAR < HOST_BITS_PER_WIDE_INT)
537 hostval &= (((unsigned HOST_WIDE_INT) 1) << HOST_BITS_PER_CHAR) - 1;
539 if (val != hostval)
540 return 1;
542 *p = hostval;
543 return 0;
546 /* Similar to save_expr, but assumes that arbitrary code is not executed
547 in between the multiple evaluations. In particular, we assume that a
548 non-addressable local variable will not be modified. */
550 static tree
551 builtin_save_expr (tree exp)
553 if (TREE_ADDRESSABLE (exp) == 0
554 && (TREE_CODE (exp) == PARM_DECL
555 || (TREE_CODE (exp) == VAR_DECL && !TREE_STATIC (exp))))
556 return exp;
558 return save_expr (exp);
561 /* Given TEM, a pointer to a stack frame, follow the dynamic chain COUNT
562 times to get the address of either a higher stack frame, or a return
563 address located within it (depending on FNDECL_CODE). */
565 static rtx
566 expand_builtin_return_addr (enum built_in_function fndecl_code, int count)
568 int i;
570 #ifdef INITIAL_FRAME_ADDRESS_RTX
571 rtx tem = INITIAL_FRAME_ADDRESS_RTX;
572 #else
573 rtx tem;
575 /* For a zero count with __builtin_return_address, we don't care what
576 frame address we return, because target-specific definitions will
577 override us. Therefore frame pointer elimination is OK, and using
578 the soft frame pointer is OK.
580 For a nonzero count, or a zero count with __builtin_frame_address,
581 we require a stable offset from the current frame pointer to the
582 previous one, so we must use the hard frame pointer, and
583 we must disable frame pointer elimination. */
584 if (count == 0 && fndecl_code == BUILT_IN_RETURN_ADDRESS)
585 tem = frame_pointer_rtx;
586 else
588 tem = hard_frame_pointer_rtx;
590 /* Tell reload not to eliminate the frame pointer. */
591 current_function_accesses_prior_frames = 1;
593 #endif
595 /* Some machines need special handling before we can access
596 arbitrary frames. For example, on the SPARC, we must first flush
597 all register windows to the stack. */
598 #ifdef SETUP_FRAME_ADDRESSES
599 if (count > 0)
600 SETUP_FRAME_ADDRESSES ();
601 #endif
603 /* On the SPARC, the return address is not in the frame, it is in a
604 register. There is no way to access it off of the current frame
605 pointer, but it can be accessed off the previous frame pointer by
606 reading the value from the register window save area. */
607 #ifdef RETURN_ADDR_IN_PREVIOUS_FRAME
608 if (fndecl_code == BUILT_IN_RETURN_ADDRESS)
609 count--;
610 #endif
612 /* Scan back COUNT frames to the specified frame. */
613 for (i = 0; i < count; i++)
615 /* Assume the dynamic chain pointer is in the word that the
616 frame address points to, unless otherwise specified. */
617 #ifdef DYNAMIC_CHAIN_ADDRESS
618 tem = DYNAMIC_CHAIN_ADDRESS (tem);
619 #endif
620 tem = memory_address (Pmode, tem);
621 tem = gen_frame_mem (Pmode, tem);
622 tem = copy_to_reg (tem);
625 /* For __builtin_frame_address, return what we've got. But, on
626 the SPARC for example, we may have to add a bias. */
627 if (fndecl_code == BUILT_IN_FRAME_ADDRESS)
628 #ifdef FRAME_ADDR_RTX
629 return FRAME_ADDR_RTX (tem);
630 #else
631 return tem;
632 #endif
634 /* For __builtin_return_address, get the return address from that frame. */
635 #ifdef RETURN_ADDR_RTX
636 tem = RETURN_ADDR_RTX (count, tem);
637 #else
638 tem = memory_address (Pmode,
639 plus_constant (tem, GET_MODE_SIZE (Pmode)));
640 tem = gen_frame_mem (Pmode, tem);
641 #endif
642 return tem;
645 /* Alias set used for setjmp buffer. */
646 static alias_set_type setjmp_alias_set = -1;
648 /* Construct the leading half of a __builtin_setjmp call. Control will
649 return to RECEIVER_LABEL. This is also called directly by the SJLJ
650 exception handling code. */
652 void
653 expand_builtin_setjmp_setup (rtx buf_addr, rtx receiver_label)
655 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
656 rtx stack_save;
657 rtx mem;
659 if (setjmp_alias_set == -1)
660 setjmp_alias_set = new_alias_set ();
662 buf_addr = convert_memory_address (Pmode, buf_addr);
664 buf_addr = force_reg (Pmode, force_operand (buf_addr, NULL_RTX));
666 /* We store the frame pointer and the address of receiver_label in
667 the buffer and use the rest of it for the stack save area, which
668 is machine-dependent. */
670 mem = gen_rtx_MEM (Pmode, buf_addr);
671 set_mem_alias_set (mem, setjmp_alias_set);
672 emit_move_insn (mem, targetm.builtin_setjmp_frame_value ());
674 mem = gen_rtx_MEM (Pmode, plus_constant (buf_addr, GET_MODE_SIZE (Pmode))),
675 set_mem_alias_set (mem, setjmp_alias_set);
677 emit_move_insn (validize_mem (mem),
678 force_reg (Pmode, gen_rtx_LABEL_REF (Pmode, receiver_label)));
680 stack_save = gen_rtx_MEM (sa_mode,
681 plus_constant (buf_addr,
682 2 * GET_MODE_SIZE (Pmode)));
683 set_mem_alias_set (stack_save, setjmp_alias_set);
684 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
686 /* If there is further processing to do, do it. */
687 #ifdef HAVE_builtin_setjmp_setup
688 if (HAVE_builtin_setjmp_setup)
689 emit_insn (gen_builtin_setjmp_setup (buf_addr));
690 #endif
692 /* Tell optimize_save_area_alloca that extra work is going to
693 need to go on during alloca. */
694 current_function_calls_setjmp = 1;
696 /* We have a nonlocal label. */
697 current_function_has_nonlocal_label = 1;
700 /* Construct the trailing part of a __builtin_setjmp call. This is
701 also called directly by the SJLJ exception handling code. */
703 void
704 expand_builtin_setjmp_receiver (rtx receiver_label ATTRIBUTE_UNUSED)
706 /* Clobber the FP when we get here, so we have to make sure it's
707 marked as used by this function. */
708 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
710 /* Mark the static chain as clobbered here so life information
711 doesn't get messed up for it. */
712 emit_insn (gen_rtx_CLOBBER (VOIDmode, static_chain_rtx));
714 /* Now put in the code to restore the frame pointer, and argument
715 pointer, if needed. */
716 #ifdef HAVE_nonlocal_goto
717 if (! HAVE_nonlocal_goto)
718 #endif
720 emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
721 /* This might change the hard frame pointer in ways that aren't
722 apparent to early optimization passes, so force a clobber. */
723 emit_insn (gen_rtx_CLOBBER (VOIDmode, hard_frame_pointer_rtx));
726 #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM
727 if (fixed_regs[ARG_POINTER_REGNUM])
729 #ifdef ELIMINABLE_REGS
730 size_t i;
731 static const struct elims {const int from, to;} elim_regs[] = ELIMINABLE_REGS;
733 for (i = 0; i < ARRAY_SIZE (elim_regs); i++)
734 if (elim_regs[i].from == ARG_POINTER_REGNUM
735 && elim_regs[i].to == HARD_FRAME_POINTER_REGNUM)
736 break;
738 if (i == ARRAY_SIZE (elim_regs))
739 #endif
741 /* Now restore our arg pointer from the address at which it
742 was saved in our stack frame. */
743 emit_move_insn (virtual_incoming_args_rtx,
744 copy_to_reg (get_arg_pointer_save_area (cfun)));
747 #endif
749 #ifdef HAVE_builtin_setjmp_receiver
750 if (HAVE_builtin_setjmp_receiver)
751 emit_insn (gen_builtin_setjmp_receiver (receiver_label));
752 else
753 #endif
754 #ifdef HAVE_nonlocal_goto_receiver
755 if (HAVE_nonlocal_goto_receiver)
756 emit_insn (gen_nonlocal_goto_receiver ());
757 else
758 #endif
759 { /* Nothing */ }
761 /* We must not allow the code we just generated to be reordered by
762 scheduling. Specifically, the update of the frame pointer must
763 happen immediately, not later. */
764 emit_insn (gen_blockage ());
767 /* __builtin_longjmp is passed a pointer to an array of five words (not
768 all will be used on all machines). It operates similarly to the C
769 library function of the same name, but is more efficient. Much of
770 the code below is copied from the handling of non-local gotos. */
772 static void
773 expand_builtin_longjmp (rtx buf_addr, rtx value)
775 rtx fp, lab, stack, insn, last;
776 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
778 if (setjmp_alias_set == -1)
779 setjmp_alias_set = new_alias_set ();
781 buf_addr = convert_memory_address (Pmode, buf_addr);
783 buf_addr = force_reg (Pmode, buf_addr);
785 /* We used to store value in static_chain_rtx, but that fails if pointers
786 are smaller than integers. We instead require that the user must pass
787 a second argument of 1, because that is what builtin_setjmp will
788 return. This also makes EH slightly more efficient, since we are no
789 longer copying around a value that we don't care about. */
790 gcc_assert (value == const1_rtx);
792 last = get_last_insn ();
793 #ifdef HAVE_builtin_longjmp
794 if (HAVE_builtin_longjmp)
795 emit_insn (gen_builtin_longjmp (buf_addr));
796 else
797 #endif
799 fp = gen_rtx_MEM (Pmode, buf_addr);
800 lab = gen_rtx_MEM (Pmode, plus_constant (buf_addr,
801 GET_MODE_SIZE (Pmode)));
803 stack = gen_rtx_MEM (sa_mode, plus_constant (buf_addr,
804 2 * GET_MODE_SIZE (Pmode)));
805 set_mem_alias_set (fp, setjmp_alias_set);
806 set_mem_alias_set (lab, setjmp_alias_set);
807 set_mem_alias_set (stack, setjmp_alias_set);
809 /* Pick up FP, label, and SP from the block and jump. This code is
810 from expand_goto in stmt.c; see there for detailed comments. */
811 #ifdef HAVE_nonlocal_goto
812 if (HAVE_nonlocal_goto)
813 /* We have to pass a value to the nonlocal_goto pattern that will
814 get copied into the static_chain pointer, but it does not matter
815 what that value is, because builtin_setjmp does not use it. */
816 emit_insn (gen_nonlocal_goto (value, lab, stack, fp));
817 else
818 #endif
820 lab = copy_to_reg (lab);
822 emit_insn (gen_rtx_CLOBBER (VOIDmode,
823 gen_rtx_MEM (BLKmode,
824 gen_rtx_SCRATCH (VOIDmode))));
825 emit_insn (gen_rtx_CLOBBER (VOIDmode,
826 gen_rtx_MEM (BLKmode,
827 hard_frame_pointer_rtx)));
829 emit_move_insn (hard_frame_pointer_rtx, fp);
830 emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
832 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
833 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
834 emit_indirect_jump (lab);
838 /* Search backwards and mark the jump insn as a non-local goto.
839 Note that this precludes the use of __builtin_longjmp to a
840 __builtin_setjmp target in the same function. However, we've
841 already cautioned the user that these functions are for
842 internal exception handling use only. */
843 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
845 gcc_assert (insn != last);
847 if (JUMP_P (insn))
849 REG_NOTES (insn) = alloc_EXPR_LIST (REG_NON_LOCAL_GOTO, const0_rtx,
850 REG_NOTES (insn));
851 break;
853 else if (CALL_P (insn))
854 break;
858 /* Expand a call to __builtin_nonlocal_goto. We're passed the target label
859 and the address of the save area. */
861 static rtx
862 expand_builtin_nonlocal_goto (tree exp)
864 tree t_label, t_save_area;
865 rtx r_label, r_save_area, r_fp, r_sp, insn;
867 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
868 return NULL_RTX;
870 t_label = CALL_EXPR_ARG (exp, 0);
871 t_save_area = CALL_EXPR_ARG (exp, 1);
873 r_label = expand_normal (t_label);
874 r_label = convert_memory_address (Pmode, r_label);
875 r_save_area = expand_normal (t_save_area);
876 r_save_area = convert_memory_address (Pmode, r_save_area);
877 r_fp = gen_rtx_MEM (Pmode, r_save_area);
878 r_sp = gen_rtx_MEM (STACK_SAVEAREA_MODE (SAVE_NONLOCAL),
879 plus_constant (r_save_area, GET_MODE_SIZE (Pmode)));
881 current_function_has_nonlocal_goto = 1;
883 #ifdef HAVE_nonlocal_goto
884 /* ??? We no longer need to pass the static chain value, afaik. */
885 if (HAVE_nonlocal_goto)
886 emit_insn (gen_nonlocal_goto (const0_rtx, r_label, r_sp, r_fp));
887 else
888 #endif
890 r_label = copy_to_reg (r_label);
892 emit_insn (gen_rtx_CLOBBER (VOIDmode,
893 gen_rtx_MEM (BLKmode,
894 gen_rtx_SCRATCH (VOIDmode))));
896 emit_insn (gen_rtx_CLOBBER (VOIDmode,
897 gen_rtx_MEM (BLKmode,
898 hard_frame_pointer_rtx)));
900 /* Restore frame pointer for containing function.
901 This sets the actual hard register used for the frame pointer
902 to the location of the function's incoming static chain info.
903 The non-local goto handler will then adjust it to contain the
904 proper value and reload the argument pointer, if needed. */
905 emit_move_insn (hard_frame_pointer_rtx, r_fp);
906 emit_stack_restore (SAVE_NONLOCAL, r_sp, NULL_RTX);
908 /* USE of hard_frame_pointer_rtx added for consistency;
909 not clear if really needed. */
910 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
911 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
912 emit_indirect_jump (r_label);
915 /* Search backwards to the jump insn and mark it as a
916 non-local goto. */
917 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
919 if (JUMP_P (insn))
921 REG_NOTES (insn) = alloc_EXPR_LIST (REG_NON_LOCAL_GOTO,
922 const0_rtx, REG_NOTES (insn));
923 break;
925 else if (CALL_P (insn))
926 break;
929 return const0_rtx;
932 /* __builtin_update_setjmp_buf is passed a pointer to an array of five words
933 (not all will be used on all machines) that was passed to __builtin_setjmp.
934 It updates the stack pointer in that block to correspond to the current
935 stack pointer. */
937 static void
938 expand_builtin_update_setjmp_buf (rtx buf_addr)
940 enum machine_mode sa_mode = Pmode;
941 rtx stack_save;
944 #ifdef HAVE_save_stack_nonlocal
945 if (HAVE_save_stack_nonlocal)
946 sa_mode = insn_data[(int) CODE_FOR_save_stack_nonlocal].operand[0].mode;
947 #endif
948 #ifdef STACK_SAVEAREA_MODE
949 sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
950 #endif
952 stack_save
953 = gen_rtx_MEM (sa_mode,
954 memory_address
955 (sa_mode,
956 plus_constant (buf_addr, 2 * GET_MODE_SIZE (Pmode))));
958 #ifdef HAVE_setjmp
959 if (HAVE_setjmp)
960 emit_insn (gen_setjmp ());
961 #endif
963 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
966 /* Expand a call to __builtin_prefetch. For a target that does not support
967 data prefetch, evaluate the memory address argument in case it has side
968 effects. */
970 static void
971 expand_builtin_prefetch (tree exp)
973 tree arg0, arg1, arg2;
974 int nargs;
975 rtx op0, op1, op2;
977 if (!validate_arglist (exp, POINTER_TYPE, 0))
978 return;
980 arg0 = CALL_EXPR_ARG (exp, 0);
982 /* Arguments 1 and 2 are optional; argument 1 (read/write) defaults to
983 zero (read) and argument 2 (locality) defaults to 3 (high degree of
984 locality). */
985 nargs = call_expr_nargs (exp);
986 if (nargs > 1)
987 arg1 = CALL_EXPR_ARG (exp, 1);
988 else
989 arg1 = integer_zero_node;
990 if (nargs > 2)
991 arg2 = CALL_EXPR_ARG (exp, 2);
992 else
993 arg2 = build_int_cst (NULL_TREE, 3);
995 /* Argument 0 is an address. */
996 op0 = expand_expr (arg0, NULL_RTX, Pmode, EXPAND_NORMAL);
998 /* Argument 1 (read/write flag) must be a compile-time constant int. */
999 if (TREE_CODE (arg1) != INTEGER_CST)
1001 error ("second argument to %<__builtin_prefetch%> must be a constant");
1002 arg1 = integer_zero_node;
1004 op1 = expand_normal (arg1);
1005 /* Argument 1 must be either zero or one. */
1006 if (INTVAL (op1) != 0 && INTVAL (op1) != 1)
1008 warning (0, "invalid second argument to %<__builtin_prefetch%>;"
1009 " using zero");
1010 op1 = const0_rtx;
1013 /* Argument 2 (locality) must be a compile-time constant int. */
1014 if (TREE_CODE (arg2) != INTEGER_CST)
1016 error ("third argument to %<__builtin_prefetch%> must be a constant");
1017 arg2 = integer_zero_node;
1019 op2 = expand_normal (arg2);
1020 /* Argument 2 must be 0, 1, 2, or 3. */
1021 if (INTVAL (op2) < 0 || INTVAL (op2) > 3)
1023 warning (0, "invalid third argument to %<__builtin_prefetch%>; using zero");
1024 op2 = const0_rtx;
1027 #ifdef HAVE_prefetch
1028 if (HAVE_prefetch)
1030 if ((! (*insn_data[(int) CODE_FOR_prefetch].operand[0].predicate)
1031 (op0,
1032 insn_data[(int) CODE_FOR_prefetch].operand[0].mode))
1033 || (GET_MODE (op0) != Pmode))
1035 op0 = convert_memory_address (Pmode, op0);
1036 op0 = force_reg (Pmode, op0);
1038 emit_insn (gen_prefetch (op0, op1, op2));
1040 #endif
1042 /* Don't do anything with direct references to volatile memory, but
1043 generate code to handle other side effects. */
1044 if (!MEM_P (op0) && side_effects_p (op0))
1045 emit_insn (op0);
1048 /* Get a MEM rtx for expression EXP which is the address of an operand
1049 to be used in a string instruction (cmpstrsi, movmemsi, ..). LEN is
1050 the maximum length of the block of memory that might be accessed or
1051 NULL if unknown. */
1053 static rtx
1054 get_memory_rtx (tree exp, tree len)
1056 rtx addr = expand_expr (exp, NULL_RTX, ptr_mode, EXPAND_NORMAL);
1057 rtx mem = gen_rtx_MEM (BLKmode, memory_address (BLKmode, addr));
1059 /* Get an expression we can use to find the attributes to assign to MEM.
1060 If it is an ADDR_EXPR, use the operand. Otherwise, dereference it if
1061 we can. First remove any nops. */
1062 while ((TREE_CODE (exp) == NOP_EXPR || TREE_CODE (exp) == CONVERT_EXPR
1063 || TREE_CODE (exp) == NON_LVALUE_EXPR)
1064 && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (exp, 0))))
1065 exp = TREE_OPERAND (exp, 0);
1067 if (TREE_CODE (exp) == ADDR_EXPR)
1068 exp = TREE_OPERAND (exp, 0);
1069 else if (POINTER_TYPE_P (TREE_TYPE (exp)))
1070 exp = build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (exp)), exp);
1071 else
1072 exp = NULL;
1074 /* Honor attributes derived from exp, except for the alias set
1075 (as builtin stringops may alias with anything) and the size
1076 (as stringops may access multiple array elements). */
1077 if (exp)
1079 set_mem_attributes (mem, exp, 0);
1081 /* Allow the string and memory builtins to overflow from one
1082 field into another, see http://gcc.gnu.org/PR23561.
1083 Thus avoid COMPONENT_REFs in MEM_EXPR unless we know the whole
1084 memory accessed by the string or memory builtin will fit
1085 within the field. */
1086 if (MEM_EXPR (mem) && TREE_CODE (MEM_EXPR (mem)) == COMPONENT_REF)
1088 tree mem_expr = MEM_EXPR (mem);
1089 HOST_WIDE_INT offset = -1, length = -1;
1090 tree inner = exp;
1092 while (TREE_CODE (inner) == ARRAY_REF
1093 || TREE_CODE (inner) == NOP_EXPR
1094 || TREE_CODE (inner) == CONVERT_EXPR
1095 || TREE_CODE (inner) == NON_LVALUE_EXPR
1096 || TREE_CODE (inner) == VIEW_CONVERT_EXPR
1097 || TREE_CODE (inner) == SAVE_EXPR)
1098 inner = TREE_OPERAND (inner, 0);
1100 gcc_assert (TREE_CODE (inner) == COMPONENT_REF);
1102 if (MEM_OFFSET (mem)
1103 && GET_CODE (MEM_OFFSET (mem)) == CONST_INT)
1104 offset = INTVAL (MEM_OFFSET (mem));
1106 if (offset >= 0 && len && host_integerp (len, 0))
1107 length = tree_low_cst (len, 0);
1109 while (TREE_CODE (inner) == COMPONENT_REF)
1111 tree field = TREE_OPERAND (inner, 1);
1112 gcc_assert (! DECL_BIT_FIELD (field));
1113 gcc_assert (TREE_CODE (mem_expr) == COMPONENT_REF);
1114 gcc_assert (field == TREE_OPERAND (mem_expr, 1));
1116 if (length >= 0
1117 && TYPE_SIZE_UNIT (TREE_TYPE (inner))
1118 && host_integerp (TYPE_SIZE_UNIT (TREE_TYPE (inner)), 0))
1120 HOST_WIDE_INT size
1121 = tree_low_cst (TYPE_SIZE_UNIT (TREE_TYPE (inner)), 0);
1122 /* If we can prove the memory starting at XEXP (mem, 0)
1123 and ending at XEXP (mem, 0) + LENGTH will fit into
1124 this field, we can keep that COMPONENT_REF in MEM_EXPR. */
1125 if (offset <= size
1126 && length <= size
1127 && offset + length <= size)
1128 break;
1131 if (offset >= 0
1132 && host_integerp (DECL_FIELD_OFFSET (field), 0))
1133 offset += tree_low_cst (DECL_FIELD_OFFSET (field), 0)
1134 + tree_low_cst (DECL_FIELD_BIT_OFFSET (field), 1)
1135 / BITS_PER_UNIT;
1136 else
1138 offset = -1;
1139 length = -1;
1142 mem_expr = TREE_OPERAND (mem_expr, 0);
1143 inner = TREE_OPERAND (inner, 0);
1146 if (mem_expr == NULL)
1147 offset = -1;
1148 if (mem_expr != MEM_EXPR (mem))
1150 set_mem_expr (mem, mem_expr);
1151 set_mem_offset (mem, offset >= 0 ? GEN_INT (offset) : NULL_RTX);
1154 set_mem_alias_set (mem, 0);
1155 set_mem_size (mem, NULL_RTX);
1158 return mem;
1161 /* Built-in functions to perform an untyped call and return. */
1163 /* For each register that may be used for calling a function, this
1164 gives a mode used to copy the register's value. VOIDmode indicates
1165 the register is not used for calling a function. If the machine
1166 has register windows, this gives only the outbound registers.
1167 INCOMING_REGNO gives the corresponding inbound register. */
1168 static enum machine_mode apply_args_mode[FIRST_PSEUDO_REGISTER];
1170 /* For each register that may be used for returning values, this gives
1171 a mode used to copy the register's value. VOIDmode indicates the
1172 register is not used for returning values. If the machine has
1173 register windows, this gives only the outbound registers.
1174 INCOMING_REGNO gives the corresponding inbound register. */
1175 static enum machine_mode apply_result_mode[FIRST_PSEUDO_REGISTER];
1177 /* For each register that may be used for calling a function, this
1178 gives the offset of that register into the block returned by
1179 __builtin_apply_args. 0 indicates that the register is not
1180 used for calling a function. */
1181 static int apply_args_reg_offset[FIRST_PSEUDO_REGISTER];
1183 /* Return the size required for the block returned by __builtin_apply_args,
1184 and initialize apply_args_mode. */
1186 static int
1187 apply_args_size (void)
1189 static int size = -1;
1190 int align;
1191 unsigned int regno;
1192 enum machine_mode mode;
1194 /* The values computed by this function never change. */
1195 if (size < 0)
1197 /* The first value is the incoming arg-pointer. */
1198 size = GET_MODE_SIZE (Pmode);
1200 /* The second value is the structure value address unless this is
1201 passed as an "invisible" first argument. */
1202 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1203 size += GET_MODE_SIZE (Pmode);
1205 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1206 if (FUNCTION_ARG_REGNO_P (regno))
1208 mode = reg_raw_mode[regno];
1210 gcc_assert (mode != VOIDmode);
1212 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1213 if (size % align != 0)
1214 size = CEIL (size, align) * align;
1215 apply_args_reg_offset[regno] = size;
1216 size += GET_MODE_SIZE (mode);
1217 apply_args_mode[regno] = mode;
1219 else
1221 apply_args_mode[regno] = VOIDmode;
1222 apply_args_reg_offset[regno] = 0;
1225 return size;
1228 /* Return the size required for the block returned by __builtin_apply,
1229 and initialize apply_result_mode. */
1231 static int
1232 apply_result_size (void)
1234 static int size = -1;
1235 int align, regno;
1236 enum machine_mode mode;
1238 /* The values computed by this function never change. */
1239 if (size < 0)
1241 size = 0;
1243 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1244 if (FUNCTION_VALUE_REGNO_P (regno))
1246 mode = reg_raw_mode[regno];
1248 gcc_assert (mode != VOIDmode);
1250 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1251 if (size % align != 0)
1252 size = CEIL (size, align) * align;
1253 size += GET_MODE_SIZE (mode);
1254 apply_result_mode[regno] = mode;
1256 else
1257 apply_result_mode[regno] = VOIDmode;
1259 /* Allow targets that use untyped_call and untyped_return to override
1260 the size so that machine-specific information can be stored here. */
1261 #ifdef APPLY_RESULT_SIZE
1262 size = APPLY_RESULT_SIZE;
1263 #endif
1265 return size;
1268 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
1269 /* Create a vector describing the result block RESULT. If SAVEP is true,
1270 the result block is used to save the values; otherwise it is used to
1271 restore the values. */
1273 static rtx
1274 result_vector (int savep, rtx result)
1276 int regno, size, align, nelts;
1277 enum machine_mode mode;
1278 rtx reg, mem;
1279 rtx *savevec = alloca (FIRST_PSEUDO_REGISTER * sizeof (rtx));
1281 size = nelts = 0;
1282 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1283 if ((mode = apply_result_mode[regno]) != VOIDmode)
1285 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1286 if (size % align != 0)
1287 size = CEIL (size, align) * align;
1288 reg = gen_rtx_REG (mode, savep ? regno : INCOMING_REGNO (regno));
1289 mem = adjust_address (result, mode, size);
1290 savevec[nelts++] = (savep
1291 ? gen_rtx_SET (VOIDmode, mem, reg)
1292 : gen_rtx_SET (VOIDmode, reg, mem));
1293 size += GET_MODE_SIZE (mode);
1295 return gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (nelts, savevec));
1297 #endif /* HAVE_untyped_call or HAVE_untyped_return */
1299 /* Save the state required to perform an untyped call with the same
1300 arguments as were passed to the current function. */
1302 static rtx
1303 expand_builtin_apply_args_1 (void)
1305 rtx registers, tem;
1306 int size, align, regno;
1307 enum machine_mode mode;
1308 rtx struct_incoming_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 1);
1310 /* Create a block where the arg-pointer, structure value address,
1311 and argument registers can be saved. */
1312 registers = assign_stack_local (BLKmode, apply_args_size (), -1);
1314 /* Walk past the arg-pointer and structure value address. */
1315 size = GET_MODE_SIZE (Pmode);
1316 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1317 size += GET_MODE_SIZE (Pmode);
1319 /* Save each register used in calling a function to the block. */
1320 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1321 if ((mode = apply_args_mode[regno]) != VOIDmode)
1323 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1324 if (size % align != 0)
1325 size = CEIL (size, align) * align;
1327 tem = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1329 emit_move_insn (adjust_address (registers, mode, size), tem);
1330 size += GET_MODE_SIZE (mode);
1333 /* Save the arg pointer to the block. */
1334 tem = copy_to_reg (virtual_incoming_args_rtx);
1335 #ifdef STACK_GROWS_DOWNWARD
1336 /* We need the pointer as the caller actually passed them to us, not
1337 as we might have pretended they were passed. Make sure it's a valid
1338 operand, as emit_move_insn isn't expected to handle a PLUS. */
1340 = force_operand (plus_constant (tem, current_function_pretend_args_size),
1341 NULL_RTX);
1342 #endif
1343 emit_move_insn (adjust_address (registers, Pmode, 0), tem);
1345 size = GET_MODE_SIZE (Pmode);
1347 /* Save the structure value address unless this is passed as an
1348 "invisible" first argument. */
1349 if (struct_incoming_value)
1351 emit_move_insn (adjust_address (registers, Pmode, size),
1352 copy_to_reg (struct_incoming_value));
1353 size += GET_MODE_SIZE (Pmode);
1356 /* Return the address of the block. */
1357 return copy_addr_to_reg (XEXP (registers, 0));
1360 /* __builtin_apply_args returns block of memory allocated on
1361 the stack into which is stored the arg pointer, structure
1362 value address, static chain, and all the registers that might
1363 possibly be used in performing a function call. The code is
1364 moved to the start of the function so the incoming values are
1365 saved. */
1367 static rtx
1368 expand_builtin_apply_args (void)
1370 /* Don't do __builtin_apply_args more than once in a function.
1371 Save the result of the first call and reuse it. */
1372 if (apply_args_value != 0)
1373 return apply_args_value;
1375 /* When this function is called, it means that registers must be
1376 saved on entry to this function. So we migrate the
1377 call to the first insn of this function. */
1378 rtx temp;
1379 rtx seq;
1381 start_sequence ();
1382 temp = expand_builtin_apply_args_1 ();
1383 seq = get_insns ();
1384 end_sequence ();
1386 apply_args_value = temp;
1388 /* Put the insns after the NOTE that starts the function.
1389 If this is inside a start_sequence, make the outer-level insn
1390 chain current, so the code is placed at the start of the
1391 function. */
1392 push_topmost_sequence ();
1393 emit_insn_before (seq, NEXT_INSN (entry_of_function ()));
1394 pop_topmost_sequence ();
1395 return temp;
1399 /* Perform an untyped call and save the state required to perform an
1400 untyped return of whatever value was returned by the given function. */
1402 static rtx
1403 expand_builtin_apply (rtx function, rtx arguments, rtx argsize)
1405 int size, align, regno;
1406 enum machine_mode mode;
1407 rtx incoming_args, result, reg, dest, src, call_insn;
1408 rtx old_stack_level = 0;
1409 rtx call_fusage = 0;
1410 rtx struct_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0);
1412 arguments = convert_memory_address (Pmode, arguments);
1414 /* Create a block where the return registers can be saved. */
1415 result = assign_stack_local (BLKmode, apply_result_size (), -1);
1417 /* Fetch the arg pointer from the ARGUMENTS block. */
1418 incoming_args = gen_reg_rtx (Pmode);
1419 emit_move_insn (incoming_args, gen_rtx_MEM (Pmode, arguments));
1420 #ifndef STACK_GROWS_DOWNWARD
1421 incoming_args = expand_simple_binop (Pmode, MINUS, incoming_args, argsize,
1422 incoming_args, 0, OPTAB_LIB_WIDEN);
1423 #endif
1425 /* Push a new argument block and copy the arguments. Do not allow
1426 the (potential) memcpy call below to interfere with our stack
1427 manipulations. */
1428 do_pending_stack_adjust ();
1429 NO_DEFER_POP;
1431 /* Save the stack with nonlocal if available. */
1432 #ifdef HAVE_save_stack_nonlocal
1433 if (HAVE_save_stack_nonlocal)
1434 emit_stack_save (SAVE_NONLOCAL, &old_stack_level, NULL_RTX);
1435 else
1436 #endif
1437 emit_stack_save (SAVE_BLOCK, &old_stack_level, NULL_RTX);
1439 /* Allocate a block of memory onto the stack and copy the memory
1440 arguments to the outgoing arguments address. */
1441 allocate_dynamic_stack_space (argsize, 0, BITS_PER_UNIT);
1442 dest = virtual_outgoing_args_rtx;
1443 #ifndef STACK_GROWS_DOWNWARD
1444 if (GET_CODE (argsize) == CONST_INT)
1445 dest = plus_constant (dest, -INTVAL (argsize));
1446 else
1447 dest = gen_rtx_PLUS (Pmode, dest, negate_rtx (Pmode, argsize));
1448 #endif
1449 dest = gen_rtx_MEM (BLKmode, dest);
1450 set_mem_align (dest, PARM_BOUNDARY);
1451 src = gen_rtx_MEM (BLKmode, incoming_args);
1452 set_mem_align (src, PARM_BOUNDARY);
1453 emit_block_move (dest, src, argsize, BLOCK_OP_NORMAL);
1455 /* Refer to the argument block. */
1456 apply_args_size ();
1457 arguments = gen_rtx_MEM (BLKmode, arguments);
1458 set_mem_align (arguments, PARM_BOUNDARY);
1460 /* Walk past the arg-pointer and structure value address. */
1461 size = GET_MODE_SIZE (Pmode);
1462 if (struct_value)
1463 size += GET_MODE_SIZE (Pmode);
1465 /* Restore each of the registers previously saved. Make USE insns
1466 for each of these registers for use in making the call. */
1467 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1468 if ((mode = apply_args_mode[regno]) != VOIDmode)
1470 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1471 if (size % align != 0)
1472 size = CEIL (size, align) * align;
1473 reg = gen_rtx_REG (mode, regno);
1474 emit_move_insn (reg, adjust_address (arguments, mode, size));
1475 use_reg (&call_fusage, reg);
1476 size += GET_MODE_SIZE (mode);
1479 /* Restore the structure value address unless this is passed as an
1480 "invisible" first argument. */
1481 size = GET_MODE_SIZE (Pmode);
1482 if (struct_value)
1484 rtx value = gen_reg_rtx (Pmode);
1485 emit_move_insn (value, adjust_address (arguments, Pmode, size));
1486 emit_move_insn (struct_value, value);
1487 if (REG_P (struct_value))
1488 use_reg (&call_fusage, struct_value);
1489 size += GET_MODE_SIZE (Pmode);
1492 /* All arguments and registers used for the call are set up by now! */
1493 function = prepare_call_address (function, NULL, &call_fusage, 0, 0);
1495 /* Ensure address is valid. SYMBOL_REF is already valid, so no need,
1496 and we don't want to load it into a register as an optimization,
1497 because prepare_call_address already did it if it should be done. */
1498 if (GET_CODE (function) != SYMBOL_REF)
1499 function = memory_address (FUNCTION_MODE, function);
1501 /* Generate the actual call instruction and save the return value. */
1502 #ifdef HAVE_untyped_call
1503 if (HAVE_untyped_call)
1504 emit_call_insn (gen_untyped_call (gen_rtx_MEM (FUNCTION_MODE, function),
1505 result, result_vector (1, result)));
1506 else
1507 #endif
1508 #ifdef HAVE_call_value
1509 if (HAVE_call_value)
1511 rtx valreg = 0;
1513 /* Locate the unique return register. It is not possible to
1514 express a call that sets more than one return register using
1515 call_value; use untyped_call for that. In fact, untyped_call
1516 only needs to save the return registers in the given block. */
1517 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1518 if ((mode = apply_result_mode[regno]) != VOIDmode)
1520 gcc_assert (!valreg); /* HAVE_untyped_call required. */
1522 valreg = gen_rtx_REG (mode, regno);
1525 emit_call_insn (GEN_CALL_VALUE (valreg,
1526 gen_rtx_MEM (FUNCTION_MODE, function),
1527 const0_rtx, NULL_RTX, const0_rtx));
1529 emit_move_insn (adjust_address (result, GET_MODE (valreg), 0), valreg);
1531 else
1532 #endif
1533 gcc_unreachable ();
1535 /* Find the CALL insn we just emitted, and attach the register usage
1536 information. */
1537 call_insn = last_call_insn ();
1538 add_function_usage_to (call_insn, call_fusage);
1540 /* Restore the stack. */
1541 #ifdef HAVE_save_stack_nonlocal
1542 if (HAVE_save_stack_nonlocal)
1543 emit_stack_restore (SAVE_NONLOCAL, old_stack_level, NULL_RTX);
1544 else
1545 #endif
1546 emit_stack_restore (SAVE_BLOCK, old_stack_level, NULL_RTX);
1548 OK_DEFER_POP;
1550 /* Return the address of the result block. */
1551 result = copy_addr_to_reg (XEXP (result, 0));
1552 return convert_memory_address (ptr_mode, result);
1555 /* Perform an untyped return. */
1557 static void
1558 expand_builtin_return (rtx result)
1560 int size, align, regno;
1561 enum machine_mode mode;
1562 rtx reg;
1563 rtx call_fusage = 0;
1565 result = convert_memory_address (Pmode, result);
1567 apply_result_size ();
1568 result = gen_rtx_MEM (BLKmode, result);
1570 #ifdef HAVE_untyped_return
1571 if (HAVE_untyped_return)
1573 emit_jump_insn (gen_untyped_return (result, result_vector (0, result)));
1574 emit_barrier ();
1575 return;
1577 #endif
1579 /* Restore the return value and note that each value is used. */
1580 size = 0;
1581 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1582 if ((mode = apply_result_mode[regno]) != VOIDmode)
1584 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1585 if (size % align != 0)
1586 size = CEIL (size, align) * align;
1587 reg = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1588 emit_move_insn (reg, adjust_address (result, mode, size));
1590 push_to_sequence (call_fusage);
1591 emit_insn (gen_rtx_USE (VOIDmode, reg));
1592 call_fusage = get_insns ();
1593 end_sequence ();
1594 size += GET_MODE_SIZE (mode);
1597 /* Put the USE insns before the return. */
1598 emit_insn (call_fusage);
1600 /* Return whatever values was restored by jumping directly to the end
1601 of the function. */
1602 expand_naked_return ();
1605 /* Used by expand_builtin_classify_type and fold_builtin_classify_type. */
1607 static enum type_class
1608 type_to_class (tree type)
1610 switch (TREE_CODE (type))
1612 case VOID_TYPE: return void_type_class;
1613 case INTEGER_TYPE: return integer_type_class;
1614 case ENUMERAL_TYPE: return enumeral_type_class;
1615 case BOOLEAN_TYPE: return boolean_type_class;
1616 case POINTER_TYPE: return pointer_type_class;
1617 case REFERENCE_TYPE: return reference_type_class;
1618 case OFFSET_TYPE: return offset_type_class;
1619 case REAL_TYPE: return real_type_class;
1620 case COMPLEX_TYPE: return complex_type_class;
1621 case FUNCTION_TYPE: return function_type_class;
1622 case METHOD_TYPE: return method_type_class;
1623 case RECORD_TYPE: return record_type_class;
1624 case UNION_TYPE:
1625 case QUAL_UNION_TYPE: return union_type_class;
1626 case ARRAY_TYPE: return (TYPE_STRING_FLAG (type)
1627 ? string_type_class : array_type_class);
1628 case LANG_TYPE: return lang_type_class;
1629 default: return no_type_class;
1633 /* Expand a call EXP to __builtin_classify_type. */
1635 static rtx
1636 expand_builtin_classify_type (tree exp)
1638 if (call_expr_nargs (exp))
1639 return GEN_INT (type_to_class (TREE_TYPE (CALL_EXPR_ARG (exp, 0))));
1640 return GEN_INT (no_type_class);
1643 /* This helper macro, meant to be used in mathfn_built_in below,
1644 determines which among a set of three builtin math functions is
1645 appropriate for a given type mode. The `F' and `L' cases are
1646 automatically generated from the `double' case. */
1647 #define CASE_MATHFN(BUILT_IN_MATHFN) \
1648 case BUILT_IN_MATHFN: case BUILT_IN_MATHFN##F: case BUILT_IN_MATHFN##L: \
1649 fcode = BUILT_IN_MATHFN; fcodef = BUILT_IN_MATHFN##F ; \
1650 fcodel = BUILT_IN_MATHFN##L ; break;
1651 /* Similar to above, but appends _R after any F/L suffix. */
1652 #define CASE_MATHFN_REENT(BUILT_IN_MATHFN) \
1653 case BUILT_IN_MATHFN##_R: case BUILT_IN_MATHFN##F_R: case BUILT_IN_MATHFN##L_R: \
1654 fcode = BUILT_IN_MATHFN##_R; fcodef = BUILT_IN_MATHFN##F_R ; \
1655 fcodel = BUILT_IN_MATHFN##L_R ; break;
1657 /* Return mathematic function equivalent to FN but operating directly
1658 on TYPE, if available. If we can't do the conversion, return zero. */
1659 tree
1660 mathfn_built_in (tree type, enum built_in_function fn)
1662 enum built_in_function fcode, fcodef, fcodel;
1664 switch (fn)
1666 CASE_MATHFN (BUILT_IN_ACOS)
1667 CASE_MATHFN (BUILT_IN_ACOSH)
1668 CASE_MATHFN (BUILT_IN_ASIN)
1669 CASE_MATHFN (BUILT_IN_ASINH)
1670 CASE_MATHFN (BUILT_IN_ATAN)
1671 CASE_MATHFN (BUILT_IN_ATAN2)
1672 CASE_MATHFN (BUILT_IN_ATANH)
1673 CASE_MATHFN (BUILT_IN_CBRT)
1674 CASE_MATHFN (BUILT_IN_CEIL)
1675 CASE_MATHFN (BUILT_IN_CEXPI)
1676 CASE_MATHFN (BUILT_IN_COPYSIGN)
1677 CASE_MATHFN (BUILT_IN_COS)
1678 CASE_MATHFN (BUILT_IN_COSH)
1679 CASE_MATHFN (BUILT_IN_DREM)
1680 CASE_MATHFN (BUILT_IN_ERF)
1681 CASE_MATHFN (BUILT_IN_ERFC)
1682 CASE_MATHFN (BUILT_IN_EXP)
1683 CASE_MATHFN (BUILT_IN_EXP10)
1684 CASE_MATHFN (BUILT_IN_EXP2)
1685 CASE_MATHFN (BUILT_IN_EXPM1)
1686 CASE_MATHFN (BUILT_IN_FABS)
1687 CASE_MATHFN (BUILT_IN_FDIM)
1688 CASE_MATHFN (BUILT_IN_FLOOR)
1689 CASE_MATHFN (BUILT_IN_FMA)
1690 CASE_MATHFN (BUILT_IN_FMAX)
1691 CASE_MATHFN (BUILT_IN_FMIN)
1692 CASE_MATHFN (BUILT_IN_FMOD)
1693 CASE_MATHFN (BUILT_IN_FREXP)
1694 CASE_MATHFN (BUILT_IN_GAMMA)
1695 CASE_MATHFN_REENT (BUILT_IN_GAMMA) /* GAMMA_R */
1696 CASE_MATHFN (BUILT_IN_HUGE_VAL)
1697 CASE_MATHFN (BUILT_IN_HYPOT)
1698 CASE_MATHFN (BUILT_IN_ILOGB)
1699 CASE_MATHFN (BUILT_IN_INF)
1700 CASE_MATHFN (BUILT_IN_ISINF)
1701 CASE_MATHFN (BUILT_IN_J0)
1702 CASE_MATHFN (BUILT_IN_J1)
1703 CASE_MATHFN (BUILT_IN_JN)
1704 CASE_MATHFN (BUILT_IN_LCEIL)
1705 CASE_MATHFN (BUILT_IN_LDEXP)
1706 CASE_MATHFN (BUILT_IN_LFLOOR)
1707 CASE_MATHFN (BUILT_IN_LGAMMA)
1708 CASE_MATHFN_REENT (BUILT_IN_LGAMMA) /* LGAMMA_R */
1709 CASE_MATHFN (BUILT_IN_LLCEIL)
1710 CASE_MATHFN (BUILT_IN_LLFLOOR)
1711 CASE_MATHFN (BUILT_IN_LLRINT)
1712 CASE_MATHFN (BUILT_IN_LLROUND)
1713 CASE_MATHFN (BUILT_IN_LOG)
1714 CASE_MATHFN (BUILT_IN_LOG10)
1715 CASE_MATHFN (BUILT_IN_LOG1P)
1716 CASE_MATHFN (BUILT_IN_LOG2)
1717 CASE_MATHFN (BUILT_IN_LOGB)
1718 CASE_MATHFN (BUILT_IN_LRINT)
1719 CASE_MATHFN (BUILT_IN_LROUND)
1720 CASE_MATHFN (BUILT_IN_MODF)
1721 CASE_MATHFN (BUILT_IN_NAN)
1722 CASE_MATHFN (BUILT_IN_NANS)
1723 CASE_MATHFN (BUILT_IN_NEARBYINT)
1724 CASE_MATHFN (BUILT_IN_NEXTAFTER)
1725 CASE_MATHFN (BUILT_IN_NEXTTOWARD)
1726 CASE_MATHFN (BUILT_IN_POW)
1727 CASE_MATHFN (BUILT_IN_POWI)
1728 CASE_MATHFN (BUILT_IN_POW10)
1729 CASE_MATHFN (BUILT_IN_REMAINDER)
1730 CASE_MATHFN (BUILT_IN_REMQUO)
1731 CASE_MATHFN (BUILT_IN_RINT)
1732 CASE_MATHFN (BUILT_IN_ROUND)
1733 CASE_MATHFN (BUILT_IN_SCALB)
1734 CASE_MATHFN (BUILT_IN_SCALBLN)
1735 CASE_MATHFN (BUILT_IN_SCALBN)
1736 CASE_MATHFN (BUILT_IN_SIGNIFICAND)
1737 CASE_MATHFN (BUILT_IN_SIN)
1738 CASE_MATHFN (BUILT_IN_SINCOS)
1739 CASE_MATHFN (BUILT_IN_SINH)
1740 CASE_MATHFN (BUILT_IN_SQRT)
1741 CASE_MATHFN (BUILT_IN_TAN)
1742 CASE_MATHFN (BUILT_IN_TANH)
1743 CASE_MATHFN (BUILT_IN_TGAMMA)
1744 CASE_MATHFN (BUILT_IN_TRUNC)
1745 CASE_MATHFN (BUILT_IN_Y0)
1746 CASE_MATHFN (BUILT_IN_Y1)
1747 CASE_MATHFN (BUILT_IN_YN)
1749 default:
1750 return NULL_TREE;
1753 if (TYPE_MAIN_VARIANT (type) == double_type_node)
1754 return implicit_built_in_decls[fcode];
1755 else if (TYPE_MAIN_VARIANT (type) == float_type_node)
1756 return implicit_built_in_decls[fcodef];
1757 else if (TYPE_MAIN_VARIANT (type) == long_double_type_node)
1758 return implicit_built_in_decls[fcodel];
1759 else
1760 return NULL_TREE;
1763 /* If errno must be maintained, expand the RTL to check if the result,
1764 TARGET, of a built-in function call, EXP, is NaN, and if so set
1765 errno to EDOM. */
1767 static void
1768 expand_errno_check (tree exp, rtx target)
1770 rtx lab = gen_label_rtx ();
1772 /* Test the result; if it is NaN, set errno=EDOM because
1773 the argument was not in the domain. */
1774 emit_cmp_and_jump_insns (target, target, EQ, 0, GET_MODE (target),
1775 0, lab);
1777 #ifdef TARGET_EDOM
1778 /* If this built-in doesn't throw an exception, set errno directly. */
1779 if (TREE_NOTHROW (TREE_OPERAND (CALL_EXPR_FN (exp), 0)))
1781 #ifdef GEN_ERRNO_RTX
1782 rtx errno_rtx = GEN_ERRNO_RTX;
1783 #else
1784 rtx errno_rtx
1785 = gen_rtx_MEM (word_mode, gen_rtx_SYMBOL_REF (Pmode, "errno"));
1786 #endif
1787 emit_move_insn (errno_rtx, GEN_INT (TARGET_EDOM));
1788 emit_label (lab);
1789 return;
1791 #endif
1793 /* We can't set errno=EDOM directly; let the library call do it.
1794 Pop the arguments right away in case the call gets deleted. */
1795 NO_DEFER_POP;
1796 expand_call (exp, target, 0);
1797 OK_DEFER_POP;
1798 emit_label (lab);
1801 /* Expand a call to one of the builtin math functions (sqrt, exp, or log).
1802 Return NULL_RTX if a normal call should be emitted rather than expanding
1803 the function in-line. EXP is the expression that is a call to the builtin
1804 function; if convenient, the result should be placed in TARGET.
1805 SUBTARGET may be used as the target for computing one of EXP's operands. */
1807 static rtx
1808 expand_builtin_mathfn (tree exp, rtx target, rtx subtarget)
1810 optab builtin_optab;
1811 rtx op0, insns, before_call;
1812 tree fndecl = get_callee_fndecl (exp);
1813 enum machine_mode mode;
1814 bool errno_set = false;
1815 tree arg;
1817 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
1818 return NULL_RTX;
1820 arg = CALL_EXPR_ARG (exp, 0);
1822 switch (DECL_FUNCTION_CODE (fndecl))
1824 CASE_FLT_FN (BUILT_IN_SQRT):
1825 errno_set = ! tree_expr_nonnegative_p (arg);
1826 builtin_optab = sqrt_optab;
1827 break;
1828 CASE_FLT_FN (BUILT_IN_EXP):
1829 errno_set = true; builtin_optab = exp_optab; break;
1830 CASE_FLT_FN (BUILT_IN_EXP10):
1831 CASE_FLT_FN (BUILT_IN_POW10):
1832 errno_set = true; builtin_optab = exp10_optab; break;
1833 CASE_FLT_FN (BUILT_IN_EXP2):
1834 errno_set = true; builtin_optab = exp2_optab; break;
1835 CASE_FLT_FN (BUILT_IN_EXPM1):
1836 errno_set = true; builtin_optab = expm1_optab; break;
1837 CASE_FLT_FN (BUILT_IN_LOGB):
1838 errno_set = true; builtin_optab = logb_optab; break;
1839 CASE_FLT_FN (BUILT_IN_LOG):
1840 errno_set = true; builtin_optab = log_optab; break;
1841 CASE_FLT_FN (BUILT_IN_LOG10):
1842 errno_set = true; builtin_optab = log10_optab; break;
1843 CASE_FLT_FN (BUILT_IN_LOG2):
1844 errno_set = true; builtin_optab = log2_optab; break;
1845 CASE_FLT_FN (BUILT_IN_LOG1P):
1846 errno_set = true; builtin_optab = log1p_optab; break;
1847 CASE_FLT_FN (BUILT_IN_ASIN):
1848 builtin_optab = asin_optab; break;
1849 CASE_FLT_FN (BUILT_IN_ACOS):
1850 builtin_optab = acos_optab; break;
1851 CASE_FLT_FN (BUILT_IN_TAN):
1852 builtin_optab = tan_optab; break;
1853 CASE_FLT_FN (BUILT_IN_ATAN):
1854 builtin_optab = atan_optab; break;
1855 CASE_FLT_FN (BUILT_IN_FLOOR):
1856 builtin_optab = floor_optab; break;
1857 CASE_FLT_FN (BUILT_IN_CEIL):
1858 builtin_optab = ceil_optab; break;
1859 CASE_FLT_FN (BUILT_IN_TRUNC):
1860 builtin_optab = btrunc_optab; break;
1861 CASE_FLT_FN (BUILT_IN_ROUND):
1862 builtin_optab = round_optab; break;
1863 CASE_FLT_FN (BUILT_IN_NEARBYINT):
1864 builtin_optab = nearbyint_optab;
1865 if (flag_trapping_math)
1866 break;
1867 /* Else fallthrough and expand as rint. */
1868 CASE_FLT_FN (BUILT_IN_RINT):
1869 builtin_optab = rint_optab; break;
1870 default:
1871 gcc_unreachable ();
1874 /* Make a suitable register to place result in. */
1875 mode = TYPE_MODE (TREE_TYPE (exp));
1877 if (! flag_errno_math || ! HONOR_NANS (mode))
1878 errno_set = false;
1880 /* Before working hard, check whether the instruction is available. */
1881 if (optab_handler (builtin_optab, mode)->insn_code != CODE_FOR_nothing)
1883 target = gen_reg_rtx (mode);
1885 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
1886 need to expand the argument again. This way, we will not perform
1887 side-effects more the once. */
1888 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
1890 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
1892 start_sequence ();
1894 /* Compute into TARGET.
1895 Set TARGET to wherever the result comes back. */
1896 target = expand_unop (mode, builtin_optab, op0, target, 0);
1898 if (target != 0)
1900 if (errno_set)
1901 expand_errno_check (exp, target);
1903 /* Output the entire sequence. */
1904 insns = get_insns ();
1905 end_sequence ();
1906 emit_insn (insns);
1907 return target;
1910 /* If we were unable to expand via the builtin, stop the sequence
1911 (without outputting the insns) and call to the library function
1912 with the stabilized argument list. */
1913 end_sequence ();
1916 before_call = get_last_insn ();
1918 target = expand_call (exp, target, target == const0_rtx);
1920 /* If this is a sqrt operation and we don't care about errno, try to
1921 attach a REG_EQUAL note with a SQRT rtx to the emitted libcall.
1922 This allows the semantics of the libcall to be visible to the RTL
1923 optimizers. */
1924 if (builtin_optab == sqrt_optab && !errno_set)
1926 /* Search backwards through the insns emitted by expand_call looking
1927 for the instruction with the REG_RETVAL note. */
1928 rtx last = get_last_insn ();
1929 while (last != before_call)
1931 if (find_reg_note (last, REG_RETVAL, NULL))
1933 rtx note = find_reg_note (last, REG_EQUAL, NULL);
1934 /* Check that the REQ_EQUAL note is an EXPR_LIST with
1935 two elements, i.e. symbol_ref(sqrt) and the operand. */
1936 if (note
1937 && GET_CODE (note) == EXPR_LIST
1938 && GET_CODE (XEXP (note, 0)) == EXPR_LIST
1939 && XEXP (XEXP (note, 0), 1) != NULL_RTX
1940 && XEXP (XEXP (XEXP (note, 0), 1), 1) == NULL_RTX)
1942 rtx operand = XEXP (XEXP (XEXP (note, 0), 1), 0);
1943 /* Check operand is a register with expected mode. */
1944 if (operand
1945 && REG_P (operand)
1946 && GET_MODE (operand) == mode)
1948 /* Replace the REG_EQUAL note with a SQRT rtx. */
1949 rtx equiv = gen_rtx_SQRT (mode, operand);
1950 set_unique_reg_note (last, REG_EQUAL, equiv);
1953 break;
1955 last = PREV_INSN (last);
1959 return target;
1962 /* Expand a call to the builtin binary math functions (pow and atan2).
1963 Return NULL_RTX if a normal call should be emitted rather than expanding the
1964 function in-line. EXP is the expression that is a call to the builtin
1965 function; if convenient, the result should be placed in TARGET.
1966 SUBTARGET may be used as the target for computing one of EXP's
1967 operands. */
1969 static rtx
1970 expand_builtin_mathfn_2 (tree exp, rtx target, rtx subtarget)
1972 optab builtin_optab;
1973 rtx op0, op1, insns;
1974 int op1_type = REAL_TYPE;
1975 tree fndecl = get_callee_fndecl (exp);
1976 tree arg0, arg1;
1977 enum machine_mode mode;
1978 bool errno_set = true;
1980 switch (DECL_FUNCTION_CODE (fndecl))
1982 CASE_FLT_FN (BUILT_IN_SCALBN):
1983 CASE_FLT_FN (BUILT_IN_SCALBLN):
1984 CASE_FLT_FN (BUILT_IN_LDEXP):
1985 op1_type = INTEGER_TYPE;
1986 default:
1987 break;
1990 if (!validate_arglist (exp, REAL_TYPE, op1_type, VOID_TYPE))
1991 return NULL_RTX;
1993 arg0 = CALL_EXPR_ARG (exp, 0);
1994 arg1 = CALL_EXPR_ARG (exp, 1);
1996 switch (DECL_FUNCTION_CODE (fndecl))
1998 CASE_FLT_FN (BUILT_IN_POW):
1999 builtin_optab = pow_optab; break;
2000 CASE_FLT_FN (BUILT_IN_ATAN2):
2001 builtin_optab = atan2_optab; break;
2002 CASE_FLT_FN (BUILT_IN_SCALB):
2003 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (exp)))->b != 2)
2004 return 0;
2005 builtin_optab = scalb_optab; break;
2006 CASE_FLT_FN (BUILT_IN_SCALBN):
2007 CASE_FLT_FN (BUILT_IN_SCALBLN):
2008 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (exp)))->b != 2)
2009 return 0;
2010 /* Fall through... */
2011 CASE_FLT_FN (BUILT_IN_LDEXP):
2012 builtin_optab = ldexp_optab; break;
2013 CASE_FLT_FN (BUILT_IN_FMOD):
2014 builtin_optab = fmod_optab; break;
2015 CASE_FLT_FN (BUILT_IN_REMAINDER):
2016 CASE_FLT_FN (BUILT_IN_DREM):
2017 builtin_optab = remainder_optab; break;
2018 default:
2019 gcc_unreachable ();
2022 /* Make a suitable register to place result in. */
2023 mode = TYPE_MODE (TREE_TYPE (exp));
2025 /* Before working hard, check whether the instruction is available. */
2026 if (optab_handler (builtin_optab, mode)->insn_code == CODE_FOR_nothing)
2027 return NULL_RTX;
2029 target = gen_reg_rtx (mode);
2031 if (! flag_errno_math || ! HONOR_NANS (mode))
2032 errno_set = false;
2034 /* Always stabilize the argument list. */
2035 CALL_EXPR_ARG (exp, 0) = arg0 = builtin_save_expr (arg0);
2036 CALL_EXPR_ARG (exp, 1) = arg1 = builtin_save_expr (arg1);
2038 op0 = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
2039 op1 = expand_normal (arg1);
2041 start_sequence ();
2043 /* Compute into TARGET.
2044 Set TARGET to wherever the result comes back. */
2045 target = expand_binop (mode, builtin_optab, op0, op1,
2046 target, 0, OPTAB_DIRECT);
2048 /* If we were unable to expand via the builtin, stop the sequence
2049 (without outputting the insns) and call to the library function
2050 with the stabilized argument list. */
2051 if (target == 0)
2053 end_sequence ();
2054 return expand_call (exp, target, target == const0_rtx);
2057 if (errno_set)
2058 expand_errno_check (exp, target);
2060 /* Output the entire sequence. */
2061 insns = get_insns ();
2062 end_sequence ();
2063 emit_insn (insns);
2065 return target;
2068 /* Expand a call to the builtin sin and cos math functions.
2069 Return NULL_RTX if a normal call should be emitted rather than expanding the
2070 function in-line. EXP is the expression that is a call to the builtin
2071 function; if convenient, the result should be placed in TARGET.
2072 SUBTARGET may be used as the target for computing one of EXP's
2073 operands. */
2075 static rtx
2076 expand_builtin_mathfn_3 (tree exp, rtx target, rtx subtarget)
2078 optab builtin_optab;
2079 rtx op0, insns;
2080 tree fndecl = get_callee_fndecl (exp);
2081 enum machine_mode mode;
2082 tree arg;
2084 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2085 return NULL_RTX;
2087 arg = CALL_EXPR_ARG (exp, 0);
2089 switch (DECL_FUNCTION_CODE (fndecl))
2091 CASE_FLT_FN (BUILT_IN_SIN):
2092 CASE_FLT_FN (BUILT_IN_COS):
2093 builtin_optab = sincos_optab; break;
2094 default:
2095 gcc_unreachable ();
2098 /* Make a suitable register to place result in. */
2099 mode = TYPE_MODE (TREE_TYPE (exp));
2101 /* Check if sincos insn is available, otherwise fallback
2102 to sin or cos insn. */
2103 if (optab_handler (builtin_optab, mode)->insn_code == CODE_FOR_nothing)
2104 switch (DECL_FUNCTION_CODE (fndecl))
2106 CASE_FLT_FN (BUILT_IN_SIN):
2107 builtin_optab = sin_optab; break;
2108 CASE_FLT_FN (BUILT_IN_COS):
2109 builtin_optab = cos_optab; break;
2110 default:
2111 gcc_unreachable ();
2114 /* Before working hard, check whether the instruction is available. */
2115 if (optab_handler (builtin_optab, mode)->insn_code != CODE_FOR_nothing)
2117 target = gen_reg_rtx (mode);
2119 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2120 need to expand the argument again. This way, we will not perform
2121 side-effects more the once. */
2122 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2124 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2126 start_sequence ();
2128 /* Compute into TARGET.
2129 Set TARGET to wherever the result comes back. */
2130 if (builtin_optab == sincos_optab)
2132 int result;
2134 switch (DECL_FUNCTION_CODE (fndecl))
2136 CASE_FLT_FN (BUILT_IN_SIN):
2137 result = expand_twoval_unop (builtin_optab, op0, 0, target, 0);
2138 break;
2139 CASE_FLT_FN (BUILT_IN_COS):
2140 result = expand_twoval_unop (builtin_optab, op0, target, 0, 0);
2141 break;
2142 default:
2143 gcc_unreachable ();
2145 gcc_assert (result);
2147 else
2149 target = expand_unop (mode, builtin_optab, op0, target, 0);
2152 if (target != 0)
2154 /* Output the entire sequence. */
2155 insns = get_insns ();
2156 end_sequence ();
2157 emit_insn (insns);
2158 return target;
2161 /* If we were unable to expand via the builtin, stop the sequence
2162 (without outputting the insns) and call to the library function
2163 with the stabilized argument list. */
2164 end_sequence ();
2167 target = expand_call (exp, target, target == const0_rtx);
2169 return target;
2172 /* Expand a call to one of the builtin math functions that operate on
2173 floating point argument and output an integer result (ilogb, isinf,
2174 isnan, etc).
2175 Return 0 if a normal call should be emitted rather than expanding the
2176 function in-line. EXP is the expression that is a call to the builtin
2177 function; if convenient, the result should be placed in TARGET.
2178 SUBTARGET may be used as the target for computing one of EXP's operands. */
2180 static rtx
2181 expand_builtin_interclass_mathfn (tree exp, rtx target, rtx subtarget)
2183 optab builtin_optab = 0;
2184 enum insn_code icode = CODE_FOR_nothing;
2185 rtx op0;
2186 tree fndecl = get_callee_fndecl (exp);
2187 enum machine_mode mode;
2188 bool errno_set = false;
2189 tree arg;
2191 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2192 return NULL_RTX;
2194 arg = CALL_EXPR_ARG (exp, 0);
2196 switch (DECL_FUNCTION_CODE (fndecl))
2198 CASE_FLT_FN (BUILT_IN_ILOGB):
2199 errno_set = true; builtin_optab = ilogb_optab; break;
2200 CASE_FLT_FN (BUILT_IN_ISINF):
2201 builtin_optab = isinf_optab; break;
2202 case BUILT_IN_ISNORMAL:
2203 case BUILT_IN_ISFINITE:
2204 CASE_FLT_FN (BUILT_IN_FINITE):
2205 /* These builtins have no optabs (yet). */
2206 break;
2207 default:
2208 gcc_unreachable ();
2211 /* There's no easy way to detect the case we need to set EDOM. */
2212 if (flag_errno_math && errno_set)
2213 return NULL_RTX;
2215 /* Optab mode depends on the mode of the input argument. */
2216 mode = TYPE_MODE (TREE_TYPE (arg));
2218 if (builtin_optab)
2219 icode = optab_handler (builtin_optab, mode)->insn_code;
2221 /* Before working hard, check whether the instruction is available. */
2222 if (icode != CODE_FOR_nothing)
2224 /* Make a suitable register to place result in. */
2225 if (!target
2226 || GET_MODE (target) != TYPE_MODE (TREE_TYPE (exp)))
2227 target = gen_reg_rtx (TYPE_MODE (TREE_TYPE (exp)));
2229 gcc_assert (insn_data[icode].operand[0].predicate
2230 (target, GET_MODE (target)));
2232 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2233 need to expand the argument again. This way, we will not perform
2234 side-effects more the once. */
2235 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2237 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2239 if (mode != GET_MODE (op0))
2240 op0 = convert_to_mode (mode, op0, 0);
2242 /* Compute into TARGET.
2243 Set TARGET to wherever the result comes back. */
2244 emit_unop_insn (icode, target, op0, UNKNOWN);
2245 return target;
2248 /* If there is no optab, try generic code. */
2249 switch (DECL_FUNCTION_CODE (fndecl))
2251 tree result;
2253 CASE_FLT_FN (BUILT_IN_ISINF):
2255 /* isinf(x) -> isgreater(fabs(x),DBL_MAX). */
2256 tree const isgr_fn = built_in_decls[BUILT_IN_ISGREATER];
2257 tree const type = TREE_TYPE (arg);
2258 REAL_VALUE_TYPE r;
2259 char buf[128];
2261 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
2262 real_from_string (&r, buf);
2263 result = build_call_expr (isgr_fn, 2,
2264 fold_build1 (ABS_EXPR, type, arg),
2265 build_real (type, r));
2266 return expand_expr (result, target, VOIDmode, EXPAND_NORMAL);
2268 CASE_FLT_FN (BUILT_IN_FINITE):
2269 case BUILT_IN_ISFINITE:
2271 /* isfinite(x) -> islessequal(fabs(x),DBL_MAX). */
2272 tree const isle_fn = built_in_decls[BUILT_IN_ISLESSEQUAL];
2273 tree const type = TREE_TYPE (arg);
2274 REAL_VALUE_TYPE r;
2275 char buf[128];
2277 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
2278 real_from_string (&r, buf);
2279 result = build_call_expr (isle_fn, 2,
2280 fold_build1 (ABS_EXPR, type, arg),
2281 build_real (type, r));
2282 return expand_expr (result, target, VOIDmode, EXPAND_NORMAL);
2284 case BUILT_IN_ISNORMAL:
2286 /* isnormal(x) -> isgreaterequal(fabs(x),DBL_MIN) &
2287 islessequal(fabs(x),DBL_MAX). */
2288 tree const isle_fn = built_in_decls[BUILT_IN_ISLESSEQUAL];
2289 tree const isge_fn = built_in_decls[BUILT_IN_ISGREATEREQUAL];
2290 tree const type = TREE_TYPE (arg);
2291 REAL_VALUE_TYPE rmax, rmin;
2292 char buf[128];
2294 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
2295 real_from_string (&rmax, buf);
2296 sprintf (buf, "0x1p%d", REAL_MODE_FORMAT (mode)->emin - 1);
2297 real_from_string (&rmin, buf);
2298 arg = builtin_save_expr (fold_build1 (ABS_EXPR, type, arg));
2299 result = build_call_expr (isle_fn, 2, arg,
2300 build_real (type, rmax));
2301 result = fold_build2 (BIT_AND_EXPR, integer_type_node, result,
2302 build_call_expr (isge_fn, 2, arg,
2303 build_real (type, rmin)));
2304 return expand_expr (result, target, VOIDmode, EXPAND_NORMAL);
2306 default:
2307 break;
2310 target = expand_call (exp, target, target == const0_rtx);
2312 return target;
2315 /* Expand a call to the builtin sincos math function.
2316 Return NULL_RTX if a normal call should be emitted rather than expanding the
2317 function in-line. EXP is the expression that is a call to the builtin
2318 function. */
2320 static rtx
2321 expand_builtin_sincos (tree exp)
2323 rtx op0, op1, op2, target1, target2;
2324 enum machine_mode mode;
2325 tree arg, sinp, cosp;
2326 int result;
2328 if (!validate_arglist (exp, REAL_TYPE,
2329 POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
2330 return NULL_RTX;
2332 arg = CALL_EXPR_ARG (exp, 0);
2333 sinp = CALL_EXPR_ARG (exp, 1);
2334 cosp = CALL_EXPR_ARG (exp, 2);
2336 /* Make a suitable register to place result in. */
2337 mode = TYPE_MODE (TREE_TYPE (arg));
2339 /* Check if sincos insn is available, otherwise emit the call. */
2340 if (optab_handler (sincos_optab, mode)->insn_code == CODE_FOR_nothing)
2341 return NULL_RTX;
2343 target1 = gen_reg_rtx (mode);
2344 target2 = gen_reg_rtx (mode);
2346 op0 = expand_normal (arg);
2347 op1 = expand_normal (build_fold_indirect_ref (sinp));
2348 op2 = expand_normal (build_fold_indirect_ref (cosp));
2350 /* Compute into target1 and target2.
2351 Set TARGET to wherever the result comes back. */
2352 result = expand_twoval_unop (sincos_optab, op0, target2, target1, 0);
2353 gcc_assert (result);
2355 /* Move target1 and target2 to the memory locations indicated
2356 by op1 and op2. */
2357 emit_move_insn (op1, target1);
2358 emit_move_insn (op2, target2);
2360 return const0_rtx;
2363 /* Expand a call to the internal cexpi builtin to the sincos math function.
2364 EXP is the expression that is a call to the builtin function; if convenient,
2365 the result should be placed in TARGET. SUBTARGET may be used as the target
2366 for computing one of EXP's operands. */
2368 static rtx
2369 expand_builtin_cexpi (tree exp, rtx target, rtx subtarget)
2371 tree fndecl = get_callee_fndecl (exp);
2372 tree arg, type;
2373 enum machine_mode mode;
2374 rtx op0, op1, op2;
2376 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2377 return NULL_RTX;
2379 arg = CALL_EXPR_ARG (exp, 0);
2380 type = TREE_TYPE (arg);
2381 mode = TYPE_MODE (TREE_TYPE (arg));
2383 /* Try expanding via a sincos optab, fall back to emitting a libcall
2384 to sincos or cexp. We are sure we have sincos or cexp because cexpi
2385 is only generated from sincos, cexp or if we have either of them. */
2386 if (optab_handler (sincos_optab, mode)->insn_code != CODE_FOR_nothing)
2388 op1 = gen_reg_rtx (mode);
2389 op2 = gen_reg_rtx (mode);
2391 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2393 /* Compute into op1 and op2. */
2394 expand_twoval_unop (sincos_optab, op0, op2, op1, 0);
2396 else if (TARGET_HAS_SINCOS)
2398 tree call, fn = NULL_TREE;
2399 tree top1, top2;
2400 rtx op1a, op2a;
2402 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2403 fn = built_in_decls[BUILT_IN_SINCOSF];
2404 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2405 fn = built_in_decls[BUILT_IN_SINCOS];
2406 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2407 fn = built_in_decls[BUILT_IN_SINCOSL];
2408 else
2409 gcc_unreachable ();
2411 op1 = assign_temp (TREE_TYPE (arg), 0, 1, 1);
2412 op2 = assign_temp (TREE_TYPE (arg), 0, 1, 1);
2413 op1a = copy_to_mode_reg (Pmode, XEXP (op1, 0));
2414 op2a = copy_to_mode_reg (Pmode, XEXP (op2, 0));
2415 top1 = make_tree (build_pointer_type (TREE_TYPE (arg)), op1a);
2416 top2 = make_tree (build_pointer_type (TREE_TYPE (arg)), op2a);
2418 /* Make sure not to fold the sincos call again. */
2419 call = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
2420 expand_normal (build_call_nary (TREE_TYPE (TREE_TYPE (fn)),
2421 call, 3, arg, top1, top2));
2423 else
2425 tree call, fn = NULL_TREE, narg;
2426 tree ctype = build_complex_type (type);
2428 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2429 fn = built_in_decls[BUILT_IN_CEXPF];
2430 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2431 fn = built_in_decls[BUILT_IN_CEXP];
2432 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2433 fn = built_in_decls[BUILT_IN_CEXPL];
2434 else
2435 gcc_unreachable ();
2437 /* If we don't have a decl for cexp create one. This is the
2438 friendliest fallback if the user calls __builtin_cexpi
2439 without full target C99 function support. */
2440 if (fn == NULL_TREE)
2442 tree fntype;
2443 const char *name = NULL;
2445 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2446 name = "cexpf";
2447 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2448 name = "cexp";
2449 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2450 name = "cexpl";
2452 fntype = build_function_type_list (ctype, ctype, NULL_TREE);
2453 fn = build_fn_decl (name, fntype);
2456 narg = fold_build2 (COMPLEX_EXPR, ctype,
2457 build_real (type, dconst0), arg);
2459 /* Make sure not to fold the cexp call again. */
2460 call = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
2461 return expand_expr (build_call_nary (ctype, call, 1, narg),
2462 target, VOIDmode, EXPAND_NORMAL);
2465 /* Now build the proper return type. */
2466 return expand_expr (build2 (COMPLEX_EXPR, build_complex_type (type),
2467 make_tree (TREE_TYPE (arg), op2),
2468 make_tree (TREE_TYPE (arg), op1)),
2469 target, VOIDmode, EXPAND_NORMAL);
2472 /* Expand a call to one of the builtin rounding functions gcc defines
2473 as an extension (lfloor and lceil). As these are gcc extensions we
2474 do not need to worry about setting errno to EDOM.
2475 If expanding via optab fails, lower expression to (int)(floor(x)).
2476 EXP is the expression that is a call to the builtin function;
2477 if convenient, the result should be placed in TARGET. SUBTARGET may
2478 be used as the target for computing one of EXP's operands. */
2480 static rtx
2481 expand_builtin_int_roundingfn (tree exp, rtx target, rtx subtarget)
2483 convert_optab builtin_optab;
2484 rtx op0, insns, tmp;
2485 tree fndecl = get_callee_fndecl (exp);
2486 enum built_in_function fallback_fn;
2487 tree fallback_fndecl;
2488 enum machine_mode mode;
2489 tree arg;
2491 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2492 gcc_unreachable ();
2494 arg = CALL_EXPR_ARG (exp, 0);
2496 switch (DECL_FUNCTION_CODE (fndecl))
2498 CASE_FLT_FN (BUILT_IN_LCEIL):
2499 CASE_FLT_FN (BUILT_IN_LLCEIL):
2500 builtin_optab = lceil_optab;
2501 fallback_fn = BUILT_IN_CEIL;
2502 break;
2504 CASE_FLT_FN (BUILT_IN_LFLOOR):
2505 CASE_FLT_FN (BUILT_IN_LLFLOOR):
2506 builtin_optab = lfloor_optab;
2507 fallback_fn = BUILT_IN_FLOOR;
2508 break;
2510 default:
2511 gcc_unreachable ();
2514 /* Make a suitable register to place result in. */
2515 mode = TYPE_MODE (TREE_TYPE (exp));
2517 target = gen_reg_rtx (mode);
2519 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2520 need to expand the argument again. This way, we will not perform
2521 side-effects more the once. */
2522 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2524 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2526 start_sequence ();
2528 /* Compute into TARGET. */
2529 if (expand_sfix_optab (target, op0, builtin_optab))
2531 /* Output the entire sequence. */
2532 insns = get_insns ();
2533 end_sequence ();
2534 emit_insn (insns);
2535 return target;
2538 /* If we were unable to expand via the builtin, stop the sequence
2539 (without outputting the insns). */
2540 end_sequence ();
2542 /* Fall back to floating point rounding optab. */
2543 fallback_fndecl = mathfn_built_in (TREE_TYPE (arg), fallback_fn);
2545 /* For non-C99 targets we may end up without a fallback fndecl here
2546 if the user called __builtin_lfloor directly. In this case emit
2547 a call to the floor/ceil variants nevertheless. This should result
2548 in the best user experience for not full C99 targets. */
2549 if (fallback_fndecl == NULL_TREE)
2551 tree fntype;
2552 const char *name = NULL;
2554 switch (DECL_FUNCTION_CODE (fndecl))
2556 case BUILT_IN_LCEIL:
2557 case BUILT_IN_LLCEIL:
2558 name = "ceil";
2559 break;
2560 case BUILT_IN_LCEILF:
2561 case BUILT_IN_LLCEILF:
2562 name = "ceilf";
2563 break;
2564 case BUILT_IN_LCEILL:
2565 case BUILT_IN_LLCEILL:
2566 name = "ceill";
2567 break;
2568 case BUILT_IN_LFLOOR:
2569 case BUILT_IN_LLFLOOR:
2570 name = "floor";
2571 break;
2572 case BUILT_IN_LFLOORF:
2573 case BUILT_IN_LLFLOORF:
2574 name = "floorf";
2575 break;
2576 case BUILT_IN_LFLOORL:
2577 case BUILT_IN_LLFLOORL:
2578 name = "floorl";
2579 break;
2580 default:
2581 gcc_unreachable ();
2584 fntype = build_function_type_list (TREE_TYPE (arg),
2585 TREE_TYPE (arg), NULL_TREE);
2586 fallback_fndecl = build_fn_decl (name, fntype);
2589 exp = build_call_expr (fallback_fndecl, 1, arg);
2591 tmp = expand_normal (exp);
2593 /* Truncate the result of floating point optab to integer
2594 via expand_fix (). */
2595 target = gen_reg_rtx (mode);
2596 expand_fix (target, tmp, 0);
2598 return target;
2601 /* Expand a call to one of the builtin math functions doing integer
2602 conversion (lrint).
2603 Return 0 if a normal call should be emitted rather than expanding the
2604 function in-line. EXP is the expression that is a call to the builtin
2605 function; if convenient, the result should be placed in TARGET.
2606 SUBTARGET may be used as the target for computing one of EXP's operands. */
2608 static rtx
2609 expand_builtin_int_roundingfn_2 (tree exp, rtx target, rtx subtarget)
2611 convert_optab builtin_optab;
2612 rtx op0, insns;
2613 tree fndecl = get_callee_fndecl (exp);
2614 tree arg;
2615 enum machine_mode mode;
2617 /* There's no easy way to detect the case we need to set EDOM. */
2618 if (flag_errno_math)
2619 return NULL_RTX;
2621 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2622 gcc_unreachable ();
2624 arg = CALL_EXPR_ARG (exp, 0);
2626 switch (DECL_FUNCTION_CODE (fndecl))
2628 CASE_FLT_FN (BUILT_IN_LRINT):
2629 CASE_FLT_FN (BUILT_IN_LLRINT):
2630 builtin_optab = lrint_optab; break;
2631 CASE_FLT_FN (BUILT_IN_LROUND):
2632 CASE_FLT_FN (BUILT_IN_LLROUND):
2633 builtin_optab = lround_optab; break;
2634 default:
2635 gcc_unreachable ();
2638 /* Make a suitable register to place result in. */
2639 mode = TYPE_MODE (TREE_TYPE (exp));
2641 target = gen_reg_rtx (mode);
2643 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2644 need to expand the argument again. This way, we will not perform
2645 side-effects more the once. */
2646 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2648 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2650 start_sequence ();
2652 if (expand_sfix_optab (target, op0, builtin_optab))
2654 /* Output the entire sequence. */
2655 insns = get_insns ();
2656 end_sequence ();
2657 emit_insn (insns);
2658 return target;
2661 /* If we were unable to expand via the builtin, stop the sequence
2662 (without outputting the insns) and call to the library function
2663 with the stabilized argument list. */
2664 end_sequence ();
2666 target = expand_call (exp, target, target == const0_rtx);
2668 return target;
2671 /* To evaluate powi(x,n), the floating point value x raised to the
2672 constant integer exponent n, we use a hybrid algorithm that
2673 combines the "window method" with look-up tables. For an
2674 introduction to exponentiation algorithms and "addition chains",
2675 see section 4.6.3, "Evaluation of Powers" of Donald E. Knuth,
2676 "Seminumerical Algorithms", Vol. 2, "The Art of Computer Programming",
2677 3rd Edition, 1998, and Daniel M. Gordon, "A Survey of Fast Exponentiation
2678 Methods", Journal of Algorithms, Vol. 27, pp. 129-146, 1998. */
2680 /* Provide a default value for POWI_MAX_MULTS, the maximum number of
2681 multiplications to inline before calling the system library's pow
2682 function. powi(x,n) requires at worst 2*bits(n)-2 multiplications,
2683 so this default never requires calling pow, powf or powl. */
2685 #ifndef POWI_MAX_MULTS
2686 #define POWI_MAX_MULTS (2*HOST_BITS_PER_WIDE_INT-2)
2687 #endif
2689 /* The size of the "optimal power tree" lookup table. All
2690 exponents less than this value are simply looked up in the
2691 powi_table below. This threshold is also used to size the
2692 cache of pseudo registers that hold intermediate results. */
2693 #define POWI_TABLE_SIZE 256
2695 /* The size, in bits of the window, used in the "window method"
2696 exponentiation algorithm. This is equivalent to a radix of
2697 (1<<POWI_WINDOW_SIZE) in the corresponding "m-ary method". */
2698 #define POWI_WINDOW_SIZE 3
2700 /* The following table is an efficient representation of an
2701 "optimal power tree". For each value, i, the corresponding
2702 value, j, in the table states than an optimal evaluation
2703 sequence for calculating pow(x,i) can be found by evaluating
2704 pow(x,j)*pow(x,i-j). An optimal power tree for the first
2705 100 integers is given in Knuth's "Seminumerical algorithms". */
2707 static const unsigned char powi_table[POWI_TABLE_SIZE] =
2709 0, 1, 1, 2, 2, 3, 3, 4, /* 0 - 7 */
2710 4, 6, 5, 6, 6, 10, 7, 9, /* 8 - 15 */
2711 8, 16, 9, 16, 10, 12, 11, 13, /* 16 - 23 */
2712 12, 17, 13, 18, 14, 24, 15, 26, /* 24 - 31 */
2713 16, 17, 17, 19, 18, 33, 19, 26, /* 32 - 39 */
2714 20, 25, 21, 40, 22, 27, 23, 44, /* 40 - 47 */
2715 24, 32, 25, 34, 26, 29, 27, 44, /* 48 - 55 */
2716 28, 31, 29, 34, 30, 60, 31, 36, /* 56 - 63 */
2717 32, 64, 33, 34, 34, 46, 35, 37, /* 64 - 71 */
2718 36, 65, 37, 50, 38, 48, 39, 69, /* 72 - 79 */
2719 40, 49, 41, 43, 42, 51, 43, 58, /* 80 - 87 */
2720 44, 64, 45, 47, 46, 59, 47, 76, /* 88 - 95 */
2721 48, 65, 49, 66, 50, 67, 51, 66, /* 96 - 103 */
2722 52, 70, 53, 74, 54, 104, 55, 74, /* 104 - 111 */
2723 56, 64, 57, 69, 58, 78, 59, 68, /* 112 - 119 */
2724 60, 61, 61, 80, 62, 75, 63, 68, /* 120 - 127 */
2725 64, 65, 65, 128, 66, 129, 67, 90, /* 128 - 135 */
2726 68, 73, 69, 131, 70, 94, 71, 88, /* 136 - 143 */
2727 72, 128, 73, 98, 74, 132, 75, 121, /* 144 - 151 */
2728 76, 102, 77, 124, 78, 132, 79, 106, /* 152 - 159 */
2729 80, 97, 81, 160, 82, 99, 83, 134, /* 160 - 167 */
2730 84, 86, 85, 95, 86, 160, 87, 100, /* 168 - 175 */
2731 88, 113, 89, 98, 90, 107, 91, 122, /* 176 - 183 */
2732 92, 111, 93, 102, 94, 126, 95, 150, /* 184 - 191 */
2733 96, 128, 97, 130, 98, 133, 99, 195, /* 192 - 199 */
2734 100, 128, 101, 123, 102, 164, 103, 138, /* 200 - 207 */
2735 104, 145, 105, 146, 106, 109, 107, 149, /* 208 - 215 */
2736 108, 200, 109, 146, 110, 170, 111, 157, /* 216 - 223 */
2737 112, 128, 113, 130, 114, 182, 115, 132, /* 224 - 231 */
2738 116, 200, 117, 132, 118, 158, 119, 206, /* 232 - 239 */
2739 120, 240, 121, 162, 122, 147, 123, 152, /* 240 - 247 */
2740 124, 166, 125, 214, 126, 138, 127, 153, /* 248 - 255 */
2744 /* Return the number of multiplications required to calculate
2745 powi(x,n) where n is less than POWI_TABLE_SIZE. This is a
2746 subroutine of powi_cost. CACHE is an array indicating
2747 which exponents have already been calculated. */
2749 static int
2750 powi_lookup_cost (unsigned HOST_WIDE_INT n, bool *cache)
2752 /* If we've already calculated this exponent, then this evaluation
2753 doesn't require any additional multiplications. */
2754 if (cache[n])
2755 return 0;
2757 cache[n] = true;
2758 return powi_lookup_cost (n - powi_table[n], cache)
2759 + powi_lookup_cost (powi_table[n], cache) + 1;
2762 /* Return the number of multiplications required to calculate
2763 powi(x,n) for an arbitrary x, given the exponent N. This
2764 function needs to be kept in sync with expand_powi below. */
2766 static int
2767 powi_cost (HOST_WIDE_INT n)
2769 bool cache[POWI_TABLE_SIZE];
2770 unsigned HOST_WIDE_INT digit;
2771 unsigned HOST_WIDE_INT val;
2772 int result;
2774 if (n == 0)
2775 return 0;
2777 /* Ignore the reciprocal when calculating the cost. */
2778 val = (n < 0) ? -n : n;
2780 /* Initialize the exponent cache. */
2781 memset (cache, 0, POWI_TABLE_SIZE * sizeof (bool));
2782 cache[1] = true;
2784 result = 0;
2786 while (val >= POWI_TABLE_SIZE)
2788 if (val & 1)
2790 digit = val & ((1 << POWI_WINDOW_SIZE) - 1);
2791 result += powi_lookup_cost (digit, cache)
2792 + POWI_WINDOW_SIZE + 1;
2793 val >>= POWI_WINDOW_SIZE;
2795 else
2797 val >>= 1;
2798 result++;
2802 return result + powi_lookup_cost (val, cache);
2805 /* Recursive subroutine of expand_powi. This function takes the array,
2806 CACHE, of already calculated exponents and an exponent N and returns
2807 an RTX that corresponds to CACHE[1]**N, as calculated in mode MODE. */
2809 static rtx
2810 expand_powi_1 (enum machine_mode mode, unsigned HOST_WIDE_INT n, rtx *cache)
2812 unsigned HOST_WIDE_INT digit;
2813 rtx target, result;
2814 rtx op0, op1;
2816 if (n < POWI_TABLE_SIZE)
2818 if (cache[n])
2819 return cache[n];
2821 target = gen_reg_rtx (mode);
2822 cache[n] = target;
2824 op0 = expand_powi_1 (mode, n - powi_table[n], cache);
2825 op1 = expand_powi_1 (mode, powi_table[n], cache);
2827 else if (n & 1)
2829 target = gen_reg_rtx (mode);
2830 digit = n & ((1 << POWI_WINDOW_SIZE) - 1);
2831 op0 = expand_powi_1 (mode, n - digit, cache);
2832 op1 = expand_powi_1 (mode, digit, cache);
2834 else
2836 target = gen_reg_rtx (mode);
2837 op0 = expand_powi_1 (mode, n >> 1, cache);
2838 op1 = op0;
2841 result = expand_mult (mode, op0, op1, target, 0);
2842 if (result != target)
2843 emit_move_insn (target, result);
2844 return target;
2847 /* Expand the RTL to evaluate powi(x,n) in mode MODE. X is the
2848 floating point operand in mode MODE, and N is the exponent. This
2849 function needs to be kept in sync with powi_cost above. */
2851 static rtx
2852 expand_powi (rtx x, enum machine_mode mode, HOST_WIDE_INT n)
2854 unsigned HOST_WIDE_INT val;
2855 rtx cache[POWI_TABLE_SIZE];
2856 rtx result;
2858 if (n == 0)
2859 return CONST1_RTX (mode);
2861 val = (n < 0) ? -n : n;
2863 memset (cache, 0, sizeof (cache));
2864 cache[1] = x;
2866 result = expand_powi_1 (mode, (n < 0) ? -n : n, cache);
2868 /* If the original exponent was negative, reciprocate the result. */
2869 if (n < 0)
2870 result = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
2871 result, NULL_RTX, 0, OPTAB_LIB_WIDEN);
2873 return result;
2876 /* Expand a call to the pow built-in mathematical function. Return NULL_RTX if
2877 a normal call should be emitted rather than expanding the function
2878 in-line. EXP is the expression that is a call to the builtin
2879 function; if convenient, the result should be placed in TARGET. */
2881 static rtx
2882 expand_builtin_pow (tree exp, rtx target, rtx subtarget)
2884 tree arg0, arg1;
2885 tree fn, narg0;
2886 tree type = TREE_TYPE (exp);
2887 REAL_VALUE_TYPE cint, c, c2;
2888 HOST_WIDE_INT n;
2889 rtx op, op2;
2890 enum machine_mode mode = TYPE_MODE (type);
2892 if (! validate_arglist (exp, REAL_TYPE, REAL_TYPE, VOID_TYPE))
2893 return NULL_RTX;
2895 arg0 = CALL_EXPR_ARG (exp, 0);
2896 arg1 = CALL_EXPR_ARG (exp, 1);
2898 if (TREE_CODE (arg1) != REAL_CST
2899 || TREE_OVERFLOW (arg1))
2900 return expand_builtin_mathfn_2 (exp, target, subtarget);
2902 /* Handle constant exponents. */
2904 /* For integer valued exponents we can expand to an optimal multiplication
2905 sequence using expand_powi. */
2906 c = TREE_REAL_CST (arg1);
2907 n = real_to_integer (&c);
2908 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
2909 if (real_identical (&c, &cint)
2910 && ((n >= -1 && n <= 2)
2911 || (flag_unsafe_math_optimizations
2912 && !optimize_size
2913 && powi_cost (n) <= POWI_MAX_MULTS)))
2915 op = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
2916 if (n != 1)
2918 op = force_reg (mode, op);
2919 op = expand_powi (op, mode, n);
2921 return op;
2924 narg0 = builtin_save_expr (arg0);
2926 /* If the exponent is not integer valued, check if it is half of an integer.
2927 In this case we can expand to sqrt (x) * x**(n/2). */
2928 fn = mathfn_built_in (type, BUILT_IN_SQRT);
2929 if (fn != NULL_TREE)
2931 real_arithmetic (&c2, MULT_EXPR, &c, &dconst2);
2932 n = real_to_integer (&c2);
2933 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
2934 if (real_identical (&c2, &cint)
2935 && ((flag_unsafe_math_optimizations
2936 && !optimize_size
2937 && powi_cost (n/2) <= POWI_MAX_MULTS)
2938 || n == 1))
2940 tree call_expr = build_call_expr (fn, 1, narg0);
2941 op = expand_builtin (call_expr, NULL_RTX, subtarget, mode, 0);
2942 if (n != 1)
2944 op2 = expand_expr (narg0, subtarget, VOIDmode, EXPAND_NORMAL);
2945 op2 = force_reg (mode, op2);
2946 op2 = expand_powi (op2, mode, abs (n / 2));
2947 op = expand_simple_binop (mode, MULT, op, op2, NULL_RTX,
2948 0, OPTAB_LIB_WIDEN);
2949 /* If the original exponent was negative, reciprocate the
2950 result. */
2951 if (n < 0)
2952 op = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
2953 op, NULL_RTX, 0, OPTAB_LIB_WIDEN);
2955 return op;
2959 /* Try if the exponent is a third of an integer. In this case
2960 we can expand to x**(n/3) * cbrt(x)**(n%3). As cbrt (x) is
2961 different from pow (x, 1./3.) due to rounding and behavior
2962 with negative x we need to constrain this transformation to
2963 unsafe math and positive x or finite math. */
2964 fn = mathfn_built_in (type, BUILT_IN_CBRT);
2965 if (fn != NULL_TREE
2966 && flag_unsafe_math_optimizations
2967 && (tree_expr_nonnegative_p (arg0)
2968 || !HONOR_NANS (mode)))
2970 real_arithmetic (&c2, MULT_EXPR, &c, &dconst3);
2971 real_round (&c2, mode, &c2);
2972 n = real_to_integer (&c2);
2973 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
2974 real_arithmetic (&c2, RDIV_EXPR, &cint, &dconst3);
2975 real_convert (&c2, mode, &c2);
2976 if (real_identical (&c2, &c)
2977 && ((!optimize_size
2978 && powi_cost (n/3) <= POWI_MAX_MULTS)
2979 || n == 1))
2981 tree call_expr = build_call_expr (fn, 1,narg0);
2982 op = expand_builtin (call_expr, NULL_RTX, subtarget, mode, 0);
2983 if (abs (n) % 3 == 2)
2984 op = expand_simple_binop (mode, MULT, op, op, op,
2985 0, OPTAB_LIB_WIDEN);
2986 if (n != 1)
2988 op2 = expand_expr (narg0, subtarget, VOIDmode, EXPAND_NORMAL);
2989 op2 = force_reg (mode, op2);
2990 op2 = expand_powi (op2, mode, abs (n / 3));
2991 op = expand_simple_binop (mode, MULT, op, op2, NULL_RTX,
2992 0, OPTAB_LIB_WIDEN);
2993 /* If the original exponent was negative, reciprocate the
2994 result. */
2995 if (n < 0)
2996 op = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
2997 op, NULL_RTX, 0, OPTAB_LIB_WIDEN);
2999 return op;
3003 /* Fall back to optab expansion. */
3004 return expand_builtin_mathfn_2 (exp, target, subtarget);
3007 /* Expand a call to the powi built-in mathematical function. Return NULL_RTX if
3008 a normal call should be emitted rather than expanding the function
3009 in-line. EXP is the expression that is a call to the builtin
3010 function; if convenient, the result should be placed in TARGET. */
3012 static rtx
3013 expand_builtin_powi (tree exp, rtx target, rtx subtarget)
3015 tree arg0, arg1;
3016 rtx op0, op1;
3017 enum machine_mode mode;
3018 enum machine_mode mode2;
3020 if (! validate_arglist (exp, REAL_TYPE, INTEGER_TYPE, VOID_TYPE))
3021 return NULL_RTX;
3023 arg0 = CALL_EXPR_ARG (exp, 0);
3024 arg1 = CALL_EXPR_ARG (exp, 1);
3025 mode = TYPE_MODE (TREE_TYPE (exp));
3027 /* Handle constant power. */
3029 if (TREE_CODE (arg1) == INTEGER_CST
3030 && !TREE_OVERFLOW (arg1))
3032 HOST_WIDE_INT n = TREE_INT_CST_LOW (arg1);
3034 /* If the exponent is -1, 0, 1 or 2, then expand_powi is exact.
3035 Otherwise, check the number of multiplications required. */
3036 if ((TREE_INT_CST_HIGH (arg1) == 0
3037 || TREE_INT_CST_HIGH (arg1) == -1)
3038 && ((n >= -1 && n <= 2)
3039 || (! optimize_size
3040 && powi_cost (n) <= POWI_MAX_MULTS)))
3042 op0 = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
3043 op0 = force_reg (mode, op0);
3044 return expand_powi (op0, mode, n);
3048 /* Emit a libcall to libgcc. */
3050 /* Mode of the 2nd argument must match that of an int. */
3051 mode2 = mode_for_size (INT_TYPE_SIZE, MODE_INT, 0);
3053 if (target == NULL_RTX)
3054 target = gen_reg_rtx (mode);
3056 op0 = expand_expr (arg0, subtarget, mode, EXPAND_NORMAL);
3057 if (GET_MODE (op0) != mode)
3058 op0 = convert_to_mode (mode, op0, 0);
3059 op1 = expand_expr (arg1, NULL_RTX, mode2, EXPAND_NORMAL);
3060 if (GET_MODE (op1) != mode2)
3061 op1 = convert_to_mode (mode2, op1, 0);
3063 target = emit_library_call_value (optab_libfunc (powi_optab, mode),
3064 target, LCT_CONST_MAKE_BLOCK, mode, 2,
3065 op0, mode, op1, mode2);
3067 return target;
3070 /* Expand expression EXP which is a call to the strlen builtin. Return
3071 NULL_RTX if we failed the caller should emit a normal call, otherwise
3072 try to get the result in TARGET, if convenient. */
3074 static rtx
3075 expand_builtin_strlen (tree exp, rtx target,
3076 enum machine_mode target_mode)
3078 if (!validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
3079 return NULL_RTX;
3080 else
3082 rtx pat;
3083 tree len;
3084 tree src = CALL_EXPR_ARG (exp, 0);
3085 rtx result, src_reg, char_rtx, before_strlen;
3086 enum machine_mode insn_mode = target_mode, char_mode;
3087 enum insn_code icode = CODE_FOR_nothing;
3088 int align;
3090 /* If the length can be computed at compile-time, return it. */
3091 len = c_strlen (src, 0);
3092 if (len)
3093 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
3095 /* If the length can be computed at compile-time and is constant
3096 integer, but there are side-effects in src, evaluate
3097 src for side-effects, then return len.
3098 E.g. x = strlen (i++ ? "xfoo" + 1 : "bar");
3099 can be optimized into: i++; x = 3; */
3100 len = c_strlen (src, 1);
3101 if (len && TREE_CODE (len) == INTEGER_CST)
3103 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
3104 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
3107 align = get_pointer_alignment (src, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3109 /* If SRC is not a pointer type, don't do this operation inline. */
3110 if (align == 0)
3111 return NULL_RTX;
3113 /* Bail out if we can't compute strlen in the right mode. */
3114 while (insn_mode != VOIDmode)
3116 icode = optab_handler (strlen_optab, insn_mode)->insn_code;
3117 if (icode != CODE_FOR_nothing)
3118 break;
3120 insn_mode = GET_MODE_WIDER_MODE (insn_mode);
3122 if (insn_mode == VOIDmode)
3123 return NULL_RTX;
3125 /* Make a place to write the result of the instruction. */
3126 result = target;
3127 if (! (result != 0
3128 && REG_P (result)
3129 && GET_MODE (result) == insn_mode
3130 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
3131 result = gen_reg_rtx (insn_mode);
3133 /* Make a place to hold the source address. We will not expand
3134 the actual source until we are sure that the expansion will
3135 not fail -- there are trees that cannot be expanded twice. */
3136 src_reg = gen_reg_rtx (Pmode);
3138 /* Mark the beginning of the strlen sequence so we can emit the
3139 source operand later. */
3140 before_strlen = get_last_insn ();
3142 char_rtx = const0_rtx;
3143 char_mode = insn_data[(int) icode].operand[2].mode;
3144 if (! (*insn_data[(int) icode].operand[2].predicate) (char_rtx,
3145 char_mode))
3146 char_rtx = copy_to_mode_reg (char_mode, char_rtx);
3148 pat = GEN_FCN (icode) (result, gen_rtx_MEM (BLKmode, src_reg),
3149 char_rtx, GEN_INT (align));
3150 if (! pat)
3151 return NULL_RTX;
3152 emit_insn (pat);
3154 /* Now that we are assured of success, expand the source. */
3155 start_sequence ();
3156 pat = expand_expr (src, src_reg, ptr_mode, EXPAND_NORMAL);
3157 if (pat != src_reg)
3158 emit_move_insn (src_reg, pat);
3159 pat = get_insns ();
3160 end_sequence ();
3162 if (before_strlen)
3163 emit_insn_after (pat, before_strlen);
3164 else
3165 emit_insn_before (pat, get_insns ());
3167 /* Return the value in the proper mode for this function. */
3168 if (GET_MODE (result) == target_mode)
3169 target = result;
3170 else if (target != 0)
3171 convert_move (target, result, 0);
3172 else
3173 target = convert_to_mode (target_mode, result, 0);
3175 return target;
3179 /* Expand a call to the strstr builtin. Return NULL_RTX if we failed the
3180 caller should emit a normal call, otherwise try to get the result
3181 in TARGET, if convenient (and in mode MODE if that's convenient). */
3183 static rtx
3184 expand_builtin_strstr (tree exp, rtx target, enum machine_mode mode)
3186 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3188 tree type = TREE_TYPE (exp);
3189 tree result = fold_builtin_strstr (CALL_EXPR_ARG (exp, 0),
3190 CALL_EXPR_ARG (exp, 1), type);
3191 if (result)
3192 return expand_expr (result, target, mode, EXPAND_NORMAL);
3194 return NULL_RTX;
3197 /* Expand a call to the strchr builtin. Return NULL_RTX if we failed the
3198 caller should emit a normal call, otherwise try to get the result
3199 in TARGET, if convenient (and in mode MODE if that's convenient). */
3201 static rtx
3202 expand_builtin_strchr (tree exp, rtx target, enum machine_mode mode)
3204 if (validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3206 tree type = TREE_TYPE (exp);
3207 tree result = fold_builtin_strchr (CALL_EXPR_ARG (exp, 0),
3208 CALL_EXPR_ARG (exp, 1), type);
3209 if (result)
3210 return expand_expr (result, target, mode, EXPAND_NORMAL);
3212 /* FIXME: Should use strchrM optab so that ports can optimize this. */
3214 return NULL_RTX;
3217 /* Expand a call to the strrchr builtin. Return NULL_RTX if we failed the
3218 caller should emit a normal call, otherwise try to get the result
3219 in TARGET, if convenient (and in mode MODE if that's convenient). */
3221 static rtx
3222 expand_builtin_strrchr (tree exp, rtx target, enum machine_mode mode)
3224 if (validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3226 tree type = TREE_TYPE (exp);
3227 tree result = fold_builtin_strrchr (CALL_EXPR_ARG (exp, 0),
3228 CALL_EXPR_ARG (exp, 1), type);
3229 if (result)
3230 return expand_expr (result, target, mode, EXPAND_NORMAL);
3232 return NULL_RTX;
3235 /* Expand a call to the strpbrk builtin. Return NULL_RTX if we failed the
3236 caller should emit a normal call, otherwise try to get the result
3237 in TARGET, if convenient (and in mode MODE if that's convenient). */
3239 static rtx
3240 expand_builtin_strpbrk (tree exp, rtx target, enum machine_mode mode)
3242 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3244 tree type = TREE_TYPE (exp);
3245 tree result = fold_builtin_strpbrk (CALL_EXPR_ARG (exp, 0),
3246 CALL_EXPR_ARG (exp, 1), type);
3247 if (result)
3248 return expand_expr (result, target, mode, EXPAND_NORMAL);
3250 return NULL_RTX;
3253 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3254 bytes from constant string DATA + OFFSET and return it as target
3255 constant. */
3257 static rtx
3258 builtin_memcpy_read_str (void *data, HOST_WIDE_INT offset,
3259 enum machine_mode mode)
3261 const char *str = (const char *) data;
3263 gcc_assert (offset >= 0
3264 && ((unsigned HOST_WIDE_INT) offset + GET_MODE_SIZE (mode)
3265 <= strlen (str) + 1));
3267 return c_readstr (str + offset, mode);
3270 /* Expand a call EXP to the memcpy builtin.
3271 Return NULL_RTX if we failed, the caller should emit a normal call,
3272 otherwise try to get the result in TARGET, if convenient (and in
3273 mode MODE if that's convenient). */
3275 static rtx
3276 expand_builtin_memcpy (tree exp, rtx target, enum machine_mode mode)
3278 tree fndecl = get_callee_fndecl (exp);
3280 if (!validate_arglist (exp,
3281 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3282 return NULL_RTX;
3283 else
3285 tree dest = CALL_EXPR_ARG (exp, 0);
3286 tree src = CALL_EXPR_ARG (exp, 1);
3287 tree len = CALL_EXPR_ARG (exp, 2);
3288 const char *src_str;
3289 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
3290 unsigned int dest_align
3291 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3292 rtx dest_mem, src_mem, dest_addr, len_rtx;
3293 tree result = fold_builtin_memory_op (dest, src, len,
3294 TREE_TYPE (TREE_TYPE (fndecl)),
3295 false, /*endp=*/0);
3296 HOST_WIDE_INT expected_size = -1;
3297 unsigned int expected_align = 0;
3299 if (result)
3301 while (TREE_CODE (result) == COMPOUND_EXPR)
3303 expand_expr (TREE_OPERAND (result, 0), const0_rtx, VOIDmode,
3304 EXPAND_NORMAL);
3305 result = TREE_OPERAND (result, 1);
3307 return expand_expr (result, target, mode, EXPAND_NORMAL);
3310 /* If DEST is not a pointer type, call the normal function. */
3311 if (dest_align == 0)
3312 return NULL_RTX;
3314 /* If either SRC is not a pointer type, don't do this
3315 operation in-line. */
3316 if (src_align == 0)
3317 return NULL_RTX;
3319 stringop_block_profile (exp, &expected_align, &expected_size);
3320 if (expected_align < dest_align)
3321 expected_align = dest_align;
3322 dest_mem = get_memory_rtx (dest, len);
3323 set_mem_align (dest_mem, dest_align);
3324 len_rtx = expand_normal (len);
3325 src_str = c_getstr (src);
3327 /* If SRC is a string constant and block move would be done
3328 by pieces, we can avoid loading the string from memory
3329 and only stored the computed constants. */
3330 if (src_str
3331 && GET_CODE (len_rtx) == CONST_INT
3332 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
3333 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
3334 (void *) src_str, dest_align, false))
3336 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
3337 builtin_memcpy_read_str,
3338 (void *) src_str, dest_align, false, 0);
3339 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3340 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3341 return dest_mem;
3344 src_mem = get_memory_rtx (src, len);
3345 set_mem_align (src_mem, src_align);
3347 /* Copy word part most expediently. */
3348 dest_addr = emit_block_move_hints (dest_mem, src_mem, len_rtx,
3349 CALL_EXPR_TAILCALL (exp)
3350 ? BLOCK_OP_TAILCALL : BLOCK_OP_NORMAL,
3351 expected_align, expected_size);
3353 if (dest_addr == 0)
3355 dest_addr = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3356 dest_addr = convert_memory_address (ptr_mode, dest_addr);
3358 return dest_addr;
3362 /* Expand a call EXP to the mempcpy builtin.
3363 Return NULL_RTX if we failed; the caller should emit a normal call,
3364 otherwise try to get the result in TARGET, if convenient (and in
3365 mode MODE if that's convenient). If ENDP is 0 return the
3366 destination pointer, if ENDP is 1 return the end pointer ala
3367 mempcpy, and if ENDP is 2 return the end pointer minus one ala
3368 stpcpy. */
3370 static rtx
3371 expand_builtin_mempcpy(tree exp, rtx target, enum machine_mode mode)
3373 if (!validate_arglist (exp,
3374 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3375 return NULL_RTX;
3376 else
3378 tree dest = CALL_EXPR_ARG (exp, 0);
3379 tree src = CALL_EXPR_ARG (exp, 1);
3380 tree len = CALL_EXPR_ARG (exp, 2);
3381 return expand_builtin_mempcpy_args (dest, src, len,
3382 TREE_TYPE (exp),
3383 target, mode, /*endp=*/ 1);
3387 /* Helper function to do the actual work for expand_builtin_mempcpy. The
3388 arguments to the builtin_mempcpy call DEST, SRC, and LEN are broken out
3389 so that this can also be called without constructing an actual CALL_EXPR.
3390 TYPE is the return type of the call. The other arguments and return value
3391 are the same as for expand_builtin_mempcpy. */
3393 static rtx
3394 expand_builtin_mempcpy_args (tree dest, tree src, tree len, tree type,
3395 rtx target, enum machine_mode mode, int endp)
3397 /* If return value is ignored, transform mempcpy into memcpy. */
3398 if (target == const0_rtx)
3400 tree fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
3402 if (!fn)
3403 return NULL_RTX;
3405 return expand_expr (build_call_expr (fn, 3, dest, src, len),
3406 target, mode, EXPAND_NORMAL);
3408 else
3410 const char *src_str;
3411 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
3412 unsigned int dest_align
3413 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3414 rtx dest_mem, src_mem, len_rtx;
3415 tree result = fold_builtin_memory_op (dest, src, len, type, false, endp);
3417 if (result)
3419 while (TREE_CODE (result) == COMPOUND_EXPR)
3421 expand_expr (TREE_OPERAND (result, 0), const0_rtx, VOIDmode,
3422 EXPAND_NORMAL);
3423 result = TREE_OPERAND (result, 1);
3425 return expand_expr (result, target, mode, EXPAND_NORMAL);
3428 /* If either SRC or DEST is not a pointer type, don't do this
3429 operation in-line. */
3430 if (dest_align == 0 || src_align == 0)
3431 return NULL_RTX;
3433 /* If LEN is not constant, call the normal function. */
3434 if (! host_integerp (len, 1))
3435 return NULL_RTX;
3437 len_rtx = expand_normal (len);
3438 src_str = c_getstr (src);
3440 /* If SRC is a string constant and block move would be done
3441 by pieces, we can avoid loading the string from memory
3442 and only stored the computed constants. */
3443 if (src_str
3444 && GET_CODE (len_rtx) == CONST_INT
3445 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
3446 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
3447 (void *) src_str, dest_align, false))
3449 dest_mem = get_memory_rtx (dest, len);
3450 set_mem_align (dest_mem, dest_align);
3451 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
3452 builtin_memcpy_read_str,
3453 (void *) src_str, dest_align,
3454 false, endp);
3455 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3456 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3457 return dest_mem;
3460 if (GET_CODE (len_rtx) == CONST_INT
3461 && can_move_by_pieces (INTVAL (len_rtx),
3462 MIN (dest_align, src_align)))
3464 dest_mem = get_memory_rtx (dest, len);
3465 set_mem_align (dest_mem, dest_align);
3466 src_mem = get_memory_rtx (src, len);
3467 set_mem_align (src_mem, src_align);
3468 dest_mem = move_by_pieces (dest_mem, src_mem, INTVAL (len_rtx),
3469 MIN (dest_align, src_align), endp);
3470 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3471 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3472 return dest_mem;
3475 return NULL_RTX;
3479 /* Expand expression EXP, which is a call to the memmove builtin. Return
3480 NULL_RTX if we failed; the caller should emit a normal call. */
3482 static rtx
3483 expand_builtin_memmove (tree exp, rtx target, enum machine_mode mode, int ignore)
3485 if (!validate_arglist (exp,
3486 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3487 return NULL_RTX;
3488 else
3490 tree dest = CALL_EXPR_ARG (exp, 0);
3491 tree src = CALL_EXPR_ARG (exp, 1);
3492 tree len = CALL_EXPR_ARG (exp, 2);
3493 return expand_builtin_memmove_args (dest, src, len, TREE_TYPE (exp),
3494 target, mode, ignore);
3498 /* Helper function to do the actual work for expand_builtin_memmove. The
3499 arguments to the builtin_memmove call DEST, SRC, and LEN are broken out
3500 so that this can also be called without constructing an actual CALL_EXPR.
3501 TYPE is the return type of the call. The other arguments and return value
3502 are the same as for expand_builtin_memmove. */
3504 static rtx
3505 expand_builtin_memmove_args (tree dest, tree src, tree len,
3506 tree type, rtx target, enum machine_mode mode,
3507 int ignore)
3509 tree result = fold_builtin_memory_op (dest, src, len, type, ignore, /*endp=*/3);
3511 if (result)
3513 STRIP_TYPE_NOPS (result);
3514 while (TREE_CODE (result) == COMPOUND_EXPR)
3516 expand_expr (TREE_OPERAND (result, 0), const0_rtx, VOIDmode,
3517 EXPAND_NORMAL);
3518 result = TREE_OPERAND (result, 1);
3520 return expand_expr (result, target, mode, EXPAND_NORMAL);
3523 /* Otherwise, call the normal function. */
3524 return NULL_RTX;
3527 /* Expand expression EXP, which is a call to the bcopy builtin. Return
3528 NULL_RTX if we failed the caller should emit a normal call. */
3530 static rtx
3531 expand_builtin_bcopy (tree exp, int ignore)
3533 tree type = TREE_TYPE (exp);
3534 tree src, dest, size;
3536 if (!validate_arglist (exp,
3537 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3538 return NULL_RTX;
3540 src = CALL_EXPR_ARG (exp, 0);
3541 dest = CALL_EXPR_ARG (exp, 1);
3542 size = CALL_EXPR_ARG (exp, 2);
3544 /* Transform bcopy(ptr x, ptr y, int z) to memmove(ptr y, ptr x, size_t z).
3545 This is done this way so that if it isn't expanded inline, we fall
3546 back to calling bcopy instead of memmove. */
3547 return expand_builtin_memmove_args (dest, src,
3548 fold_convert (sizetype, size),
3549 type, const0_rtx, VOIDmode,
3550 ignore);
3553 #ifndef HAVE_movstr
3554 # define HAVE_movstr 0
3555 # define CODE_FOR_movstr CODE_FOR_nothing
3556 #endif
3558 /* Expand into a movstr instruction, if one is available. Return NULL_RTX if
3559 we failed, the caller should emit a normal call, otherwise try to
3560 get the result in TARGET, if convenient. If ENDP is 0 return the
3561 destination pointer, if ENDP is 1 return the end pointer ala
3562 mempcpy, and if ENDP is 2 return the end pointer minus one ala
3563 stpcpy. */
3565 static rtx
3566 expand_movstr (tree dest, tree src, rtx target, int endp)
3568 rtx end;
3569 rtx dest_mem;
3570 rtx src_mem;
3571 rtx insn;
3572 const struct insn_data * data;
3574 if (!HAVE_movstr)
3575 return NULL_RTX;
3577 dest_mem = get_memory_rtx (dest, NULL);
3578 src_mem = get_memory_rtx (src, NULL);
3579 if (!endp)
3581 target = force_reg (Pmode, XEXP (dest_mem, 0));
3582 dest_mem = replace_equiv_address (dest_mem, target);
3583 end = gen_reg_rtx (Pmode);
3585 else
3587 if (target == 0 || target == const0_rtx)
3589 end = gen_reg_rtx (Pmode);
3590 if (target == 0)
3591 target = end;
3593 else
3594 end = target;
3597 data = insn_data + CODE_FOR_movstr;
3599 if (data->operand[0].mode != VOIDmode)
3600 end = gen_lowpart (data->operand[0].mode, end);
3602 insn = data->genfun (end, dest_mem, src_mem);
3604 gcc_assert (insn);
3606 emit_insn (insn);
3608 /* movstr is supposed to set end to the address of the NUL
3609 terminator. If the caller requested a mempcpy-like return value,
3610 adjust it. */
3611 if (endp == 1 && target != const0_rtx)
3613 rtx tem = plus_constant (gen_lowpart (GET_MODE (target), end), 1);
3614 emit_move_insn (target, force_operand (tem, NULL_RTX));
3617 return target;
3620 /* Expand expression EXP, which is a call to the strcpy builtin. Return
3621 NULL_RTX if we failed the caller should emit a normal call, otherwise
3622 try to get the result in TARGET, if convenient (and in mode MODE if that's
3623 convenient). */
3625 static rtx
3626 expand_builtin_strcpy (tree fndecl, tree exp, rtx target, enum machine_mode mode)
3628 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3630 tree dest = CALL_EXPR_ARG (exp, 0);
3631 tree src = CALL_EXPR_ARG (exp, 1);
3632 return expand_builtin_strcpy_args (fndecl, dest, src, target, mode);
3634 return NULL_RTX;
3637 /* Helper function to do the actual work for expand_builtin_strcpy. The
3638 arguments to the builtin_strcpy call DEST and SRC are broken out
3639 so that this can also be called without constructing an actual CALL_EXPR.
3640 The other arguments and return value are the same as for
3641 expand_builtin_strcpy. */
3643 static rtx
3644 expand_builtin_strcpy_args (tree fndecl, tree dest, tree src,
3645 rtx target, enum machine_mode mode)
3647 tree result = fold_builtin_strcpy (fndecl, dest, src, 0);
3648 if (result)
3649 return expand_expr (result, target, mode, EXPAND_NORMAL);
3650 return expand_movstr (dest, src, target, /*endp=*/0);
3654 /* Expand a call EXP to the stpcpy builtin.
3655 Return NULL_RTX if we failed the caller should emit a normal call,
3656 otherwise try to get the result in TARGET, if convenient (and in
3657 mode MODE if that's convenient). */
3659 static rtx
3660 expand_builtin_stpcpy (tree exp, rtx target, enum machine_mode mode)
3662 tree dst, src;
3664 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3665 return NULL_RTX;
3667 dst = CALL_EXPR_ARG (exp, 0);
3668 src = CALL_EXPR_ARG (exp, 1);
3670 /* If return value is ignored, transform stpcpy into strcpy. */
3671 if (target == const0_rtx)
3673 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
3674 if (!fn)
3675 return NULL_RTX;
3677 return expand_expr (build_call_expr (fn, 2, dst, src),
3678 target, mode, EXPAND_NORMAL);
3680 else
3682 tree len, lenp1;
3683 rtx ret;
3685 /* Ensure we get an actual string whose length can be evaluated at
3686 compile-time, not an expression containing a string. This is
3687 because the latter will potentially produce pessimized code
3688 when used to produce the return value. */
3689 if (! c_getstr (src) || ! (len = c_strlen (src, 0)))
3690 return expand_movstr (dst, src, target, /*endp=*/2);
3692 lenp1 = size_binop (PLUS_EXPR, len, ssize_int (1));
3693 ret = expand_builtin_mempcpy_args (dst, src, lenp1, TREE_TYPE (exp),
3694 target, mode, /*endp=*/2);
3696 if (ret)
3697 return ret;
3699 if (TREE_CODE (len) == INTEGER_CST)
3701 rtx len_rtx = expand_normal (len);
3703 if (GET_CODE (len_rtx) == CONST_INT)
3705 ret = expand_builtin_strcpy_args (get_callee_fndecl (exp),
3706 dst, src, target, mode);
3708 if (ret)
3710 if (! target)
3712 if (mode != VOIDmode)
3713 target = gen_reg_rtx (mode);
3714 else
3715 target = gen_reg_rtx (GET_MODE (ret));
3717 if (GET_MODE (target) != GET_MODE (ret))
3718 ret = gen_lowpart (GET_MODE (target), ret);
3720 ret = plus_constant (ret, INTVAL (len_rtx));
3721 ret = emit_move_insn (target, force_operand (ret, NULL_RTX));
3722 gcc_assert (ret);
3724 return target;
3729 return expand_movstr (dst, src, target, /*endp=*/2);
3733 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3734 bytes from constant string DATA + OFFSET and return it as target
3735 constant. */
3738 builtin_strncpy_read_str (void *data, HOST_WIDE_INT offset,
3739 enum machine_mode mode)
3741 const char *str = (const char *) data;
3743 if ((unsigned HOST_WIDE_INT) offset > strlen (str))
3744 return const0_rtx;
3746 return c_readstr (str + offset, mode);
3749 /* Expand expression EXP, which is a call to the strncpy builtin. Return
3750 NULL_RTX if we failed the caller should emit a normal call. */
3752 static rtx
3753 expand_builtin_strncpy (tree exp, rtx target, enum machine_mode mode)
3755 tree fndecl = get_callee_fndecl (exp);
3757 if (validate_arglist (exp,
3758 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3760 tree dest = CALL_EXPR_ARG (exp, 0);
3761 tree src = CALL_EXPR_ARG (exp, 1);
3762 tree len = CALL_EXPR_ARG (exp, 2);
3763 tree slen = c_strlen (src, 1);
3764 tree result = fold_builtin_strncpy (fndecl, dest, src, len, slen);
3766 if (result)
3768 while (TREE_CODE (result) == COMPOUND_EXPR)
3770 expand_expr (TREE_OPERAND (result, 0), const0_rtx, VOIDmode,
3771 EXPAND_NORMAL);
3772 result = TREE_OPERAND (result, 1);
3774 return expand_expr (result, target, mode, EXPAND_NORMAL);
3777 /* We must be passed a constant len and src parameter. */
3778 if (!host_integerp (len, 1) || !slen || !host_integerp (slen, 1))
3779 return NULL_RTX;
3781 slen = size_binop (PLUS_EXPR, slen, ssize_int (1));
3783 /* We're required to pad with trailing zeros if the requested
3784 len is greater than strlen(s2)+1. In that case try to
3785 use store_by_pieces, if it fails, punt. */
3786 if (tree_int_cst_lt (slen, len))
3788 unsigned int dest_align
3789 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3790 const char *p = c_getstr (src);
3791 rtx dest_mem;
3793 if (!p || dest_align == 0 || !host_integerp (len, 1)
3794 || !can_store_by_pieces (tree_low_cst (len, 1),
3795 builtin_strncpy_read_str,
3796 (void *) p, dest_align, false))
3797 return NULL_RTX;
3799 dest_mem = get_memory_rtx (dest, len);
3800 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3801 builtin_strncpy_read_str,
3802 (void *) p, dest_align, false, 0);
3803 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3804 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3805 return dest_mem;
3808 return NULL_RTX;
3811 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3812 bytes from constant string DATA + OFFSET and return it as target
3813 constant. */
3816 builtin_memset_read_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3817 enum machine_mode mode)
3819 const char *c = (const char *) data;
3820 char *p = alloca (GET_MODE_SIZE (mode));
3822 memset (p, *c, GET_MODE_SIZE (mode));
3824 return c_readstr (p, mode);
3827 /* Callback routine for store_by_pieces. Return the RTL of a register
3828 containing GET_MODE_SIZE (MODE) consecutive copies of the unsigned
3829 char value given in the RTL register data. For example, if mode is
3830 4 bytes wide, return the RTL for 0x01010101*data. */
3832 static rtx
3833 builtin_memset_gen_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3834 enum machine_mode mode)
3836 rtx target, coeff;
3837 size_t size;
3838 char *p;
3840 size = GET_MODE_SIZE (mode);
3841 if (size == 1)
3842 return (rtx) data;
3844 p = alloca (size);
3845 memset (p, 1, size);
3846 coeff = c_readstr (p, mode);
3848 target = convert_to_mode (mode, (rtx) data, 1);
3849 target = expand_mult (mode, target, coeff, NULL_RTX, 1);
3850 return force_reg (mode, target);
3853 /* Expand expression EXP, which is a call to the memset builtin. Return
3854 NULL_RTX if we failed the caller should emit a normal call, otherwise
3855 try to get the result in TARGET, if convenient (and in mode MODE if that's
3856 convenient). */
3858 static rtx
3859 expand_builtin_memset (tree exp, rtx target, enum machine_mode mode)
3861 if (!validate_arglist (exp,
3862 POINTER_TYPE, INTEGER_TYPE, INTEGER_TYPE, VOID_TYPE))
3863 return NULL_RTX;
3864 else
3866 tree dest = CALL_EXPR_ARG (exp, 0);
3867 tree val = CALL_EXPR_ARG (exp, 1);
3868 tree len = CALL_EXPR_ARG (exp, 2);
3869 return expand_builtin_memset_args (dest, val, len, target, mode, exp);
3873 /* Helper function to do the actual work for expand_builtin_memset. The
3874 arguments to the builtin_memset call DEST, VAL, and LEN are broken out
3875 so that this can also be called without constructing an actual CALL_EXPR.
3876 The other arguments and return value are the same as for
3877 expand_builtin_memset. */
3879 static rtx
3880 expand_builtin_memset_args (tree dest, tree val, tree len,
3881 rtx target, enum machine_mode mode, tree orig_exp)
3883 tree fndecl, fn;
3884 enum built_in_function fcode;
3885 char c;
3886 unsigned int dest_align;
3887 rtx dest_mem, dest_addr, len_rtx;
3888 HOST_WIDE_INT expected_size = -1;
3889 unsigned int expected_align = 0;
3891 dest_align = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3893 /* If DEST is not a pointer type, don't do this operation in-line. */
3894 if (dest_align == 0)
3895 return NULL_RTX;
3897 stringop_block_profile (orig_exp, &expected_align, &expected_size);
3898 if (expected_align < dest_align)
3899 expected_align = dest_align;
3901 /* If the LEN parameter is zero, return DEST. */
3902 if (integer_zerop (len))
3904 /* Evaluate and ignore VAL in case it has side-effects. */
3905 expand_expr (val, const0_rtx, VOIDmode, EXPAND_NORMAL);
3906 return expand_expr (dest, target, mode, EXPAND_NORMAL);
3909 /* Stabilize the arguments in case we fail. */
3910 dest = builtin_save_expr (dest);
3911 val = builtin_save_expr (val);
3912 len = builtin_save_expr (len);
3914 len_rtx = expand_normal (len);
3915 dest_mem = get_memory_rtx (dest, len);
3917 if (TREE_CODE (val) != INTEGER_CST)
3919 rtx val_rtx;
3921 val_rtx = expand_normal (val);
3922 val_rtx = convert_to_mode (TYPE_MODE (unsigned_char_type_node),
3923 val_rtx, 0);
3925 /* Assume that we can memset by pieces if we can store
3926 * the coefficients by pieces (in the required modes).
3927 * We can't pass builtin_memset_gen_str as that emits RTL. */
3928 c = 1;
3929 if (host_integerp (len, 1)
3930 && can_store_by_pieces (tree_low_cst (len, 1),
3931 builtin_memset_read_str, &c, dest_align,
3932 true))
3934 val_rtx = force_reg (TYPE_MODE (unsigned_char_type_node),
3935 val_rtx);
3936 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3937 builtin_memset_gen_str, val_rtx, dest_align,
3938 true, 0);
3940 else if (!set_storage_via_setmem (dest_mem, len_rtx, val_rtx,
3941 dest_align, expected_align,
3942 expected_size))
3943 goto do_libcall;
3945 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3946 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3947 return dest_mem;
3950 if (target_char_cast (val, &c))
3951 goto do_libcall;
3953 if (c)
3955 if (host_integerp (len, 1)
3956 && can_store_by_pieces (tree_low_cst (len, 1),
3957 builtin_memset_read_str, &c, dest_align,
3958 true))
3959 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3960 builtin_memset_read_str, &c, dest_align, true, 0);
3961 else if (!set_storage_via_setmem (dest_mem, len_rtx, GEN_INT (c),
3962 dest_align, expected_align,
3963 expected_size))
3964 goto do_libcall;
3966 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3967 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3968 return dest_mem;
3971 set_mem_align (dest_mem, dest_align);
3972 dest_addr = clear_storage_hints (dest_mem, len_rtx,
3973 CALL_EXPR_TAILCALL (orig_exp)
3974 ? BLOCK_OP_TAILCALL : BLOCK_OP_NORMAL,
3975 expected_align, expected_size);
3977 if (dest_addr == 0)
3979 dest_addr = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3980 dest_addr = convert_memory_address (ptr_mode, dest_addr);
3983 return dest_addr;
3985 do_libcall:
3986 fndecl = get_callee_fndecl (orig_exp);
3987 fcode = DECL_FUNCTION_CODE (fndecl);
3988 if (fcode == BUILT_IN_MEMSET)
3989 fn = build_call_expr (fndecl, 3, dest, val, len);
3990 else if (fcode == BUILT_IN_BZERO)
3991 fn = build_call_expr (fndecl, 2, dest, len);
3992 else
3993 gcc_unreachable ();
3994 if (TREE_CODE (fn) == CALL_EXPR)
3995 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (orig_exp);
3996 return expand_call (fn, target, target == const0_rtx);
3999 /* Expand expression EXP, which is a call to the bzero builtin. Return
4000 NULL_RTX if we failed the caller should emit a normal call. */
4002 static rtx
4003 expand_builtin_bzero (tree exp)
4005 tree dest, size;
4007 if (!validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4008 return NULL_RTX;
4010 dest = CALL_EXPR_ARG (exp, 0);
4011 size = CALL_EXPR_ARG (exp, 1);
4013 /* New argument list transforming bzero(ptr x, int y) to
4014 memset(ptr x, int 0, size_t y). This is done this way
4015 so that if it isn't expanded inline, we fallback to
4016 calling bzero instead of memset. */
4018 return expand_builtin_memset_args (dest, integer_zero_node,
4019 fold_convert (sizetype, size),
4020 const0_rtx, VOIDmode, exp);
4023 /* Expand a call to the memchr builtin. Return NULL_RTX if we failed the
4024 caller should emit a normal call, otherwise try to get the result
4025 in TARGET, if convenient (and in mode MODE if that's convenient). */
4027 static rtx
4028 expand_builtin_memchr (tree exp, rtx target, enum machine_mode mode)
4030 if (validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE,
4031 INTEGER_TYPE, VOID_TYPE))
4033 tree type = TREE_TYPE (exp);
4034 tree result = fold_builtin_memchr (CALL_EXPR_ARG (exp, 0),
4035 CALL_EXPR_ARG (exp, 1),
4036 CALL_EXPR_ARG (exp, 2), type);
4037 if (result)
4038 return expand_expr (result, target, mode, EXPAND_NORMAL);
4040 return NULL_RTX;
4043 /* Expand expression EXP, which is a call to the memcmp built-in function.
4044 Return NULL_RTX if we failed and the
4045 caller should emit a normal call, otherwise try to get the result in
4046 TARGET, if convenient (and in mode MODE, if that's convenient). */
4048 static rtx
4049 expand_builtin_memcmp (tree exp, rtx target, enum machine_mode mode)
4051 if (!validate_arglist (exp,
4052 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4053 return NULL_RTX;
4054 else
4056 tree result = fold_builtin_memcmp (CALL_EXPR_ARG (exp, 0),
4057 CALL_EXPR_ARG (exp, 1),
4058 CALL_EXPR_ARG (exp, 2));
4059 if (result)
4060 return expand_expr (result, target, mode, EXPAND_NORMAL);
4063 #if defined HAVE_cmpmemsi || defined HAVE_cmpstrnsi
4065 rtx arg1_rtx, arg2_rtx, arg3_rtx;
4066 rtx result;
4067 rtx insn;
4068 tree arg1 = CALL_EXPR_ARG (exp, 0);
4069 tree arg2 = CALL_EXPR_ARG (exp, 1);
4070 tree len = CALL_EXPR_ARG (exp, 2);
4072 int arg1_align
4073 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4074 int arg2_align
4075 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4076 enum machine_mode insn_mode;
4078 #ifdef HAVE_cmpmemsi
4079 if (HAVE_cmpmemsi)
4080 insn_mode = insn_data[(int) CODE_FOR_cmpmemsi].operand[0].mode;
4081 else
4082 #endif
4083 #ifdef HAVE_cmpstrnsi
4084 if (HAVE_cmpstrnsi)
4085 insn_mode = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4086 else
4087 #endif
4088 return NULL_RTX;
4090 /* If we don't have POINTER_TYPE, call the function. */
4091 if (arg1_align == 0 || arg2_align == 0)
4092 return NULL_RTX;
4094 /* Make a place to write the result of the instruction. */
4095 result = target;
4096 if (! (result != 0
4097 && REG_P (result) && GET_MODE (result) == insn_mode
4098 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4099 result = gen_reg_rtx (insn_mode);
4101 arg1_rtx = get_memory_rtx (arg1, len);
4102 arg2_rtx = get_memory_rtx (arg2, len);
4103 arg3_rtx = expand_normal (len);
4105 /* Set MEM_SIZE as appropriate. */
4106 if (GET_CODE (arg3_rtx) == CONST_INT)
4108 set_mem_size (arg1_rtx, arg3_rtx);
4109 set_mem_size (arg2_rtx, arg3_rtx);
4112 #ifdef HAVE_cmpmemsi
4113 if (HAVE_cmpmemsi)
4114 insn = gen_cmpmemsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4115 GEN_INT (MIN (arg1_align, arg2_align)));
4116 else
4117 #endif
4118 #ifdef HAVE_cmpstrnsi
4119 if (HAVE_cmpstrnsi)
4120 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4121 GEN_INT (MIN (arg1_align, arg2_align)));
4122 else
4123 #endif
4124 gcc_unreachable ();
4126 if (insn)
4127 emit_insn (insn);
4128 else
4129 emit_library_call_value (memcmp_libfunc, result, LCT_PURE_MAKE_BLOCK,
4130 TYPE_MODE (integer_type_node), 3,
4131 XEXP (arg1_rtx, 0), Pmode,
4132 XEXP (arg2_rtx, 0), Pmode,
4133 convert_to_mode (TYPE_MODE (sizetype), arg3_rtx,
4134 TYPE_UNSIGNED (sizetype)),
4135 TYPE_MODE (sizetype));
4137 /* Return the value in the proper mode for this function. */
4138 mode = TYPE_MODE (TREE_TYPE (exp));
4139 if (GET_MODE (result) == mode)
4140 return result;
4141 else if (target != 0)
4143 convert_move (target, result, 0);
4144 return target;
4146 else
4147 return convert_to_mode (mode, result, 0);
4149 #endif
4151 return NULL_RTX;
4154 /* Expand expression EXP, which is a call to the strcmp builtin. Return NULL_RTX
4155 if we failed the caller should emit a normal call, otherwise try to get
4156 the result in TARGET, if convenient. */
4158 static rtx
4159 expand_builtin_strcmp (tree exp, rtx target, enum machine_mode mode)
4161 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4162 return NULL_RTX;
4163 else
4165 tree result = fold_builtin_strcmp (CALL_EXPR_ARG (exp, 0),
4166 CALL_EXPR_ARG (exp, 1));
4167 if (result)
4168 return expand_expr (result, target, mode, EXPAND_NORMAL);
4171 #if defined HAVE_cmpstrsi || defined HAVE_cmpstrnsi
4172 if (cmpstr_optab[SImode] != CODE_FOR_nothing
4173 || cmpstrn_optab[SImode] != CODE_FOR_nothing)
4175 rtx arg1_rtx, arg2_rtx;
4176 rtx result, insn = NULL_RTX;
4177 tree fndecl, fn;
4178 tree arg1 = CALL_EXPR_ARG (exp, 0);
4179 tree arg2 = CALL_EXPR_ARG (exp, 1);
4181 int arg1_align
4182 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4183 int arg2_align
4184 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4186 /* If we don't have POINTER_TYPE, call the function. */
4187 if (arg1_align == 0 || arg2_align == 0)
4188 return NULL_RTX;
4190 /* Stabilize the arguments in case gen_cmpstr(n)si fail. */
4191 arg1 = builtin_save_expr (arg1);
4192 arg2 = builtin_save_expr (arg2);
4194 arg1_rtx = get_memory_rtx (arg1, NULL);
4195 arg2_rtx = get_memory_rtx (arg2, NULL);
4197 #ifdef HAVE_cmpstrsi
4198 /* Try to call cmpstrsi. */
4199 if (HAVE_cmpstrsi)
4201 enum machine_mode insn_mode
4202 = insn_data[(int) CODE_FOR_cmpstrsi].operand[0].mode;
4204 /* Make a place to write the result of the instruction. */
4205 result = target;
4206 if (! (result != 0
4207 && REG_P (result) && GET_MODE (result) == insn_mode
4208 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4209 result = gen_reg_rtx (insn_mode);
4211 insn = gen_cmpstrsi (result, arg1_rtx, arg2_rtx,
4212 GEN_INT (MIN (arg1_align, arg2_align)));
4214 #endif
4215 #ifdef HAVE_cmpstrnsi
4216 /* Try to determine at least one length and call cmpstrnsi. */
4217 if (!insn && HAVE_cmpstrnsi)
4219 tree len;
4220 rtx arg3_rtx;
4222 enum machine_mode insn_mode
4223 = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4224 tree len1 = c_strlen (arg1, 1);
4225 tree len2 = c_strlen (arg2, 1);
4227 if (len1)
4228 len1 = size_binop (PLUS_EXPR, ssize_int (1), len1);
4229 if (len2)
4230 len2 = size_binop (PLUS_EXPR, ssize_int (1), len2);
4232 /* If we don't have a constant length for the first, use the length
4233 of the second, if we know it. We don't require a constant for
4234 this case; some cost analysis could be done if both are available
4235 but neither is constant. For now, assume they're equally cheap,
4236 unless one has side effects. If both strings have constant lengths,
4237 use the smaller. */
4239 if (!len1)
4240 len = len2;
4241 else if (!len2)
4242 len = len1;
4243 else if (TREE_SIDE_EFFECTS (len1))
4244 len = len2;
4245 else if (TREE_SIDE_EFFECTS (len2))
4246 len = len1;
4247 else if (TREE_CODE (len1) != INTEGER_CST)
4248 len = len2;
4249 else if (TREE_CODE (len2) != INTEGER_CST)
4250 len = len1;
4251 else if (tree_int_cst_lt (len1, len2))
4252 len = len1;
4253 else
4254 len = len2;
4256 /* If both arguments have side effects, we cannot optimize. */
4257 if (!len || TREE_SIDE_EFFECTS (len))
4258 goto do_libcall;
4260 arg3_rtx = expand_normal (len);
4262 /* Make a place to write the result of the instruction. */
4263 result = target;
4264 if (! (result != 0
4265 && REG_P (result) && GET_MODE (result) == insn_mode
4266 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4267 result = gen_reg_rtx (insn_mode);
4269 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4270 GEN_INT (MIN (arg1_align, arg2_align)));
4272 #endif
4274 if (insn)
4276 emit_insn (insn);
4278 /* Return the value in the proper mode for this function. */
4279 mode = TYPE_MODE (TREE_TYPE (exp));
4280 if (GET_MODE (result) == mode)
4281 return result;
4282 if (target == 0)
4283 return convert_to_mode (mode, result, 0);
4284 convert_move (target, result, 0);
4285 return target;
4288 /* Expand the library call ourselves using a stabilized argument
4289 list to avoid re-evaluating the function's arguments twice. */
4290 #ifdef HAVE_cmpstrnsi
4291 do_libcall:
4292 #endif
4293 fndecl = get_callee_fndecl (exp);
4294 fn = build_call_expr (fndecl, 2, arg1, arg2);
4295 if (TREE_CODE (fn) == CALL_EXPR)
4296 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
4297 return expand_call (fn, target, target == const0_rtx);
4299 #endif
4300 return NULL_RTX;
4303 /* Expand expression EXP, which is a call to the strncmp builtin. Return
4304 NULL_RTX if we failed the caller should emit a normal call, otherwise try to get
4305 the result in TARGET, if convenient. */
4307 static rtx
4308 expand_builtin_strncmp (tree exp, rtx target, enum machine_mode mode)
4310 if (!validate_arglist (exp,
4311 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4312 return NULL_RTX;
4313 else
4315 tree result = fold_builtin_strncmp (CALL_EXPR_ARG (exp, 0),
4316 CALL_EXPR_ARG (exp, 1),
4317 CALL_EXPR_ARG (exp, 2));
4318 if (result)
4319 return expand_expr (result, target, mode, EXPAND_NORMAL);
4322 /* If c_strlen can determine an expression for one of the string
4323 lengths, and it doesn't have side effects, then emit cmpstrnsi
4324 using length MIN(strlen(string)+1, arg3). */
4325 #ifdef HAVE_cmpstrnsi
4326 if (HAVE_cmpstrnsi)
4328 tree len, len1, len2;
4329 rtx arg1_rtx, arg2_rtx, arg3_rtx;
4330 rtx result, insn;
4331 tree fndecl, fn;
4332 tree arg1 = CALL_EXPR_ARG (exp, 0);
4333 tree arg2 = CALL_EXPR_ARG (exp, 1);
4334 tree arg3 = CALL_EXPR_ARG (exp, 2);
4336 int arg1_align
4337 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4338 int arg2_align
4339 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4340 enum machine_mode insn_mode
4341 = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4343 len1 = c_strlen (arg1, 1);
4344 len2 = c_strlen (arg2, 1);
4346 if (len1)
4347 len1 = size_binop (PLUS_EXPR, ssize_int (1), len1);
4348 if (len2)
4349 len2 = size_binop (PLUS_EXPR, ssize_int (1), len2);
4351 /* If we don't have a constant length for the first, use the length
4352 of the second, if we know it. We don't require a constant for
4353 this case; some cost analysis could be done if both are available
4354 but neither is constant. For now, assume they're equally cheap,
4355 unless one has side effects. If both strings have constant lengths,
4356 use the smaller. */
4358 if (!len1)
4359 len = len2;
4360 else if (!len2)
4361 len = len1;
4362 else if (TREE_SIDE_EFFECTS (len1))
4363 len = len2;
4364 else if (TREE_SIDE_EFFECTS (len2))
4365 len = len1;
4366 else if (TREE_CODE (len1) != INTEGER_CST)
4367 len = len2;
4368 else if (TREE_CODE (len2) != INTEGER_CST)
4369 len = len1;
4370 else if (tree_int_cst_lt (len1, len2))
4371 len = len1;
4372 else
4373 len = len2;
4375 /* If both arguments have side effects, we cannot optimize. */
4376 if (!len || TREE_SIDE_EFFECTS (len))
4377 return NULL_RTX;
4379 /* The actual new length parameter is MIN(len,arg3). */
4380 len = fold_build2 (MIN_EXPR, TREE_TYPE (len), len,
4381 fold_convert (TREE_TYPE (len), arg3));
4383 /* If we don't have POINTER_TYPE, call the function. */
4384 if (arg1_align == 0 || arg2_align == 0)
4385 return NULL_RTX;
4387 /* Make a place to write the result of the instruction. */
4388 result = target;
4389 if (! (result != 0
4390 && REG_P (result) && GET_MODE (result) == insn_mode
4391 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4392 result = gen_reg_rtx (insn_mode);
4394 /* Stabilize the arguments in case gen_cmpstrnsi fails. */
4395 arg1 = builtin_save_expr (arg1);
4396 arg2 = builtin_save_expr (arg2);
4397 len = builtin_save_expr (len);
4399 arg1_rtx = get_memory_rtx (arg1, len);
4400 arg2_rtx = get_memory_rtx (arg2, len);
4401 arg3_rtx = expand_normal (len);
4402 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4403 GEN_INT (MIN (arg1_align, arg2_align)));
4404 if (insn)
4406 emit_insn (insn);
4408 /* Return the value in the proper mode for this function. */
4409 mode = TYPE_MODE (TREE_TYPE (exp));
4410 if (GET_MODE (result) == mode)
4411 return result;
4412 if (target == 0)
4413 return convert_to_mode (mode, result, 0);
4414 convert_move (target, result, 0);
4415 return target;
4418 /* Expand the library call ourselves using a stabilized argument
4419 list to avoid re-evaluating the function's arguments twice. */
4420 fndecl = get_callee_fndecl (exp);
4421 fn = build_call_expr (fndecl, 3, arg1, arg2, len);
4422 if (TREE_CODE (fn) == CALL_EXPR)
4423 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
4424 return expand_call (fn, target, target == const0_rtx);
4426 #endif
4427 return NULL_RTX;
4430 /* Expand expression EXP, which is a call to the strcat builtin.
4431 Return NULL_RTX if we failed the caller should emit a normal call,
4432 otherwise try to get the result in TARGET, if convenient. */
4434 static rtx
4435 expand_builtin_strcat (tree fndecl, tree exp, rtx target, enum machine_mode mode)
4437 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4438 return NULL_RTX;
4439 else
4441 tree dst = CALL_EXPR_ARG (exp, 0);
4442 tree src = CALL_EXPR_ARG (exp, 1);
4443 const char *p = c_getstr (src);
4445 /* If the string length is zero, return the dst parameter. */
4446 if (p && *p == '\0')
4447 return expand_expr (dst, target, mode, EXPAND_NORMAL);
4449 if (!optimize_size)
4451 /* See if we can store by pieces into (dst + strlen(dst)). */
4452 tree newsrc, newdst,
4453 strlen_fn = implicit_built_in_decls[BUILT_IN_STRLEN];
4454 rtx insns;
4456 /* Stabilize the argument list. */
4457 newsrc = builtin_save_expr (src);
4458 dst = builtin_save_expr (dst);
4460 start_sequence ();
4462 /* Create strlen (dst). */
4463 newdst = build_call_expr (strlen_fn, 1, dst);
4464 /* Create (dst p+ strlen (dst)). */
4466 newdst = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (dst), dst, newdst);
4467 newdst = builtin_save_expr (newdst);
4469 if (!expand_builtin_strcpy_args (fndecl, newdst, newsrc, target, mode))
4471 end_sequence (); /* Stop sequence. */
4472 return NULL_RTX;
4475 /* Output the entire sequence. */
4476 insns = get_insns ();
4477 end_sequence ();
4478 emit_insn (insns);
4480 return expand_expr (dst, target, mode, EXPAND_NORMAL);
4483 return NULL_RTX;
4487 /* Expand expression EXP, which is a call to the strncat builtin.
4488 Return NULL_RTX if we failed the caller should emit a normal call,
4489 otherwise try to get the result in TARGET, if convenient. */
4491 static rtx
4492 expand_builtin_strncat (tree exp, rtx target, enum machine_mode mode)
4494 if (validate_arglist (exp,
4495 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4497 tree result = fold_builtin_strncat (CALL_EXPR_ARG (exp, 0),
4498 CALL_EXPR_ARG (exp, 1),
4499 CALL_EXPR_ARG (exp, 2));
4500 if (result)
4501 return expand_expr (result, target, mode, EXPAND_NORMAL);
4503 return NULL_RTX;
4506 /* Expand expression EXP, which is a call to the strspn builtin.
4507 Return NULL_RTX if we failed the caller should emit a normal call,
4508 otherwise try to get the result in TARGET, if convenient. */
4510 static rtx
4511 expand_builtin_strspn (tree exp, rtx target, enum machine_mode mode)
4513 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4515 tree result = fold_builtin_strspn (CALL_EXPR_ARG (exp, 0),
4516 CALL_EXPR_ARG (exp, 1));
4517 if (result)
4518 return expand_expr (result, target, mode, EXPAND_NORMAL);
4520 return NULL_RTX;
4523 /* Expand expression EXP, which is a call to the strcspn builtin.
4524 Return NULL_RTX if we failed the caller should emit a normal call,
4525 otherwise try to get the result in TARGET, if convenient. */
4527 static rtx
4528 expand_builtin_strcspn (tree exp, rtx target, enum machine_mode mode)
4530 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4532 tree result = fold_builtin_strcspn (CALL_EXPR_ARG (exp, 0),
4533 CALL_EXPR_ARG (exp, 1));
4534 if (result)
4535 return expand_expr (result, target, mode, EXPAND_NORMAL);
4537 return NULL_RTX;
4540 /* Expand a call to __builtin_saveregs, generating the result in TARGET,
4541 if that's convenient. */
4544 expand_builtin_saveregs (void)
4546 rtx val, seq;
4548 /* Don't do __builtin_saveregs more than once in a function.
4549 Save the result of the first call and reuse it. */
4550 if (saveregs_value != 0)
4551 return saveregs_value;
4553 /* When this function is called, it means that registers must be
4554 saved on entry to this function. So we migrate the call to the
4555 first insn of this function. */
4557 start_sequence ();
4559 /* Do whatever the machine needs done in this case. */
4560 val = targetm.calls.expand_builtin_saveregs ();
4562 seq = get_insns ();
4563 end_sequence ();
4565 saveregs_value = val;
4567 /* Put the insns after the NOTE that starts the function. If this
4568 is inside a start_sequence, make the outer-level insn chain current, so
4569 the code is placed at the start of the function. */
4570 push_topmost_sequence ();
4571 emit_insn_after (seq, entry_of_function ());
4572 pop_topmost_sequence ();
4574 return val;
4577 /* __builtin_args_info (N) returns word N of the arg space info
4578 for the current function. The number and meanings of words
4579 is controlled by the definition of CUMULATIVE_ARGS. */
4581 static rtx
4582 expand_builtin_args_info (tree exp)
4584 int nwords = sizeof (CUMULATIVE_ARGS) / sizeof (int);
4585 int *word_ptr = (int *) &current_function_args_info;
4587 gcc_assert (sizeof (CUMULATIVE_ARGS) % sizeof (int) == 0);
4589 if (call_expr_nargs (exp) != 0)
4591 if (!host_integerp (CALL_EXPR_ARG (exp, 0), 0))
4592 error ("argument of %<__builtin_args_info%> must be constant");
4593 else
4595 HOST_WIDE_INT wordnum = tree_low_cst (CALL_EXPR_ARG (exp, 0), 0);
4597 if (wordnum < 0 || wordnum >= nwords)
4598 error ("argument of %<__builtin_args_info%> out of range");
4599 else
4600 return GEN_INT (word_ptr[wordnum]);
4603 else
4604 error ("missing argument in %<__builtin_args_info%>");
4606 return const0_rtx;
4609 /* Expand a call to __builtin_next_arg. */
4611 static rtx
4612 expand_builtin_next_arg (void)
4614 /* Checking arguments is already done in fold_builtin_next_arg
4615 that must be called before this function. */
4616 return expand_binop (ptr_mode, add_optab,
4617 current_function_internal_arg_pointer,
4618 current_function_arg_offset_rtx,
4619 NULL_RTX, 0, OPTAB_LIB_WIDEN);
4622 /* Make it easier for the backends by protecting the valist argument
4623 from multiple evaluations. */
4625 static tree
4626 stabilize_va_list (tree valist, int needs_lvalue)
4628 if (TREE_CODE (va_list_type_node) == ARRAY_TYPE)
4630 if (TREE_SIDE_EFFECTS (valist))
4631 valist = save_expr (valist);
4633 /* For this case, the backends will be expecting a pointer to
4634 TREE_TYPE (va_list_type_node), but it's possible we've
4635 actually been given an array (an actual va_list_type_node).
4636 So fix it. */
4637 if (TREE_CODE (TREE_TYPE (valist)) == ARRAY_TYPE)
4639 tree p1 = build_pointer_type (TREE_TYPE (va_list_type_node));
4640 valist = build_fold_addr_expr_with_type (valist, p1);
4643 else
4645 tree pt;
4647 if (! needs_lvalue)
4649 if (! TREE_SIDE_EFFECTS (valist))
4650 return valist;
4652 pt = build_pointer_type (va_list_type_node);
4653 valist = fold_build1 (ADDR_EXPR, pt, valist);
4654 TREE_SIDE_EFFECTS (valist) = 1;
4657 if (TREE_SIDE_EFFECTS (valist))
4658 valist = save_expr (valist);
4659 valist = build_fold_indirect_ref (valist);
4662 return valist;
4665 /* The "standard" definition of va_list is void*. */
4667 tree
4668 std_build_builtin_va_list (void)
4670 return ptr_type_node;
4673 /* The "standard" implementation of va_start: just assign `nextarg' to
4674 the variable. */
4676 void
4677 std_expand_builtin_va_start (tree valist, rtx nextarg)
4679 rtx va_r = expand_expr (valist, NULL_RTX, VOIDmode, EXPAND_WRITE);
4680 convert_move (va_r, nextarg, 0);
4683 /* Expand EXP, a call to __builtin_va_start. */
4685 static rtx
4686 expand_builtin_va_start (tree exp)
4688 rtx nextarg;
4689 tree valist;
4691 if (call_expr_nargs (exp) < 2)
4693 error ("too few arguments to function %<va_start%>");
4694 return const0_rtx;
4697 if (fold_builtin_next_arg (exp, true))
4698 return const0_rtx;
4700 nextarg = expand_builtin_next_arg ();
4701 valist = stabilize_va_list (CALL_EXPR_ARG (exp, 0), 1);
4703 #ifdef EXPAND_BUILTIN_VA_START
4704 EXPAND_BUILTIN_VA_START (valist, nextarg);
4705 #else
4706 std_expand_builtin_va_start (valist, nextarg);
4707 #endif
4709 return const0_rtx;
4712 /* The "standard" implementation of va_arg: read the value from the
4713 current (padded) address and increment by the (padded) size. */
4715 tree
4716 std_gimplify_va_arg_expr (tree valist, tree type, tree *pre_p, tree *post_p)
4718 tree addr, t, type_size, rounded_size, valist_tmp;
4719 unsigned HOST_WIDE_INT align, boundary;
4720 bool indirect;
4722 #ifdef ARGS_GROW_DOWNWARD
4723 /* All of the alignment and movement below is for args-grow-up machines.
4724 As of 2004, there are only 3 ARGS_GROW_DOWNWARD targets, and they all
4725 implement their own specialized gimplify_va_arg_expr routines. */
4726 gcc_unreachable ();
4727 #endif
4729 indirect = pass_by_reference (NULL, TYPE_MODE (type), type, false);
4730 if (indirect)
4731 type = build_pointer_type (type);
4733 align = PARM_BOUNDARY / BITS_PER_UNIT;
4734 boundary = FUNCTION_ARG_BOUNDARY (TYPE_MODE (type), type) / BITS_PER_UNIT;
4736 /* Hoist the valist value into a temporary for the moment. */
4737 valist_tmp = get_initialized_tmp_var (valist, pre_p, NULL);
4739 /* va_list pointer is aligned to PARM_BOUNDARY. If argument actually
4740 requires greater alignment, we must perform dynamic alignment. */
4741 if (boundary > align
4742 && !integer_zerop (TYPE_SIZE (type)))
4744 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
4745 fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (valist),
4746 valist_tmp, size_int (boundary - 1)));
4747 gimplify_and_add (t, pre_p);
4749 t = fold_convert (sizetype, valist_tmp);
4750 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
4751 fold_convert (TREE_TYPE (valist),
4752 fold_build2 (BIT_AND_EXPR, sizetype, t,
4753 size_int (-boundary))));
4754 gimplify_and_add (t, pre_p);
4756 else
4757 boundary = align;
4759 /* If the actual alignment is less than the alignment of the type,
4760 adjust the type accordingly so that we don't assume strict alignment
4761 when deferencing the pointer. */
4762 boundary *= BITS_PER_UNIT;
4763 if (boundary < TYPE_ALIGN (type))
4765 type = build_variant_type_copy (type);
4766 TYPE_ALIGN (type) = boundary;
4769 /* Compute the rounded size of the type. */
4770 type_size = size_in_bytes (type);
4771 rounded_size = round_up (type_size, align);
4773 /* Reduce rounded_size so it's sharable with the postqueue. */
4774 gimplify_expr (&rounded_size, pre_p, post_p, is_gimple_val, fb_rvalue);
4776 /* Get AP. */
4777 addr = valist_tmp;
4778 if (PAD_VARARGS_DOWN && !integer_zerop (rounded_size))
4780 /* Small args are padded downward. */
4781 t = fold_build2 (GT_EXPR, sizetype, rounded_size, size_int (align));
4782 t = fold_build3 (COND_EXPR, sizetype, t, size_zero_node,
4783 size_binop (MINUS_EXPR, rounded_size, type_size));
4784 addr = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (addr), addr, t);
4787 /* Compute new value for AP. */
4788 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (valist), valist_tmp, rounded_size);
4789 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
4790 gimplify_and_add (t, pre_p);
4792 addr = fold_convert (build_pointer_type (type), addr);
4794 if (indirect)
4795 addr = build_va_arg_indirect_ref (addr);
4797 return build_va_arg_indirect_ref (addr);
4800 /* Build an indirect-ref expression over the given TREE, which represents a
4801 piece of a va_arg() expansion. */
4802 tree
4803 build_va_arg_indirect_ref (tree addr)
4805 addr = build_fold_indirect_ref (addr);
4807 if (flag_mudflap) /* Don't instrument va_arg INDIRECT_REF. */
4808 mf_mark (addr);
4810 return addr;
4813 /* Return a dummy expression of type TYPE in order to keep going after an
4814 error. */
4816 static tree
4817 dummy_object (tree type)
4819 tree t = build_int_cst (build_pointer_type (type), 0);
4820 return build1 (INDIRECT_REF, type, t);
4823 /* Gimplify __builtin_va_arg, aka VA_ARG_EXPR, which is not really a
4824 builtin function, but a very special sort of operator. */
4826 enum gimplify_status
4827 gimplify_va_arg_expr (tree *expr_p, tree *pre_p, tree *post_p)
4829 tree promoted_type, want_va_type, have_va_type;
4830 tree valist = TREE_OPERAND (*expr_p, 0);
4831 tree type = TREE_TYPE (*expr_p);
4832 tree t;
4834 /* Verify that valist is of the proper type. */
4835 want_va_type = va_list_type_node;
4836 have_va_type = TREE_TYPE (valist);
4838 if (have_va_type == error_mark_node)
4839 return GS_ERROR;
4841 if (TREE_CODE (want_va_type) == ARRAY_TYPE)
4843 /* If va_list is an array type, the argument may have decayed
4844 to a pointer type, e.g. by being passed to another function.
4845 In that case, unwrap both types so that we can compare the
4846 underlying records. */
4847 if (TREE_CODE (have_va_type) == ARRAY_TYPE
4848 || POINTER_TYPE_P (have_va_type))
4850 want_va_type = TREE_TYPE (want_va_type);
4851 have_va_type = TREE_TYPE (have_va_type);
4855 if (TYPE_MAIN_VARIANT (want_va_type) != TYPE_MAIN_VARIANT (have_va_type))
4857 error ("first argument to %<va_arg%> not of type %<va_list%>");
4858 return GS_ERROR;
4861 /* Generate a diagnostic for requesting data of a type that cannot
4862 be passed through `...' due to type promotion at the call site. */
4863 else if ((promoted_type = lang_hooks.types.type_promotes_to (type))
4864 != type)
4866 static bool gave_help;
4868 /* Unfortunately, this is merely undefined, rather than a constraint
4869 violation, so we cannot make this an error. If this call is never
4870 executed, the program is still strictly conforming. */
4871 warning (0, "%qT is promoted to %qT when passed through %<...%>",
4872 type, promoted_type);
4873 if (! gave_help)
4875 gave_help = true;
4876 warning (0, "(so you should pass %qT not %qT to %<va_arg%>)",
4877 promoted_type, type);
4880 /* We can, however, treat "undefined" any way we please.
4881 Call abort to encourage the user to fix the program. */
4882 inform ("if this code is reached, the program will abort");
4883 t = build_call_expr (implicit_built_in_decls[BUILT_IN_TRAP], 0);
4884 append_to_statement_list (t, pre_p);
4886 /* This is dead code, but go ahead and finish so that the
4887 mode of the result comes out right. */
4888 *expr_p = dummy_object (type);
4889 return GS_ALL_DONE;
4891 else
4893 /* Make it easier for the backends by protecting the valist argument
4894 from multiple evaluations. */
4895 if (TREE_CODE (va_list_type_node) == ARRAY_TYPE)
4897 /* For this case, the backends will be expecting a pointer to
4898 TREE_TYPE (va_list_type_node), but it's possible we've
4899 actually been given an array (an actual va_list_type_node).
4900 So fix it. */
4901 if (TREE_CODE (TREE_TYPE (valist)) == ARRAY_TYPE)
4903 tree p1 = build_pointer_type (TREE_TYPE (va_list_type_node));
4904 valist = build_fold_addr_expr_with_type (valist, p1);
4906 gimplify_expr (&valist, pre_p, post_p, is_gimple_val, fb_rvalue);
4908 else
4909 gimplify_expr (&valist, pre_p, post_p, is_gimple_min_lval, fb_lvalue);
4911 if (!targetm.gimplify_va_arg_expr)
4912 /* FIXME:Once most targets are converted we should merely
4913 assert this is non-null. */
4914 return GS_ALL_DONE;
4916 *expr_p = targetm.gimplify_va_arg_expr (valist, type, pre_p, post_p);
4917 return GS_OK;
4921 /* Expand EXP, a call to __builtin_va_end. */
4923 static rtx
4924 expand_builtin_va_end (tree exp)
4926 tree valist = CALL_EXPR_ARG (exp, 0);
4928 /* Evaluate for side effects, if needed. I hate macros that don't
4929 do that. */
4930 if (TREE_SIDE_EFFECTS (valist))
4931 expand_expr (valist, const0_rtx, VOIDmode, EXPAND_NORMAL);
4933 return const0_rtx;
4936 /* Expand EXP, a call to __builtin_va_copy. We do this as a
4937 builtin rather than just as an assignment in stdarg.h because of the
4938 nastiness of array-type va_list types. */
4940 static rtx
4941 expand_builtin_va_copy (tree exp)
4943 tree dst, src, t;
4945 dst = CALL_EXPR_ARG (exp, 0);
4946 src = CALL_EXPR_ARG (exp, 1);
4948 dst = stabilize_va_list (dst, 1);
4949 src = stabilize_va_list (src, 0);
4951 if (TREE_CODE (va_list_type_node) != ARRAY_TYPE)
4953 t = build2 (MODIFY_EXPR, va_list_type_node, dst, src);
4954 TREE_SIDE_EFFECTS (t) = 1;
4955 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4957 else
4959 rtx dstb, srcb, size;
4961 /* Evaluate to pointers. */
4962 dstb = expand_expr (dst, NULL_RTX, Pmode, EXPAND_NORMAL);
4963 srcb = expand_expr (src, NULL_RTX, Pmode, EXPAND_NORMAL);
4964 size = expand_expr (TYPE_SIZE_UNIT (va_list_type_node), NULL_RTX,
4965 VOIDmode, EXPAND_NORMAL);
4967 dstb = convert_memory_address (Pmode, dstb);
4968 srcb = convert_memory_address (Pmode, srcb);
4970 /* "Dereference" to BLKmode memories. */
4971 dstb = gen_rtx_MEM (BLKmode, dstb);
4972 set_mem_alias_set (dstb, get_alias_set (TREE_TYPE (TREE_TYPE (dst))));
4973 set_mem_align (dstb, TYPE_ALIGN (va_list_type_node));
4974 srcb = gen_rtx_MEM (BLKmode, srcb);
4975 set_mem_alias_set (srcb, get_alias_set (TREE_TYPE (TREE_TYPE (src))));
4976 set_mem_align (srcb, TYPE_ALIGN (va_list_type_node));
4978 /* Copy. */
4979 emit_block_move (dstb, srcb, size, BLOCK_OP_NORMAL);
4982 return const0_rtx;
4985 /* Expand a call to one of the builtin functions __builtin_frame_address or
4986 __builtin_return_address. */
4988 static rtx
4989 expand_builtin_frame_address (tree fndecl, tree exp)
4991 /* The argument must be a nonnegative integer constant.
4992 It counts the number of frames to scan up the stack.
4993 The value is the return address saved in that frame. */
4994 if (call_expr_nargs (exp) == 0)
4995 /* Warning about missing arg was already issued. */
4996 return const0_rtx;
4997 else if (! host_integerp (CALL_EXPR_ARG (exp, 0), 1))
4999 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
5000 error ("invalid argument to %<__builtin_frame_address%>");
5001 else
5002 error ("invalid argument to %<__builtin_return_address%>");
5003 return const0_rtx;
5005 else
5007 rtx tem
5008 = expand_builtin_return_addr (DECL_FUNCTION_CODE (fndecl),
5009 tree_low_cst (CALL_EXPR_ARG (exp, 0), 1));
5011 /* Some ports cannot access arbitrary stack frames. */
5012 if (tem == NULL)
5014 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
5015 warning (0, "unsupported argument to %<__builtin_frame_address%>");
5016 else
5017 warning (0, "unsupported argument to %<__builtin_return_address%>");
5018 return const0_rtx;
5021 /* For __builtin_frame_address, return what we've got. */
5022 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
5023 return tem;
5025 if (!REG_P (tem)
5026 && ! CONSTANT_P (tem))
5027 tem = copy_to_mode_reg (Pmode, tem);
5028 return tem;
5032 /* Expand EXP, a call to the alloca builtin. Return NULL_RTX if
5033 we failed and the caller should emit a normal call, otherwise try to get
5034 the result in TARGET, if convenient. */
5036 static rtx
5037 expand_builtin_alloca (tree exp, rtx target)
5039 rtx op0;
5040 rtx result;
5042 /* In -fmudflap-instrumented code, alloca() and __builtin_alloca()
5043 should always expand to function calls. These can be intercepted
5044 in libmudflap. */
5045 if (flag_mudflap)
5046 return NULL_RTX;
5048 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
5049 return NULL_RTX;
5051 /* Compute the argument. */
5052 op0 = expand_normal (CALL_EXPR_ARG (exp, 0));
5054 /* Allocate the desired space. */
5055 result = allocate_dynamic_stack_space (op0, target, BITS_PER_UNIT);
5056 result = convert_memory_address (ptr_mode, result);
5058 return result;
5061 /* Expand a call to a bswap builtin with argument ARG0. MODE
5062 is the mode to expand with. */
5064 static rtx
5065 expand_builtin_bswap (tree exp, rtx target, rtx subtarget)
5067 enum machine_mode mode;
5068 tree arg;
5069 rtx op0;
5071 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
5072 return NULL_RTX;
5074 arg = CALL_EXPR_ARG (exp, 0);
5075 mode = TYPE_MODE (TREE_TYPE (arg));
5076 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
5078 target = expand_unop (mode, bswap_optab, op0, target, 1);
5080 gcc_assert (target);
5082 return convert_to_mode (mode, target, 0);
5085 /* Expand a call to a unary builtin in EXP.
5086 Return NULL_RTX if a normal call should be emitted rather than expanding the
5087 function in-line. If convenient, the result should be placed in TARGET.
5088 SUBTARGET may be used as the target for computing one of EXP's operands. */
5090 static rtx
5091 expand_builtin_unop (enum machine_mode target_mode, tree exp, rtx target,
5092 rtx subtarget, optab op_optab)
5094 rtx op0;
5096 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
5097 return NULL_RTX;
5099 /* Compute the argument. */
5100 op0 = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
5101 VOIDmode, EXPAND_NORMAL);
5102 /* Compute op, into TARGET if possible.
5103 Set TARGET to wherever the result comes back. */
5104 target = expand_unop (TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 0))),
5105 op_optab, op0, target, 1);
5106 gcc_assert (target);
5108 return convert_to_mode (target_mode, target, 0);
5111 /* If the string passed to fputs is a constant and is one character
5112 long, we attempt to transform this call into __builtin_fputc(). */
5114 static rtx
5115 expand_builtin_fputs (tree exp, rtx target, bool unlocked)
5117 /* Verify the arguments in the original call. */
5118 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
5120 tree result = fold_builtin_fputs (CALL_EXPR_ARG (exp, 0),
5121 CALL_EXPR_ARG (exp, 1),
5122 (target == const0_rtx),
5123 unlocked, NULL_TREE);
5124 if (result)
5125 return expand_expr (result, target, VOIDmode, EXPAND_NORMAL);
5127 return NULL_RTX;
5130 /* Expand a call to __builtin_expect. We just return our argument
5131 as the builtin_expect semantic should've been already executed by
5132 tree branch prediction pass. */
5134 static rtx
5135 expand_builtin_expect (tree exp, rtx target)
5137 tree arg, c;
5139 if (call_expr_nargs (exp) < 2)
5140 return const0_rtx;
5141 arg = CALL_EXPR_ARG (exp, 0);
5142 c = CALL_EXPR_ARG (exp, 1);
5144 target = expand_expr (arg, target, VOIDmode, EXPAND_NORMAL);
5145 /* When guessing was done, the hints should be already stripped away. */
5146 gcc_assert (!flag_guess_branch_prob
5147 || optimize == 0 || errorcount || sorrycount);
5148 return target;
5151 void
5152 expand_builtin_trap (void)
5154 #ifdef HAVE_trap
5155 if (HAVE_trap)
5156 emit_insn (gen_trap ());
5157 else
5158 #endif
5159 emit_library_call (abort_libfunc, LCT_NORETURN, VOIDmode, 0);
5160 emit_barrier ();
5163 /* Expand EXP, a call to fabs, fabsf or fabsl.
5164 Return NULL_RTX if a normal call should be emitted rather than expanding
5165 the function inline. If convenient, the result should be placed
5166 in TARGET. SUBTARGET may be used as the target for computing
5167 the operand. */
5169 static rtx
5170 expand_builtin_fabs (tree exp, rtx target, rtx subtarget)
5172 enum machine_mode mode;
5173 tree arg;
5174 rtx op0;
5176 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
5177 return NULL_RTX;
5179 arg = CALL_EXPR_ARG (exp, 0);
5180 mode = TYPE_MODE (TREE_TYPE (arg));
5181 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
5182 return expand_abs (mode, op0, target, 0, safe_from_p (target, arg, 1));
5185 /* Expand EXP, a call to copysign, copysignf, or copysignl.
5186 Return NULL is a normal call should be emitted rather than expanding the
5187 function inline. If convenient, the result should be placed in TARGET.
5188 SUBTARGET may be used as the target for computing the operand. */
5190 static rtx
5191 expand_builtin_copysign (tree exp, rtx target, rtx subtarget)
5193 rtx op0, op1;
5194 tree arg;
5196 if (!validate_arglist (exp, REAL_TYPE, REAL_TYPE, VOID_TYPE))
5197 return NULL_RTX;
5199 arg = CALL_EXPR_ARG (exp, 0);
5200 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
5202 arg = CALL_EXPR_ARG (exp, 1);
5203 op1 = expand_normal (arg);
5205 return expand_copysign (op0, op1, target);
5208 /* Create a new constant string literal and return a char* pointer to it.
5209 The STRING_CST value is the LEN characters at STR. */
5210 tree
5211 build_string_literal (int len, const char *str)
5213 tree t, elem, index, type;
5215 t = build_string (len, str);
5216 elem = build_type_variant (char_type_node, 1, 0);
5217 index = build_index_type (build_int_cst (NULL_TREE, len - 1));
5218 type = build_array_type (elem, index);
5219 TREE_TYPE (t) = type;
5220 TREE_CONSTANT (t) = 1;
5221 TREE_INVARIANT (t) = 1;
5222 TREE_READONLY (t) = 1;
5223 TREE_STATIC (t) = 1;
5225 type = build_pointer_type (type);
5226 t = build1 (ADDR_EXPR, type, t);
5228 type = build_pointer_type (elem);
5229 t = build1 (NOP_EXPR, type, t);
5230 return t;
5233 /* Expand EXP, a call to printf or printf_unlocked.
5234 Return NULL_RTX if a normal call should be emitted rather than transforming
5235 the function inline. If convenient, the result should be placed in
5236 TARGET with mode MODE. UNLOCKED indicates this is a printf_unlocked
5237 call. */
5238 static rtx
5239 expand_builtin_printf (tree exp, rtx target, enum machine_mode mode,
5240 bool unlocked)
5242 /* If we're using an unlocked function, assume the other unlocked
5243 functions exist explicitly. */
5244 tree const fn_putchar = unlocked ? built_in_decls[BUILT_IN_PUTCHAR_UNLOCKED]
5245 : implicit_built_in_decls[BUILT_IN_PUTCHAR];
5246 tree const fn_puts = unlocked ? built_in_decls[BUILT_IN_PUTS_UNLOCKED]
5247 : implicit_built_in_decls[BUILT_IN_PUTS];
5248 const char *fmt_str;
5249 tree fn = 0;
5250 tree fmt, arg;
5251 int nargs = call_expr_nargs (exp);
5253 /* If the return value is used, don't do the transformation. */
5254 if (target != const0_rtx)
5255 return NULL_RTX;
5257 /* Verify the required arguments in the original call. */
5258 if (nargs == 0)
5259 return NULL_RTX;
5260 fmt = CALL_EXPR_ARG (exp, 0);
5261 if (! POINTER_TYPE_P (TREE_TYPE (fmt)))
5262 return NULL_RTX;
5264 /* Check whether the format is a literal string constant. */
5265 fmt_str = c_getstr (fmt);
5266 if (fmt_str == NULL)
5267 return NULL_RTX;
5269 if (!init_target_chars ())
5270 return NULL_RTX;
5272 /* If the format specifier was "%s\n", call __builtin_puts(arg). */
5273 if (strcmp (fmt_str, target_percent_s_newline) == 0)
5275 if ((nargs != 2)
5276 || ! POINTER_TYPE_P (TREE_TYPE (CALL_EXPR_ARG (exp, 1))))
5277 return NULL_RTX;
5278 if (fn_puts)
5279 fn = build_call_expr (fn_puts, 1, CALL_EXPR_ARG (exp, 1));
5281 /* If the format specifier was "%c", call __builtin_putchar(arg). */
5282 else if (strcmp (fmt_str, target_percent_c) == 0)
5284 if ((nargs != 2)
5285 || TREE_CODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1))) != INTEGER_TYPE)
5286 return NULL_RTX;
5287 if (fn_putchar)
5288 fn = build_call_expr (fn_putchar, 1, CALL_EXPR_ARG (exp, 1));
5290 else
5292 /* We can't handle anything else with % args or %% ... yet. */
5293 if (strchr (fmt_str, target_percent))
5294 return NULL_RTX;
5296 if (nargs > 1)
5297 return NULL_RTX;
5299 /* If the format specifier was "", printf does nothing. */
5300 if (fmt_str[0] == '\0')
5301 return const0_rtx;
5302 /* If the format specifier has length of 1, call putchar. */
5303 if (fmt_str[1] == '\0')
5305 /* Given printf("c"), (where c is any one character,)
5306 convert "c"[0] to an int and pass that to the replacement
5307 function. */
5308 arg = build_int_cst (NULL_TREE, fmt_str[0]);
5309 if (fn_putchar)
5310 fn = build_call_expr (fn_putchar, 1, arg);
5312 else
5314 /* If the format specifier was "string\n", call puts("string"). */
5315 size_t len = strlen (fmt_str);
5316 if ((unsigned char)fmt_str[len - 1] == target_newline)
5318 /* Create a NUL-terminated string that's one char shorter
5319 than the original, stripping off the trailing '\n'. */
5320 char *newstr = alloca (len);
5321 memcpy (newstr, fmt_str, len - 1);
5322 newstr[len - 1] = 0;
5323 arg = build_string_literal (len, newstr);
5324 if (fn_puts)
5325 fn = build_call_expr (fn_puts, 1, arg);
5327 else
5328 /* We'd like to arrange to call fputs(string,stdout) here,
5329 but we need stdout and don't have a way to get it yet. */
5330 return NULL_RTX;
5334 if (!fn)
5335 return NULL_RTX;
5336 if (TREE_CODE (fn) == CALL_EXPR)
5337 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
5338 return expand_expr (fn, target, mode, EXPAND_NORMAL);
5341 /* Expand EXP, a call to fprintf or fprintf_unlocked.
5342 Return NULL_RTX if a normal call should be emitted rather than transforming
5343 the function inline. If convenient, the result should be placed in
5344 TARGET with mode MODE. UNLOCKED indicates this is a fprintf_unlocked
5345 call. */
5346 static rtx
5347 expand_builtin_fprintf (tree exp, rtx target, enum machine_mode mode,
5348 bool unlocked)
5350 /* If we're using an unlocked function, assume the other unlocked
5351 functions exist explicitly. */
5352 tree const fn_fputc = unlocked ? built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
5353 : implicit_built_in_decls[BUILT_IN_FPUTC];
5354 tree const fn_fputs = unlocked ? built_in_decls[BUILT_IN_FPUTS_UNLOCKED]
5355 : implicit_built_in_decls[BUILT_IN_FPUTS];
5356 const char *fmt_str;
5357 tree fn = 0;
5358 tree fmt, fp, arg;
5359 int nargs = call_expr_nargs (exp);
5361 /* If the return value is used, don't do the transformation. */
5362 if (target != const0_rtx)
5363 return NULL_RTX;
5365 /* Verify the required arguments in the original call. */
5366 if (nargs < 2)
5367 return NULL_RTX;
5368 fp = CALL_EXPR_ARG (exp, 0);
5369 if (! POINTER_TYPE_P (TREE_TYPE (fp)))
5370 return NULL_RTX;
5371 fmt = CALL_EXPR_ARG (exp, 1);
5372 if (! POINTER_TYPE_P (TREE_TYPE (fmt)))
5373 return NULL_RTX;
5375 /* Check whether the format is a literal string constant. */
5376 fmt_str = c_getstr (fmt);
5377 if (fmt_str == NULL)
5378 return NULL_RTX;
5380 if (!init_target_chars ())
5381 return NULL_RTX;
5383 /* If the format specifier was "%s", call __builtin_fputs(arg,fp). */
5384 if (strcmp (fmt_str, target_percent_s) == 0)
5386 if ((nargs != 3)
5387 || ! POINTER_TYPE_P (TREE_TYPE (CALL_EXPR_ARG (exp, 2))))
5388 return NULL_RTX;
5389 arg = CALL_EXPR_ARG (exp, 2);
5390 if (fn_fputs)
5391 fn = build_call_expr (fn_fputs, 2, arg, fp);
5393 /* If the format specifier was "%c", call __builtin_fputc(arg,fp). */
5394 else if (strcmp (fmt_str, target_percent_c) == 0)
5396 if ((nargs != 3)
5397 || TREE_CODE (TREE_TYPE (CALL_EXPR_ARG (exp, 2))) != INTEGER_TYPE)
5398 return NULL_RTX;
5399 arg = CALL_EXPR_ARG (exp, 2);
5400 if (fn_fputc)
5401 fn = build_call_expr (fn_fputc, 2, arg, fp);
5403 else
5405 /* We can't handle anything else with % args or %% ... yet. */
5406 if (strchr (fmt_str, target_percent))
5407 return NULL_RTX;
5409 if (nargs > 2)
5410 return NULL_RTX;
5412 /* If the format specifier was "", fprintf does nothing. */
5413 if (fmt_str[0] == '\0')
5415 /* Evaluate and ignore FILE* argument for side-effects. */
5416 expand_expr (fp, const0_rtx, VOIDmode, EXPAND_NORMAL);
5417 return const0_rtx;
5420 /* When "string" doesn't contain %, replace all cases of
5421 fprintf(stream,string) with fputs(string,stream). The fputs
5422 builtin will take care of special cases like length == 1. */
5423 if (fn_fputs)
5424 fn = build_call_expr (fn_fputs, 2, fmt, fp);
5427 if (!fn)
5428 return NULL_RTX;
5429 if (TREE_CODE (fn) == CALL_EXPR)
5430 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
5431 return expand_expr (fn, target, mode, EXPAND_NORMAL);
5434 /* Expand a call EXP to sprintf. Return NULL_RTX if
5435 a normal call should be emitted rather than expanding the function
5436 inline. If convenient, the result should be placed in TARGET with
5437 mode MODE. */
5439 static rtx
5440 expand_builtin_sprintf (tree exp, rtx target, enum machine_mode mode)
5442 tree dest, fmt;
5443 const char *fmt_str;
5444 int nargs = call_expr_nargs (exp);
5446 /* Verify the required arguments in the original call. */
5447 if (nargs < 2)
5448 return NULL_RTX;
5449 dest = CALL_EXPR_ARG (exp, 0);
5450 if (! POINTER_TYPE_P (TREE_TYPE (dest)))
5451 return NULL_RTX;
5452 fmt = CALL_EXPR_ARG (exp, 0);
5453 if (! POINTER_TYPE_P (TREE_TYPE (fmt)))
5454 return NULL_RTX;
5456 /* Check whether the format is a literal string constant. */
5457 fmt_str = c_getstr (fmt);
5458 if (fmt_str == NULL)
5459 return NULL_RTX;
5461 if (!init_target_chars ())
5462 return NULL_RTX;
5464 /* If the format doesn't contain % args or %%, use strcpy. */
5465 if (strchr (fmt_str, target_percent) == 0)
5467 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
5468 tree exp;
5470 if ((nargs > 2) || ! fn)
5471 return NULL_RTX;
5472 expand_expr (build_call_expr (fn, 2, dest, fmt),
5473 const0_rtx, VOIDmode, EXPAND_NORMAL);
5474 if (target == const0_rtx)
5475 return const0_rtx;
5476 exp = build_int_cst (NULL_TREE, strlen (fmt_str));
5477 return expand_expr (exp, target, mode, EXPAND_NORMAL);
5479 /* If the format is "%s", use strcpy if the result isn't used. */
5480 else if (strcmp (fmt_str, target_percent_s) == 0)
5482 tree fn, arg, len;
5483 fn = implicit_built_in_decls[BUILT_IN_STRCPY];
5485 if (! fn)
5486 return NULL_RTX;
5487 if (nargs != 3)
5488 return NULL_RTX;
5489 arg = CALL_EXPR_ARG (exp, 2);
5490 if (! POINTER_TYPE_P (TREE_TYPE (arg)))
5491 return NULL_RTX;
5493 if (target != const0_rtx)
5495 len = c_strlen (arg, 1);
5496 if (! len || TREE_CODE (len) != INTEGER_CST)
5497 return NULL_RTX;
5499 else
5500 len = NULL_TREE;
5502 expand_expr (build_call_expr (fn, 2, dest, arg),
5503 const0_rtx, VOIDmode, EXPAND_NORMAL);
5505 if (target == const0_rtx)
5506 return const0_rtx;
5507 return expand_expr (len, target, mode, EXPAND_NORMAL);
5510 return NULL_RTX;
5513 /* Expand a call to either the entry or exit function profiler. */
5515 static rtx
5516 expand_builtin_profile_func (bool exitp)
5518 rtx this, which;
5520 this = DECL_RTL (current_function_decl);
5521 gcc_assert (MEM_P (this));
5522 this = XEXP (this, 0);
5524 if (exitp)
5525 which = profile_function_exit_libfunc;
5526 else
5527 which = profile_function_entry_libfunc;
5529 emit_library_call (which, LCT_NORMAL, VOIDmode, 2, this, Pmode,
5530 expand_builtin_return_addr (BUILT_IN_RETURN_ADDRESS,
5532 Pmode);
5534 return const0_rtx;
5537 /* Expand a call to __builtin___clear_cache. */
5539 static rtx
5540 expand_builtin___clear_cache (tree exp ATTRIBUTE_UNUSED)
5542 #ifndef HAVE_clear_cache
5543 #ifdef CLEAR_INSN_CACHE
5544 /* There is no "clear_cache" insn, and __clear_cache() in libgcc
5545 does something. Just do the default expansion to a call to
5546 __clear_cache(). */
5547 return NULL_RTX;
5548 #else
5549 /* There is no "clear_cache" insn, and __clear_cache() in libgcc
5550 does nothing. There is no need to call it. Do nothing. */
5551 return const0_rtx;
5552 #endif /* CLEAR_INSN_CACHE */
5553 #else
5554 /* We have a "clear_cache" insn, and it will handle everything. */
5555 tree begin, end;
5556 rtx begin_rtx, end_rtx;
5557 enum insn_code icode;
5559 /* We must not expand to a library call. If we did, any
5560 fallback library function in libgcc that might contain a call to
5561 __builtin___clear_cache() would recurse infinitely. */
5562 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
5564 error ("both arguments to %<__builtin___clear_cache%> must be pointers");
5565 return const0_rtx;
5568 if (HAVE_clear_cache)
5570 icode = CODE_FOR_clear_cache;
5572 begin = CALL_EXPR_ARG (exp, 0);
5573 begin_rtx = expand_expr (begin, NULL_RTX, Pmode, EXPAND_NORMAL);
5574 begin_rtx = convert_memory_address (Pmode, begin_rtx);
5575 if (!insn_data[icode].operand[0].predicate (begin_rtx, Pmode))
5576 begin_rtx = copy_to_mode_reg (Pmode, begin_rtx);
5578 end = CALL_EXPR_ARG (exp, 1);
5579 end_rtx = expand_expr (end, NULL_RTX, Pmode, EXPAND_NORMAL);
5580 end_rtx = convert_memory_address (Pmode, end_rtx);
5581 if (!insn_data[icode].operand[1].predicate (end_rtx, Pmode))
5582 end_rtx = copy_to_mode_reg (Pmode, end_rtx);
5584 emit_insn (gen_clear_cache (begin_rtx, end_rtx));
5586 return const0_rtx;
5587 #endif /* HAVE_clear_cache */
5590 /* Given a trampoline address, make sure it satisfies TRAMPOLINE_ALIGNMENT. */
5592 static rtx
5593 round_trampoline_addr (rtx tramp)
5595 rtx temp, addend, mask;
5597 /* If we don't need too much alignment, we'll have been guaranteed
5598 proper alignment by get_trampoline_type. */
5599 if (TRAMPOLINE_ALIGNMENT <= STACK_BOUNDARY)
5600 return tramp;
5602 /* Round address up to desired boundary. */
5603 temp = gen_reg_rtx (Pmode);
5604 addend = GEN_INT (TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT - 1);
5605 mask = GEN_INT (-TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT);
5607 temp = expand_simple_binop (Pmode, PLUS, tramp, addend,
5608 temp, 0, OPTAB_LIB_WIDEN);
5609 tramp = expand_simple_binop (Pmode, AND, temp, mask,
5610 temp, 0, OPTAB_LIB_WIDEN);
5612 return tramp;
5615 static rtx
5616 expand_builtin_init_trampoline (tree exp)
5618 tree t_tramp, t_func, t_chain;
5619 rtx r_tramp, r_func, r_chain;
5620 #ifdef TRAMPOLINE_TEMPLATE
5621 rtx blktramp;
5622 #endif
5624 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE,
5625 POINTER_TYPE, VOID_TYPE))
5626 return NULL_RTX;
5628 t_tramp = CALL_EXPR_ARG (exp, 0);
5629 t_func = CALL_EXPR_ARG (exp, 1);
5630 t_chain = CALL_EXPR_ARG (exp, 2);
5632 r_tramp = expand_normal (t_tramp);
5633 r_func = expand_normal (t_func);
5634 r_chain = expand_normal (t_chain);
5636 /* Generate insns to initialize the trampoline. */
5637 r_tramp = round_trampoline_addr (r_tramp);
5638 #ifdef TRAMPOLINE_TEMPLATE
5639 blktramp = gen_rtx_MEM (BLKmode, r_tramp);
5640 set_mem_align (blktramp, TRAMPOLINE_ALIGNMENT);
5641 emit_block_move (blktramp, assemble_trampoline_template (),
5642 GEN_INT (TRAMPOLINE_SIZE), BLOCK_OP_NORMAL);
5643 #endif
5644 trampolines_created = 1;
5645 INITIALIZE_TRAMPOLINE (r_tramp, r_func, r_chain);
5647 return const0_rtx;
5650 static rtx
5651 expand_builtin_adjust_trampoline (tree exp)
5653 rtx tramp;
5655 if (!validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
5656 return NULL_RTX;
5658 tramp = expand_normal (CALL_EXPR_ARG (exp, 0));
5659 tramp = round_trampoline_addr (tramp);
5660 #ifdef TRAMPOLINE_ADJUST_ADDRESS
5661 TRAMPOLINE_ADJUST_ADDRESS (tramp);
5662 #endif
5664 return tramp;
5667 /* Expand the call EXP to the built-in signbit, signbitf or signbitl
5668 function. The function first checks whether the back end provides
5669 an insn to implement signbit for the respective mode. If not, it
5670 checks whether the floating point format of the value is such that
5671 the sign bit can be extracted. If that is not the case, the
5672 function returns NULL_RTX to indicate that a normal call should be
5673 emitted rather than expanding the function in-line. EXP is the
5674 expression that is a call to the builtin function; if convenient,
5675 the result should be placed in TARGET. */
5676 static rtx
5677 expand_builtin_signbit (tree exp, rtx target)
5679 const struct real_format *fmt;
5680 enum machine_mode fmode, imode, rmode;
5681 HOST_WIDE_INT hi, lo;
5682 tree arg;
5683 int word, bitpos;
5684 enum insn_code icode;
5685 rtx temp;
5687 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
5688 return NULL_RTX;
5690 arg = CALL_EXPR_ARG (exp, 0);
5691 fmode = TYPE_MODE (TREE_TYPE (arg));
5692 rmode = TYPE_MODE (TREE_TYPE (exp));
5693 fmt = REAL_MODE_FORMAT (fmode);
5695 arg = builtin_save_expr (arg);
5697 /* Expand the argument yielding a RTX expression. */
5698 temp = expand_normal (arg);
5700 /* Check if the back end provides an insn that handles signbit for the
5701 argument's mode. */
5702 icode = signbit_optab->handlers [(int) fmode].insn_code;
5703 if (icode != CODE_FOR_nothing)
5705 target = gen_reg_rtx (TYPE_MODE (TREE_TYPE (exp)));
5706 emit_unop_insn (icode, target, temp, UNKNOWN);
5707 return target;
5710 /* For floating point formats without a sign bit, implement signbit
5711 as "ARG < 0.0". */
5712 bitpos = fmt->signbit_ro;
5713 if (bitpos < 0)
5715 /* But we can't do this if the format supports signed zero. */
5716 if (fmt->has_signed_zero && HONOR_SIGNED_ZEROS (fmode))
5717 return NULL_RTX;
5719 arg = fold_build2 (LT_EXPR, TREE_TYPE (exp), arg,
5720 build_real (TREE_TYPE (arg), dconst0));
5721 return expand_expr (arg, target, VOIDmode, EXPAND_NORMAL);
5724 if (GET_MODE_SIZE (fmode) <= UNITS_PER_WORD)
5726 imode = int_mode_for_mode (fmode);
5727 if (imode == BLKmode)
5728 return NULL_RTX;
5729 temp = gen_lowpart (imode, temp);
5731 else
5733 imode = word_mode;
5734 /* Handle targets with different FP word orders. */
5735 if (FLOAT_WORDS_BIG_ENDIAN)
5736 word = (GET_MODE_BITSIZE (fmode) - bitpos) / BITS_PER_WORD;
5737 else
5738 word = bitpos / BITS_PER_WORD;
5739 temp = operand_subword_force (temp, word, fmode);
5740 bitpos = bitpos % BITS_PER_WORD;
5743 /* Force the intermediate word_mode (or narrower) result into a
5744 register. This avoids attempting to create paradoxical SUBREGs
5745 of floating point modes below. */
5746 temp = force_reg (imode, temp);
5748 /* If the bitpos is within the "result mode" lowpart, the operation
5749 can be implement with a single bitwise AND. Otherwise, we need
5750 a right shift and an AND. */
5752 if (bitpos < GET_MODE_BITSIZE (rmode))
5754 if (bitpos < HOST_BITS_PER_WIDE_INT)
5756 hi = 0;
5757 lo = (HOST_WIDE_INT) 1 << bitpos;
5759 else
5761 hi = (HOST_WIDE_INT) 1 << (bitpos - HOST_BITS_PER_WIDE_INT);
5762 lo = 0;
5765 if (imode != rmode)
5766 temp = gen_lowpart (rmode, temp);
5767 temp = expand_binop (rmode, and_optab, temp,
5768 immed_double_const (lo, hi, rmode),
5769 NULL_RTX, 1, OPTAB_LIB_WIDEN);
5771 else
5773 /* Perform a logical right shift to place the signbit in the least
5774 significant bit, then truncate the result to the desired mode
5775 and mask just this bit. */
5776 temp = expand_shift (RSHIFT_EXPR, imode, temp,
5777 build_int_cst (NULL_TREE, bitpos), NULL_RTX, 1);
5778 temp = gen_lowpart (rmode, temp);
5779 temp = expand_binop (rmode, and_optab, temp, const1_rtx,
5780 NULL_RTX, 1, OPTAB_LIB_WIDEN);
5783 return temp;
5786 /* Expand fork or exec calls. TARGET is the desired target of the
5787 call. EXP is the call. FN is the
5788 identificator of the actual function. IGNORE is nonzero if the
5789 value is to be ignored. */
5791 static rtx
5792 expand_builtin_fork_or_exec (tree fn, tree exp, rtx target, int ignore)
5794 tree id, decl;
5795 tree call;
5797 /* If we are not profiling, just call the function. */
5798 if (!profile_arc_flag)
5799 return NULL_RTX;
5801 /* Otherwise call the wrapper. This should be equivalent for the rest of
5802 compiler, so the code does not diverge, and the wrapper may run the
5803 code necessary for keeping the profiling sane. */
5805 switch (DECL_FUNCTION_CODE (fn))
5807 case BUILT_IN_FORK:
5808 id = get_identifier ("__gcov_fork");
5809 break;
5811 case BUILT_IN_EXECL:
5812 id = get_identifier ("__gcov_execl");
5813 break;
5815 case BUILT_IN_EXECV:
5816 id = get_identifier ("__gcov_execv");
5817 break;
5819 case BUILT_IN_EXECLP:
5820 id = get_identifier ("__gcov_execlp");
5821 break;
5823 case BUILT_IN_EXECLE:
5824 id = get_identifier ("__gcov_execle");
5825 break;
5827 case BUILT_IN_EXECVP:
5828 id = get_identifier ("__gcov_execvp");
5829 break;
5831 case BUILT_IN_EXECVE:
5832 id = get_identifier ("__gcov_execve");
5833 break;
5835 default:
5836 gcc_unreachable ();
5839 decl = build_decl (FUNCTION_DECL, id, TREE_TYPE (fn));
5840 DECL_EXTERNAL (decl) = 1;
5841 TREE_PUBLIC (decl) = 1;
5842 DECL_ARTIFICIAL (decl) = 1;
5843 TREE_NOTHROW (decl) = 1;
5844 DECL_VISIBILITY (decl) = VISIBILITY_DEFAULT;
5845 DECL_VISIBILITY_SPECIFIED (decl) = 1;
5846 call = rewrite_call_expr (exp, 0, decl, 0);
5847 return expand_call (call, target, ignore);
5852 /* Reconstitute a mode for a __sync intrinsic operation. Since the type of
5853 the pointer in these functions is void*, the tree optimizers may remove
5854 casts. The mode computed in expand_builtin isn't reliable either, due
5855 to __sync_bool_compare_and_swap.
5857 FCODE_DIFF should be fcode - base, where base is the FOO_1 code for the
5858 group of builtins. This gives us log2 of the mode size. */
5860 static inline enum machine_mode
5861 get_builtin_sync_mode (int fcode_diff)
5863 /* The size is not negotiable, so ask not to get BLKmode in return
5864 if the target indicates that a smaller size would be better. */
5865 return mode_for_size (BITS_PER_UNIT << fcode_diff, MODE_INT, 0);
5868 /* Expand the memory expression LOC and return the appropriate memory operand
5869 for the builtin_sync operations. */
5871 static rtx
5872 get_builtin_sync_mem (tree loc, enum machine_mode mode)
5874 rtx addr, mem;
5876 addr = expand_expr (loc, NULL_RTX, Pmode, EXPAND_SUM);
5878 /* Note that we explicitly do not want any alias information for this
5879 memory, so that we kill all other live memories. Otherwise we don't
5880 satisfy the full barrier semantics of the intrinsic. */
5881 mem = validize_mem (gen_rtx_MEM (mode, addr));
5883 set_mem_align (mem, get_pointer_alignment (loc, BIGGEST_ALIGNMENT));
5884 set_mem_alias_set (mem, ALIAS_SET_MEMORY_BARRIER);
5885 MEM_VOLATILE_P (mem) = 1;
5887 return mem;
5890 /* Expand the __sync_xxx_and_fetch and __sync_fetch_and_xxx intrinsics.
5891 EXP is the CALL_EXPR. CODE is the rtx code
5892 that corresponds to the arithmetic or logical operation from the name;
5893 an exception here is that NOT actually means NAND. TARGET is an optional
5894 place for us to store the results; AFTER is true if this is the
5895 fetch_and_xxx form. IGNORE is true if we don't actually care about
5896 the result of the operation at all. */
5898 static rtx
5899 expand_builtin_sync_operation (enum machine_mode mode, tree exp,
5900 enum rtx_code code, bool after,
5901 rtx target, bool ignore)
5903 rtx val, mem;
5904 enum machine_mode old_mode;
5906 /* Expand the operands. */
5907 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5909 val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX, mode, EXPAND_NORMAL);
5910 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5911 of CONST_INTs, where we know the old_mode only from the call argument. */
5912 old_mode = GET_MODE (val);
5913 if (old_mode == VOIDmode)
5914 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5915 val = convert_modes (mode, old_mode, val, 1);
5917 if (ignore)
5918 return expand_sync_operation (mem, val, code);
5919 else
5920 return expand_sync_fetch_operation (mem, val, code, after, target);
5923 /* Expand the __sync_val_compare_and_swap and __sync_bool_compare_and_swap
5924 intrinsics. EXP is the CALL_EXPR. IS_BOOL is
5925 true if this is the boolean form. TARGET is a place for us to store the
5926 results; this is NOT optional if IS_BOOL is true. */
5928 static rtx
5929 expand_builtin_compare_and_swap (enum machine_mode mode, tree exp,
5930 bool is_bool, rtx target)
5932 rtx old_val, new_val, mem;
5933 enum machine_mode old_mode;
5935 /* Expand the operands. */
5936 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5939 old_val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX,
5940 mode, EXPAND_NORMAL);
5941 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5942 of CONST_INTs, where we know the old_mode only from the call argument. */
5943 old_mode = GET_MODE (old_val);
5944 if (old_mode == VOIDmode)
5945 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5946 old_val = convert_modes (mode, old_mode, old_val, 1);
5948 new_val = expand_expr (CALL_EXPR_ARG (exp, 2), NULL_RTX,
5949 mode, EXPAND_NORMAL);
5950 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5951 of CONST_INTs, where we know the old_mode only from the call argument. */
5952 old_mode = GET_MODE (new_val);
5953 if (old_mode == VOIDmode)
5954 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 2)));
5955 new_val = convert_modes (mode, old_mode, new_val, 1);
5957 if (is_bool)
5958 return expand_bool_compare_and_swap (mem, old_val, new_val, target);
5959 else
5960 return expand_val_compare_and_swap (mem, old_val, new_val, target);
5963 /* Expand the __sync_lock_test_and_set intrinsic. Note that the most
5964 general form is actually an atomic exchange, and some targets only
5965 support a reduced form with the second argument being a constant 1.
5966 EXP is the CALL_EXPR; TARGET is an optional place for us to store
5967 the results. */
5969 static rtx
5970 expand_builtin_lock_test_and_set (enum machine_mode mode, tree exp,
5971 rtx target)
5973 rtx val, mem;
5974 enum machine_mode old_mode;
5976 /* Expand the operands. */
5977 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5978 val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX, mode, EXPAND_NORMAL);
5979 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5980 of CONST_INTs, where we know the old_mode only from the call argument. */
5981 old_mode = GET_MODE (val);
5982 if (old_mode == VOIDmode)
5983 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5984 val = convert_modes (mode, old_mode, val, 1);
5986 return expand_sync_lock_test_and_set (mem, val, target);
5989 /* Expand the __sync_synchronize intrinsic. */
5991 static void
5992 expand_builtin_synchronize (void)
5994 tree x;
5996 #ifdef HAVE_memory_barrier
5997 if (HAVE_memory_barrier)
5999 emit_insn (gen_memory_barrier ());
6000 return;
6002 #endif
6004 /* If no explicit memory barrier instruction is available, create an
6005 empty asm stmt with a memory clobber. */
6006 x = build4 (ASM_EXPR, void_type_node, build_string (0, ""), NULL, NULL,
6007 tree_cons (NULL, build_string (6, "memory"), NULL));
6008 ASM_VOLATILE_P (x) = 1;
6009 expand_asm_expr (x);
6012 /* Expand the __sync_lock_release intrinsic. EXP is the CALL_EXPR. */
6014 static void
6015 expand_builtin_lock_release (enum machine_mode mode, tree exp)
6017 enum insn_code icode;
6018 rtx mem, insn;
6019 rtx val = const0_rtx;
6021 /* Expand the operands. */
6022 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
6024 /* If there is an explicit operation in the md file, use it. */
6025 icode = sync_lock_release[mode];
6026 if (icode != CODE_FOR_nothing)
6028 if (!insn_data[icode].operand[1].predicate (val, mode))
6029 val = force_reg (mode, val);
6031 insn = GEN_FCN (icode) (mem, val);
6032 if (insn)
6034 emit_insn (insn);
6035 return;
6039 /* Otherwise we can implement this operation by emitting a barrier
6040 followed by a store of zero. */
6041 expand_builtin_synchronize ();
6042 emit_move_insn (mem, val);
6045 /* Expand an expression EXP that calls a built-in function,
6046 with result going to TARGET if that's convenient
6047 (and in mode MODE if that's convenient).
6048 SUBTARGET may be used as the target for computing one of EXP's operands.
6049 IGNORE is nonzero if the value is to be ignored. */
6052 expand_builtin (tree exp, rtx target, rtx subtarget, enum machine_mode mode,
6053 int ignore)
6055 tree fndecl = get_callee_fndecl (exp);
6056 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
6057 enum machine_mode target_mode = TYPE_MODE (TREE_TYPE (exp));
6059 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
6060 return targetm.expand_builtin (exp, target, subtarget, mode, ignore);
6062 /* When not optimizing, generate calls to library functions for a certain
6063 set of builtins. */
6064 if (!optimize
6065 && !called_as_built_in (fndecl)
6066 && DECL_ASSEMBLER_NAME_SET_P (fndecl)
6067 && fcode != BUILT_IN_ALLOCA)
6068 return expand_call (exp, target, ignore);
6070 /* The built-in function expanders test for target == const0_rtx
6071 to determine whether the function's result will be ignored. */
6072 if (ignore)
6073 target = const0_rtx;
6075 /* If the result of a pure or const built-in function is ignored, and
6076 none of its arguments are volatile, we can avoid expanding the
6077 built-in call and just evaluate the arguments for side-effects. */
6078 if (target == const0_rtx
6079 && (DECL_IS_PURE (fndecl) || TREE_READONLY (fndecl)))
6081 bool volatilep = false;
6082 tree arg;
6083 call_expr_arg_iterator iter;
6085 FOR_EACH_CALL_EXPR_ARG (arg, iter, exp)
6086 if (TREE_THIS_VOLATILE (arg))
6088 volatilep = true;
6089 break;
6092 if (! volatilep)
6094 FOR_EACH_CALL_EXPR_ARG (arg, iter, exp)
6095 expand_expr (arg, const0_rtx, VOIDmode, EXPAND_NORMAL);
6096 return const0_rtx;
6100 switch (fcode)
6102 CASE_FLT_FN (BUILT_IN_FABS):
6103 target = expand_builtin_fabs (exp, target, subtarget);
6104 if (target)
6105 return target;
6106 break;
6108 CASE_FLT_FN (BUILT_IN_COPYSIGN):
6109 target = expand_builtin_copysign (exp, target, subtarget);
6110 if (target)
6111 return target;
6112 break;
6114 /* Just do a normal library call if we were unable to fold
6115 the values. */
6116 CASE_FLT_FN (BUILT_IN_CABS):
6117 break;
6119 CASE_FLT_FN (BUILT_IN_EXP):
6120 CASE_FLT_FN (BUILT_IN_EXP10):
6121 CASE_FLT_FN (BUILT_IN_POW10):
6122 CASE_FLT_FN (BUILT_IN_EXP2):
6123 CASE_FLT_FN (BUILT_IN_EXPM1):
6124 CASE_FLT_FN (BUILT_IN_LOGB):
6125 CASE_FLT_FN (BUILT_IN_LOG):
6126 CASE_FLT_FN (BUILT_IN_LOG10):
6127 CASE_FLT_FN (BUILT_IN_LOG2):
6128 CASE_FLT_FN (BUILT_IN_LOG1P):
6129 CASE_FLT_FN (BUILT_IN_TAN):
6130 CASE_FLT_FN (BUILT_IN_ASIN):
6131 CASE_FLT_FN (BUILT_IN_ACOS):
6132 CASE_FLT_FN (BUILT_IN_ATAN):
6133 /* Treat these like sqrt only if unsafe math optimizations are allowed,
6134 because of possible accuracy problems. */
6135 if (! flag_unsafe_math_optimizations)
6136 break;
6137 CASE_FLT_FN (BUILT_IN_SQRT):
6138 CASE_FLT_FN (BUILT_IN_FLOOR):
6139 CASE_FLT_FN (BUILT_IN_CEIL):
6140 CASE_FLT_FN (BUILT_IN_TRUNC):
6141 CASE_FLT_FN (BUILT_IN_ROUND):
6142 CASE_FLT_FN (BUILT_IN_NEARBYINT):
6143 CASE_FLT_FN (BUILT_IN_RINT):
6144 target = expand_builtin_mathfn (exp, target, subtarget);
6145 if (target)
6146 return target;
6147 break;
6149 CASE_FLT_FN (BUILT_IN_ILOGB):
6150 if (! flag_unsafe_math_optimizations)
6151 break;
6152 CASE_FLT_FN (BUILT_IN_ISINF):
6153 CASE_FLT_FN (BUILT_IN_FINITE):
6154 case BUILT_IN_ISFINITE:
6155 case BUILT_IN_ISNORMAL:
6156 target = expand_builtin_interclass_mathfn (exp, target, subtarget);
6157 if (target)
6158 return target;
6159 break;
6161 CASE_FLT_FN (BUILT_IN_LCEIL):
6162 CASE_FLT_FN (BUILT_IN_LLCEIL):
6163 CASE_FLT_FN (BUILT_IN_LFLOOR):
6164 CASE_FLT_FN (BUILT_IN_LLFLOOR):
6165 target = expand_builtin_int_roundingfn (exp, target, subtarget);
6166 if (target)
6167 return target;
6168 break;
6170 CASE_FLT_FN (BUILT_IN_LRINT):
6171 CASE_FLT_FN (BUILT_IN_LLRINT):
6172 CASE_FLT_FN (BUILT_IN_LROUND):
6173 CASE_FLT_FN (BUILT_IN_LLROUND):
6174 target = expand_builtin_int_roundingfn_2 (exp, target, subtarget);
6175 if (target)
6176 return target;
6177 break;
6179 CASE_FLT_FN (BUILT_IN_POW):
6180 target = expand_builtin_pow (exp, target, subtarget);
6181 if (target)
6182 return target;
6183 break;
6185 CASE_FLT_FN (BUILT_IN_POWI):
6186 target = expand_builtin_powi (exp, target, subtarget);
6187 if (target)
6188 return target;
6189 break;
6191 CASE_FLT_FN (BUILT_IN_ATAN2):
6192 CASE_FLT_FN (BUILT_IN_LDEXP):
6193 CASE_FLT_FN (BUILT_IN_SCALB):
6194 CASE_FLT_FN (BUILT_IN_SCALBN):
6195 CASE_FLT_FN (BUILT_IN_SCALBLN):
6196 if (! flag_unsafe_math_optimizations)
6197 break;
6199 CASE_FLT_FN (BUILT_IN_FMOD):
6200 CASE_FLT_FN (BUILT_IN_REMAINDER):
6201 CASE_FLT_FN (BUILT_IN_DREM):
6202 target = expand_builtin_mathfn_2 (exp, target, subtarget);
6203 if (target)
6204 return target;
6205 break;
6207 CASE_FLT_FN (BUILT_IN_CEXPI):
6208 target = expand_builtin_cexpi (exp, target, subtarget);
6209 gcc_assert (target);
6210 return target;
6212 CASE_FLT_FN (BUILT_IN_SIN):
6213 CASE_FLT_FN (BUILT_IN_COS):
6214 if (! flag_unsafe_math_optimizations)
6215 break;
6216 target = expand_builtin_mathfn_3 (exp, target, subtarget);
6217 if (target)
6218 return target;
6219 break;
6221 CASE_FLT_FN (BUILT_IN_SINCOS):
6222 if (! flag_unsafe_math_optimizations)
6223 break;
6224 target = expand_builtin_sincos (exp);
6225 if (target)
6226 return target;
6227 break;
6229 case BUILT_IN_APPLY_ARGS:
6230 return expand_builtin_apply_args ();
6232 /* __builtin_apply (FUNCTION, ARGUMENTS, ARGSIZE) invokes
6233 FUNCTION with a copy of the parameters described by
6234 ARGUMENTS, and ARGSIZE. It returns a block of memory
6235 allocated on the stack into which is stored all the registers
6236 that might possibly be used for returning the result of a
6237 function. ARGUMENTS is the value returned by
6238 __builtin_apply_args. ARGSIZE is the number of bytes of
6239 arguments that must be copied. ??? How should this value be
6240 computed? We'll also need a safe worst case value for varargs
6241 functions. */
6242 case BUILT_IN_APPLY:
6243 if (!validate_arglist (exp, POINTER_TYPE,
6244 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE)
6245 && !validate_arglist (exp, REFERENCE_TYPE,
6246 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
6247 return const0_rtx;
6248 else
6250 rtx ops[3];
6252 ops[0] = expand_normal (CALL_EXPR_ARG (exp, 0));
6253 ops[1] = expand_normal (CALL_EXPR_ARG (exp, 1));
6254 ops[2] = expand_normal (CALL_EXPR_ARG (exp, 2));
6256 return expand_builtin_apply (ops[0], ops[1], ops[2]);
6259 /* __builtin_return (RESULT) causes the function to return the
6260 value described by RESULT. RESULT is address of the block of
6261 memory returned by __builtin_apply. */
6262 case BUILT_IN_RETURN:
6263 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6264 expand_builtin_return (expand_normal (CALL_EXPR_ARG (exp, 0)));
6265 return const0_rtx;
6267 case BUILT_IN_SAVEREGS:
6268 return expand_builtin_saveregs ();
6270 case BUILT_IN_ARGS_INFO:
6271 return expand_builtin_args_info (exp);
6273 case BUILT_IN_VA_ARG_PACK:
6274 /* All valid uses of __builtin_va_arg_pack () are removed during
6275 inlining. */
6276 error ("invalid use of %<__builtin_va_arg_pack ()%>");
6277 return const0_rtx;
6279 case BUILT_IN_VA_ARG_PACK_LEN:
6280 /* All valid uses of __builtin_va_arg_pack_len () are removed during
6281 inlining. */
6282 error ("invalid use of %<__builtin_va_arg_pack_len ()%>");
6283 return const0_rtx;
6285 /* Return the address of the first anonymous stack arg. */
6286 case BUILT_IN_NEXT_ARG:
6287 if (fold_builtin_next_arg (exp, false))
6288 return const0_rtx;
6289 return expand_builtin_next_arg ();
6291 case BUILT_IN_CLEAR_CACHE:
6292 target = expand_builtin___clear_cache (exp);
6293 if (target)
6294 return target;
6295 break;
6297 case BUILT_IN_CLASSIFY_TYPE:
6298 return expand_builtin_classify_type (exp);
6300 case BUILT_IN_CONSTANT_P:
6301 return const0_rtx;
6303 case BUILT_IN_FRAME_ADDRESS:
6304 case BUILT_IN_RETURN_ADDRESS:
6305 return expand_builtin_frame_address (fndecl, exp);
6307 /* Returns the address of the area where the structure is returned.
6308 0 otherwise. */
6309 case BUILT_IN_AGGREGATE_INCOMING_ADDRESS:
6310 if (call_expr_nargs (exp) != 0
6311 || ! AGGREGATE_TYPE_P (TREE_TYPE (TREE_TYPE (current_function_decl)))
6312 || !MEM_P (DECL_RTL (DECL_RESULT (current_function_decl))))
6313 return const0_rtx;
6314 else
6315 return XEXP (DECL_RTL (DECL_RESULT (current_function_decl)), 0);
6317 case BUILT_IN_ALLOCA:
6318 target = expand_builtin_alloca (exp, target);
6319 if (target)
6320 return target;
6321 break;
6323 case BUILT_IN_STACK_SAVE:
6324 return expand_stack_save ();
6326 case BUILT_IN_STACK_RESTORE:
6327 expand_stack_restore (CALL_EXPR_ARG (exp, 0));
6328 return const0_rtx;
6330 case BUILT_IN_BSWAP32:
6331 case BUILT_IN_BSWAP64:
6332 target = expand_builtin_bswap (exp, target, subtarget);
6334 if (target)
6335 return target;
6336 break;
6338 CASE_INT_FN (BUILT_IN_FFS):
6339 case BUILT_IN_FFSIMAX:
6340 target = expand_builtin_unop (target_mode, exp, target,
6341 subtarget, ffs_optab);
6342 if (target)
6343 return target;
6344 break;
6346 CASE_INT_FN (BUILT_IN_CLZ):
6347 case BUILT_IN_CLZIMAX:
6348 target = expand_builtin_unop (target_mode, exp, target,
6349 subtarget, clz_optab);
6350 if (target)
6351 return target;
6352 break;
6354 CASE_INT_FN (BUILT_IN_CTZ):
6355 case BUILT_IN_CTZIMAX:
6356 target = expand_builtin_unop (target_mode, exp, target,
6357 subtarget, ctz_optab);
6358 if (target)
6359 return target;
6360 break;
6362 CASE_INT_FN (BUILT_IN_POPCOUNT):
6363 case BUILT_IN_POPCOUNTIMAX:
6364 target = expand_builtin_unop (target_mode, exp, target,
6365 subtarget, popcount_optab);
6366 if (target)
6367 return target;
6368 break;
6370 CASE_INT_FN (BUILT_IN_PARITY):
6371 case BUILT_IN_PARITYIMAX:
6372 target = expand_builtin_unop (target_mode, exp, target,
6373 subtarget, parity_optab);
6374 if (target)
6375 return target;
6376 break;
6378 case BUILT_IN_STRLEN:
6379 target = expand_builtin_strlen (exp, target, target_mode);
6380 if (target)
6381 return target;
6382 break;
6384 case BUILT_IN_STRCPY:
6385 target = expand_builtin_strcpy (fndecl, exp, target, mode);
6386 if (target)
6387 return target;
6388 break;
6390 case BUILT_IN_STRNCPY:
6391 target = expand_builtin_strncpy (exp, target, mode);
6392 if (target)
6393 return target;
6394 break;
6396 case BUILT_IN_STPCPY:
6397 target = expand_builtin_stpcpy (exp, target, mode);
6398 if (target)
6399 return target;
6400 break;
6402 case BUILT_IN_STRCAT:
6403 target = expand_builtin_strcat (fndecl, exp, target, mode);
6404 if (target)
6405 return target;
6406 break;
6408 case BUILT_IN_STRNCAT:
6409 target = expand_builtin_strncat (exp, target, mode);
6410 if (target)
6411 return target;
6412 break;
6414 case BUILT_IN_STRSPN:
6415 target = expand_builtin_strspn (exp, target, mode);
6416 if (target)
6417 return target;
6418 break;
6420 case BUILT_IN_STRCSPN:
6421 target = expand_builtin_strcspn (exp, target, mode);
6422 if (target)
6423 return target;
6424 break;
6426 case BUILT_IN_STRSTR:
6427 target = expand_builtin_strstr (exp, target, mode);
6428 if (target)
6429 return target;
6430 break;
6432 case BUILT_IN_STRPBRK:
6433 target = expand_builtin_strpbrk (exp, target, mode);
6434 if (target)
6435 return target;
6436 break;
6438 case BUILT_IN_INDEX:
6439 case BUILT_IN_STRCHR:
6440 target = expand_builtin_strchr (exp, target, mode);
6441 if (target)
6442 return target;
6443 break;
6445 case BUILT_IN_RINDEX:
6446 case BUILT_IN_STRRCHR:
6447 target = expand_builtin_strrchr (exp, target, mode);
6448 if (target)
6449 return target;
6450 break;
6452 case BUILT_IN_MEMCPY:
6453 target = expand_builtin_memcpy (exp, target, mode);
6454 if (target)
6455 return target;
6456 break;
6458 case BUILT_IN_MEMPCPY:
6459 target = expand_builtin_mempcpy (exp, target, mode);
6460 if (target)
6461 return target;
6462 break;
6464 case BUILT_IN_MEMMOVE:
6465 target = expand_builtin_memmove (exp, target, mode, ignore);
6466 if (target)
6467 return target;
6468 break;
6470 case BUILT_IN_BCOPY:
6471 target = expand_builtin_bcopy (exp, ignore);
6472 if (target)
6473 return target;
6474 break;
6476 case BUILT_IN_MEMSET:
6477 target = expand_builtin_memset (exp, target, mode);
6478 if (target)
6479 return target;
6480 break;
6482 case BUILT_IN_BZERO:
6483 target = expand_builtin_bzero (exp);
6484 if (target)
6485 return target;
6486 break;
6488 case BUILT_IN_STRCMP:
6489 target = expand_builtin_strcmp (exp, target, mode);
6490 if (target)
6491 return target;
6492 break;
6494 case BUILT_IN_STRNCMP:
6495 target = expand_builtin_strncmp (exp, target, mode);
6496 if (target)
6497 return target;
6498 break;
6500 case BUILT_IN_MEMCHR:
6501 target = expand_builtin_memchr (exp, target, mode);
6502 if (target)
6503 return target;
6504 break;
6506 case BUILT_IN_BCMP:
6507 case BUILT_IN_MEMCMP:
6508 target = expand_builtin_memcmp (exp, target, mode);
6509 if (target)
6510 return target;
6511 break;
6513 case BUILT_IN_SETJMP:
6514 /* This should have been lowered to the builtins below. */
6515 gcc_unreachable ();
6517 case BUILT_IN_SETJMP_SETUP:
6518 /* __builtin_setjmp_setup is passed a pointer to an array of five words
6519 and the receiver label. */
6520 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
6522 rtx buf_addr = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
6523 VOIDmode, EXPAND_NORMAL);
6524 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 1), 0);
6525 rtx label_r = label_rtx (label);
6527 /* This is copied from the handling of non-local gotos. */
6528 expand_builtin_setjmp_setup (buf_addr, label_r);
6529 nonlocal_goto_handler_labels
6530 = gen_rtx_EXPR_LIST (VOIDmode, label_r,
6531 nonlocal_goto_handler_labels);
6532 /* ??? Do not let expand_label treat us as such since we would
6533 not want to be both on the list of non-local labels and on
6534 the list of forced labels. */
6535 FORCED_LABEL (label) = 0;
6536 return const0_rtx;
6538 break;
6540 case BUILT_IN_SETJMP_DISPATCHER:
6541 /* __builtin_setjmp_dispatcher is passed the dispatcher label. */
6542 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6544 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 0), 0);
6545 rtx label_r = label_rtx (label);
6547 /* Remove the dispatcher label from the list of non-local labels
6548 since the receiver labels have been added to it above. */
6549 remove_node_from_expr_list (label_r, &nonlocal_goto_handler_labels);
6550 return const0_rtx;
6552 break;
6554 case BUILT_IN_SETJMP_RECEIVER:
6555 /* __builtin_setjmp_receiver is passed the receiver label. */
6556 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6558 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 0), 0);
6559 rtx label_r = label_rtx (label);
6561 expand_builtin_setjmp_receiver (label_r);
6562 return const0_rtx;
6564 break;
6566 /* __builtin_longjmp is passed a pointer to an array of five words.
6567 It's similar to the C library longjmp function but works with
6568 __builtin_setjmp above. */
6569 case BUILT_IN_LONGJMP:
6570 if (validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
6572 rtx buf_addr = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
6573 VOIDmode, EXPAND_NORMAL);
6574 rtx value = expand_normal (CALL_EXPR_ARG (exp, 1));
6576 if (value != const1_rtx)
6578 error ("%<__builtin_longjmp%> second argument must be 1");
6579 return const0_rtx;
6582 expand_builtin_longjmp (buf_addr, value);
6583 return const0_rtx;
6585 break;
6587 case BUILT_IN_NONLOCAL_GOTO:
6588 target = expand_builtin_nonlocal_goto (exp);
6589 if (target)
6590 return target;
6591 break;
6593 /* This updates the setjmp buffer that is its argument with the value
6594 of the current stack pointer. */
6595 case BUILT_IN_UPDATE_SETJMP_BUF:
6596 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6598 rtx buf_addr
6599 = expand_normal (CALL_EXPR_ARG (exp, 0));
6601 expand_builtin_update_setjmp_buf (buf_addr);
6602 return const0_rtx;
6604 break;
6606 case BUILT_IN_TRAP:
6607 expand_builtin_trap ();
6608 return const0_rtx;
6610 case BUILT_IN_PRINTF:
6611 target = expand_builtin_printf (exp, target, mode, false);
6612 if (target)
6613 return target;
6614 break;
6616 case BUILT_IN_PRINTF_UNLOCKED:
6617 target = expand_builtin_printf (exp, target, mode, true);
6618 if (target)
6619 return target;
6620 break;
6622 case BUILT_IN_FPUTS:
6623 target = expand_builtin_fputs (exp, target, false);
6624 if (target)
6625 return target;
6626 break;
6627 case BUILT_IN_FPUTS_UNLOCKED:
6628 target = expand_builtin_fputs (exp, target, true);
6629 if (target)
6630 return target;
6631 break;
6633 case BUILT_IN_FPRINTF:
6634 target = expand_builtin_fprintf (exp, target, mode, false);
6635 if (target)
6636 return target;
6637 break;
6639 case BUILT_IN_FPRINTF_UNLOCKED:
6640 target = expand_builtin_fprintf (exp, target, mode, true);
6641 if (target)
6642 return target;
6643 break;
6645 case BUILT_IN_SPRINTF:
6646 target = expand_builtin_sprintf (exp, target, mode);
6647 if (target)
6648 return target;
6649 break;
6651 CASE_FLT_FN (BUILT_IN_SIGNBIT):
6652 case BUILT_IN_SIGNBITD32:
6653 case BUILT_IN_SIGNBITD64:
6654 case BUILT_IN_SIGNBITD128:
6655 target = expand_builtin_signbit (exp, target);
6656 if (target)
6657 return target;
6658 break;
6660 /* Various hooks for the DWARF 2 __throw routine. */
6661 case BUILT_IN_UNWIND_INIT:
6662 expand_builtin_unwind_init ();
6663 return const0_rtx;
6664 case BUILT_IN_DWARF_CFA:
6665 return virtual_cfa_rtx;
6666 #ifdef DWARF2_UNWIND_INFO
6667 case BUILT_IN_DWARF_SP_COLUMN:
6668 return expand_builtin_dwarf_sp_column ();
6669 case BUILT_IN_INIT_DWARF_REG_SIZES:
6670 expand_builtin_init_dwarf_reg_sizes (CALL_EXPR_ARG (exp, 0));
6671 return const0_rtx;
6672 #endif
6673 case BUILT_IN_FROB_RETURN_ADDR:
6674 return expand_builtin_frob_return_addr (CALL_EXPR_ARG (exp, 0));
6675 case BUILT_IN_EXTRACT_RETURN_ADDR:
6676 return expand_builtin_extract_return_addr (CALL_EXPR_ARG (exp, 0));
6677 case BUILT_IN_EH_RETURN:
6678 expand_builtin_eh_return (CALL_EXPR_ARG (exp, 0),
6679 CALL_EXPR_ARG (exp, 1));
6680 return const0_rtx;
6681 #ifdef EH_RETURN_DATA_REGNO
6682 case BUILT_IN_EH_RETURN_DATA_REGNO:
6683 return expand_builtin_eh_return_data_regno (exp);
6684 #endif
6685 case BUILT_IN_EXTEND_POINTER:
6686 return expand_builtin_extend_pointer (CALL_EXPR_ARG (exp, 0));
6688 case BUILT_IN_VA_START:
6689 case BUILT_IN_STDARG_START:
6690 return expand_builtin_va_start (exp);
6691 case BUILT_IN_VA_END:
6692 return expand_builtin_va_end (exp);
6693 case BUILT_IN_VA_COPY:
6694 return expand_builtin_va_copy (exp);
6695 case BUILT_IN_EXPECT:
6696 return expand_builtin_expect (exp, target);
6697 case BUILT_IN_PREFETCH:
6698 expand_builtin_prefetch (exp);
6699 return const0_rtx;
6701 case BUILT_IN_PROFILE_FUNC_ENTER:
6702 return expand_builtin_profile_func (false);
6703 case BUILT_IN_PROFILE_FUNC_EXIT:
6704 return expand_builtin_profile_func (true);
6706 case BUILT_IN_INIT_TRAMPOLINE:
6707 return expand_builtin_init_trampoline (exp);
6708 case BUILT_IN_ADJUST_TRAMPOLINE:
6709 return expand_builtin_adjust_trampoline (exp);
6711 case BUILT_IN_FORK:
6712 case BUILT_IN_EXECL:
6713 case BUILT_IN_EXECV:
6714 case BUILT_IN_EXECLP:
6715 case BUILT_IN_EXECLE:
6716 case BUILT_IN_EXECVP:
6717 case BUILT_IN_EXECVE:
6718 target = expand_builtin_fork_or_exec (fndecl, exp, target, ignore);
6719 if (target)
6720 return target;
6721 break;
6723 case BUILT_IN_FETCH_AND_ADD_1:
6724 case BUILT_IN_FETCH_AND_ADD_2:
6725 case BUILT_IN_FETCH_AND_ADD_4:
6726 case BUILT_IN_FETCH_AND_ADD_8:
6727 case BUILT_IN_FETCH_AND_ADD_16:
6728 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_ADD_1);
6729 target = expand_builtin_sync_operation (mode, exp, PLUS,
6730 false, target, ignore);
6731 if (target)
6732 return target;
6733 break;
6735 case BUILT_IN_FETCH_AND_SUB_1:
6736 case BUILT_IN_FETCH_AND_SUB_2:
6737 case BUILT_IN_FETCH_AND_SUB_4:
6738 case BUILT_IN_FETCH_AND_SUB_8:
6739 case BUILT_IN_FETCH_AND_SUB_16:
6740 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_SUB_1);
6741 target = expand_builtin_sync_operation (mode, exp, MINUS,
6742 false, target, ignore);
6743 if (target)
6744 return target;
6745 break;
6747 case BUILT_IN_FETCH_AND_OR_1:
6748 case BUILT_IN_FETCH_AND_OR_2:
6749 case BUILT_IN_FETCH_AND_OR_4:
6750 case BUILT_IN_FETCH_AND_OR_8:
6751 case BUILT_IN_FETCH_AND_OR_16:
6752 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_OR_1);
6753 target = expand_builtin_sync_operation (mode, exp, IOR,
6754 false, target, ignore);
6755 if (target)
6756 return target;
6757 break;
6759 case BUILT_IN_FETCH_AND_AND_1:
6760 case BUILT_IN_FETCH_AND_AND_2:
6761 case BUILT_IN_FETCH_AND_AND_4:
6762 case BUILT_IN_FETCH_AND_AND_8:
6763 case BUILT_IN_FETCH_AND_AND_16:
6764 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_AND_1);
6765 target = expand_builtin_sync_operation (mode, exp, AND,
6766 false, target, ignore);
6767 if (target)
6768 return target;
6769 break;
6771 case BUILT_IN_FETCH_AND_XOR_1:
6772 case BUILT_IN_FETCH_AND_XOR_2:
6773 case BUILT_IN_FETCH_AND_XOR_4:
6774 case BUILT_IN_FETCH_AND_XOR_8:
6775 case BUILT_IN_FETCH_AND_XOR_16:
6776 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_XOR_1);
6777 target = expand_builtin_sync_operation (mode, exp, XOR,
6778 false, target, ignore);
6779 if (target)
6780 return target;
6781 break;
6783 case BUILT_IN_FETCH_AND_NAND_1:
6784 case BUILT_IN_FETCH_AND_NAND_2:
6785 case BUILT_IN_FETCH_AND_NAND_4:
6786 case BUILT_IN_FETCH_AND_NAND_8:
6787 case BUILT_IN_FETCH_AND_NAND_16:
6788 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_NAND_1);
6789 target = expand_builtin_sync_operation (mode, exp, NOT,
6790 false, target, ignore);
6791 if (target)
6792 return target;
6793 break;
6795 case BUILT_IN_ADD_AND_FETCH_1:
6796 case BUILT_IN_ADD_AND_FETCH_2:
6797 case BUILT_IN_ADD_AND_FETCH_4:
6798 case BUILT_IN_ADD_AND_FETCH_8:
6799 case BUILT_IN_ADD_AND_FETCH_16:
6800 mode = get_builtin_sync_mode (fcode - BUILT_IN_ADD_AND_FETCH_1);
6801 target = expand_builtin_sync_operation (mode, exp, PLUS,
6802 true, target, ignore);
6803 if (target)
6804 return target;
6805 break;
6807 case BUILT_IN_SUB_AND_FETCH_1:
6808 case BUILT_IN_SUB_AND_FETCH_2:
6809 case BUILT_IN_SUB_AND_FETCH_4:
6810 case BUILT_IN_SUB_AND_FETCH_8:
6811 case BUILT_IN_SUB_AND_FETCH_16:
6812 mode = get_builtin_sync_mode (fcode - BUILT_IN_SUB_AND_FETCH_1);
6813 target = expand_builtin_sync_operation (mode, exp, MINUS,
6814 true, target, ignore);
6815 if (target)
6816 return target;
6817 break;
6819 case BUILT_IN_OR_AND_FETCH_1:
6820 case BUILT_IN_OR_AND_FETCH_2:
6821 case BUILT_IN_OR_AND_FETCH_4:
6822 case BUILT_IN_OR_AND_FETCH_8:
6823 case BUILT_IN_OR_AND_FETCH_16:
6824 mode = get_builtin_sync_mode (fcode - BUILT_IN_OR_AND_FETCH_1);
6825 target = expand_builtin_sync_operation (mode, exp, IOR,
6826 true, target, ignore);
6827 if (target)
6828 return target;
6829 break;
6831 case BUILT_IN_AND_AND_FETCH_1:
6832 case BUILT_IN_AND_AND_FETCH_2:
6833 case BUILT_IN_AND_AND_FETCH_4:
6834 case BUILT_IN_AND_AND_FETCH_8:
6835 case BUILT_IN_AND_AND_FETCH_16:
6836 mode = get_builtin_sync_mode (fcode - BUILT_IN_AND_AND_FETCH_1);
6837 target = expand_builtin_sync_operation (mode, exp, AND,
6838 true, target, ignore);
6839 if (target)
6840 return target;
6841 break;
6843 case BUILT_IN_XOR_AND_FETCH_1:
6844 case BUILT_IN_XOR_AND_FETCH_2:
6845 case BUILT_IN_XOR_AND_FETCH_4:
6846 case BUILT_IN_XOR_AND_FETCH_8:
6847 case BUILT_IN_XOR_AND_FETCH_16:
6848 mode = get_builtin_sync_mode (fcode - BUILT_IN_XOR_AND_FETCH_1);
6849 target = expand_builtin_sync_operation (mode, exp, XOR,
6850 true, target, ignore);
6851 if (target)
6852 return target;
6853 break;
6855 case BUILT_IN_NAND_AND_FETCH_1:
6856 case BUILT_IN_NAND_AND_FETCH_2:
6857 case BUILT_IN_NAND_AND_FETCH_4:
6858 case BUILT_IN_NAND_AND_FETCH_8:
6859 case BUILT_IN_NAND_AND_FETCH_16:
6860 mode = get_builtin_sync_mode (fcode - BUILT_IN_NAND_AND_FETCH_1);
6861 target = expand_builtin_sync_operation (mode, exp, NOT,
6862 true, target, ignore);
6863 if (target)
6864 return target;
6865 break;
6867 case BUILT_IN_BOOL_COMPARE_AND_SWAP_1:
6868 case BUILT_IN_BOOL_COMPARE_AND_SWAP_2:
6869 case BUILT_IN_BOOL_COMPARE_AND_SWAP_4:
6870 case BUILT_IN_BOOL_COMPARE_AND_SWAP_8:
6871 case BUILT_IN_BOOL_COMPARE_AND_SWAP_16:
6872 if (mode == VOIDmode)
6873 mode = TYPE_MODE (boolean_type_node);
6874 if (!target || !register_operand (target, mode))
6875 target = gen_reg_rtx (mode);
6877 mode = get_builtin_sync_mode (fcode - BUILT_IN_BOOL_COMPARE_AND_SWAP_1);
6878 target = expand_builtin_compare_and_swap (mode, exp, true, target);
6879 if (target)
6880 return target;
6881 break;
6883 case BUILT_IN_VAL_COMPARE_AND_SWAP_1:
6884 case BUILT_IN_VAL_COMPARE_AND_SWAP_2:
6885 case BUILT_IN_VAL_COMPARE_AND_SWAP_4:
6886 case BUILT_IN_VAL_COMPARE_AND_SWAP_8:
6887 case BUILT_IN_VAL_COMPARE_AND_SWAP_16:
6888 mode = get_builtin_sync_mode (fcode - BUILT_IN_VAL_COMPARE_AND_SWAP_1);
6889 target = expand_builtin_compare_and_swap (mode, exp, false, target);
6890 if (target)
6891 return target;
6892 break;
6894 case BUILT_IN_LOCK_TEST_AND_SET_1:
6895 case BUILT_IN_LOCK_TEST_AND_SET_2:
6896 case BUILT_IN_LOCK_TEST_AND_SET_4:
6897 case BUILT_IN_LOCK_TEST_AND_SET_8:
6898 case BUILT_IN_LOCK_TEST_AND_SET_16:
6899 mode = get_builtin_sync_mode (fcode - BUILT_IN_LOCK_TEST_AND_SET_1);
6900 target = expand_builtin_lock_test_and_set (mode, exp, target);
6901 if (target)
6902 return target;
6903 break;
6905 case BUILT_IN_LOCK_RELEASE_1:
6906 case BUILT_IN_LOCK_RELEASE_2:
6907 case BUILT_IN_LOCK_RELEASE_4:
6908 case BUILT_IN_LOCK_RELEASE_8:
6909 case BUILT_IN_LOCK_RELEASE_16:
6910 mode = get_builtin_sync_mode (fcode - BUILT_IN_LOCK_RELEASE_1);
6911 expand_builtin_lock_release (mode, exp);
6912 return const0_rtx;
6914 case BUILT_IN_SYNCHRONIZE:
6915 expand_builtin_synchronize ();
6916 return const0_rtx;
6918 case BUILT_IN_OBJECT_SIZE:
6919 return expand_builtin_object_size (exp);
6921 case BUILT_IN_MEMCPY_CHK:
6922 case BUILT_IN_MEMPCPY_CHK:
6923 case BUILT_IN_MEMMOVE_CHK:
6924 case BUILT_IN_MEMSET_CHK:
6925 target = expand_builtin_memory_chk (exp, target, mode, fcode);
6926 if (target)
6927 return target;
6928 break;
6930 case BUILT_IN_STRCPY_CHK:
6931 case BUILT_IN_STPCPY_CHK:
6932 case BUILT_IN_STRNCPY_CHK:
6933 case BUILT_IN_STRCAT_CHK:
6934 case BUILT_IN_STRNCAT_CHK:
6935 case BUILT_IN_SNPRINTF_CHK:
6936 case BUILT_IN_VSNPRINTF_CHK:
6937 maybe_emit_chk_warning (exp, fcode);
6938 break;
6940 case BUILT_IN_SPRINTF_CHK:
6941 case BUILT_IN_VSPRINTF_CHK:
6942 maybe_emit_sprintf_chk_warning (exp, fcode);
6943 break;
6945 default: /* just do library call, if unknown builtin */
6946 break;
6949 /* The switch statement above can drop through to cause the function
6950 to be called normally. */
6951 return expand_call (exp, target, ignore);
6954 /* Determine whether a tree node represents a call to a built-in
6955 function. If the tree T is a call to a built-in function with
6956 the right number of arguments of the appropriate types, return
6957 the DECL_FUNCTION_CODE of the call, e.g. BUILT_IN_SQRT.
6958 Otherwise the return value is END_BUILTINS. */
6960 enum built_in_function
6961 builtin_mathfn_code (const_tree t)
6963 const_tree fndecl, arg, parmlist;
6964 const_tree argtype, parmtype;
6965 const_call_expr_arg_iterator iter;
6967 if (TREE_CODE (t) != CALL_EXPR
6968 || TREE_CODE (CALL_EXPR_FN (t)) != ADDR_EXPR)
6969 return END_BUILTINS;
6971 fndecl = get_callee_fndecl (t);
6972 if (fndecl == NULL_TREE
6973 || TREE_CODE (fndecl) != FUNCTION_DECL
6974 || ! DECL_BUILT_IN (fndecl)
6975 || DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
6976 return END_BUILTINS;
6978 parmlist = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
6979 init_const_call_expr_arg_iterator (t, &iter);
6980 for (; parmlist; parmlist = TREE_CHAIN (parmlist))
6982 /* If a function doesn't take a variable number of arguments,
6983 the last element in the list will have type `void'. */
6984 parmtype = TREE_VALUE (parmlist);
6985 if (VOID_TYPE_P (parmtype))
6987 if (more_const_call_expr_args_p (&iter))
6988 return END_BUILTINS;
6989 return DECL_FUNCTION_CODE (fndecl);
6992 if (! more_const_call_expr_args_p (&iter))
6993 return END_BUILTINS;
6995 arg = next_const_call_expr_arg (&iter);
6996 argtype = TREE_TYPE (arg);
6998 if (SCALAR_FLOAT_TYPE_P (parmtype))
7000 if (! SCALAR_FLOAT_TYPE_P (argtype))
7001 return END_BUILTINS;
7003 else if (COMPLEX_FLOAT_TYPE_P (parmtype))
7005 if (! COMPLEX_FLOAT_TYPE_P (argtype))
7006 return END_BUILTINS;
7008 else if (POINTER_TYPE_P (parmtype))
7010 if (! POINTER_TYPE_P (argtype))
7011 return END_BUILTINS;
7013 else if (INTEGRAL_TYPE_P (parmtype))
7015 if (! INTEGRAL_TYPE_P (argtype))
7016 return END_BUILTINS;
7018 else
7019 return END_BUILTINS;
7022 /* Variable-length argument list. */
7023 return DECL_FUNCTION_CODE (fndecl);
7026 /* Fold a call to __builtin_constant_p, if we know its argument ARG will
7027 evaluate to a constant. */
7029 static tree
7030 fold_builtin_constant_p (tree arg)
7032 /* We return 1 for a numeric type that's known to be a constant
7033 value at compile-time or for an aggregate type that's a
7034 literal constant. */
7035 STRIP_NOPS (arg);
7037 /* If we know this is a constant, emit the constant of one. */
7038 if (CONSTANT_CLASS_P (arg)
7039 || (TREE_CODE (arg) == CONSTRUCTOR
7040 && TREE_CONSTANT (arg)))
7041 return integer_one_node;
7042 if (TREE_CODE (arg) == ADDR_EXPR)
7044 tree op = TREE_OPERAND (arg, 0);
7045 if (TREE_CODE (op) == STRING_CST
7046 || (TREE_CODE (op) == ARRAY_REF
7047 && integer_zerop (TREE_OPERAND (op, 1))
7048 && TREE_CODE (TREE_OPERAND (op, 0)) == STRING_CST))
7049 return integer_one_node;
7052 /* If this expression has side effects, show we don't know it to be a
7053 constant. Likewise if it's a pointer or aggregate type since in
7054 those case we only want literals, since those are only optimized
7055 when generating RTL, not later.
7056 And finally, if we are compiling an initializer, not code, we
7057 need to return a definite result now; there's not going to be any
7058 more optimization done. */
7059 if (TREE_SIDE_EFFECTS (arg)
7060 || AGGREGATE_TYPE_P (TREE_TYPE (arg))
7061 || POINTER_TYPE_P (TREE_TYPE (arg))
7062 || cfun == 0
7063 || folding_initializer)
7064 return integer_zero_node;
7066 return NULL_TREE;
7069 /* Create builtin_expect with PRED and EXPECTED as its arguments and
7070 return it as a truthvalue. */
7072 static tree
7073 build_builtin_expect_predicate (tree pred, tree expected)
7075 tree fn, arg_types, pred_type, expected_type, call_expr, ret_type;
7077 fn = built_in_decls[BUILT_IN_EXPECT];
7078 arg_types = TYPE_ARG_TYPES (TREE_TYPE (fn));
7079 ret_type = TREE_TYPE (TREE_TYPE (fn));
7080 pred_type = TREE_VALUE (arg_types);
7081 expected_type = TREE_VALUE (TREE_CHAIN (arg_types));
7083 pred = fold_convert (pred_type, pred);
7084 expected = fold_convert (expected_type, expected);
7085 call_expr = build_call_expr (fn, 2, pred, expected);
7087 return build2 (NE_EXPR, TREE_TYPE (pred), call_expr,
7088 build_int_cst (ret_type, 0));
7091 /* Fold a call to builtin_expect with arguments ARG0 and ARG1. Return
7092 NULL_TREE if no simplification is possible. */
7094 static tree
7095 fold_builtin_expect (tree arg0, tree arg1)
7097 tree inner, fndecl;
7098 enum tree_code code;
7100 /* If this is a builtin_expect within a builtin_expect keep the
7101 inner one. See through a comparison against a constant. It
7102 might have been added to create a thruthvalue. */
7103 inner = arg0;
7104 if (COMPARISON_CLASS_P (inner)
7105 && TREE_CODE (TREE_OPERAND (inner, 1)) == INTEGER_CST)
7106 inner = TREE_OPERAND (inner, 0);
7108 if (TREE_CODE (inner) == CALL_EXPR
7109 && (fndecl = get_callee_fndecl (inner))
7110 && DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL
7111 && DECL_FUNCTION_CODE (fndecl) == BUILT_IN_EXPECT)
7112 return arg0;
7114 /* Distribute the expected value over short-circuiting operators.
7115 See through the cast from truthvalue_type_node to long. */
7116 inner = arg0;
7117 while (TREE_CODE (inner) == NOP_EXPR
7118 && INTEGRAL_TYPE_P (TREE_TYPE (inner))
7119 && INTEGRAL_TYPE_P (TREE_TYPE (TREE_OPERAND (inner, 0))))
7120 inner = TREE_OPERAND (inner, 0);
7122 code = TREE_CODE (inner);
7123 if (code == TRUTH_ANDIF_EXPR || code == TRUTH_ORIF_EXPR)
7125 tree op0 = TREE_OPERAND (inner, 0);
7126 tree op1 = TREE_OPERAND (inner, 1);
7128 op0 = build_builtin_expect_predicate (op0, arg1);
7129 op1 = build_builtin_expect_predicate (op1, arg1);
7130 inner = build2 (code, TREE_TYPE (inner), op0, op1);
7132 return fold_convert (TREE_TYPE (arg0), inner);
7135 /* If the argument isn't invariant then there's nothing else we can do. */
7136 if (!TREE_INVARIANT (arg0))
7137 return NULL_TREE;
7139 /* If we expect that a comparison against the argument will fold to
7140 a constant return the constant. In practice, this means a true
7141 constant or the address of a non-weak symbol. */
7142 inner = arg0;
7143 STRIP_NOPS (inner);
7144 if (TREE_CODE (inner) == ADDR_EXPR)
7148 inner = TREE_OPERAND (inner, 0);
7150 while (TREE_CODE (inner) == COMPONENT_REF
7151 || TREE_CODE (inner) == ARRAY_REF);
7152 if (DECL_P (inner) && DECL_WEAK (inner))
7153 return NULL_TREE;
7156 /* Otherwise, ARG0 already has the proper type for the return value. */
7157 return arg0;
7160 /* Fold a call to __builtin_classify_type with argument ARG. */
7162 static tree
7163 fold_builtin_classify_type (tree arg)
7165 if (arg == 0)
7166 return build_int_cst (NULL_TREE, no_type_class);
7168 return build_int_cst (NULL_TREE, type_to_class (TREE_TYPE (arg)));
7171 /* Fold a call to __builtin_strlen with argument ARG. */
7173 static tree
7174 fold_builtin_strlen (tree arg)
7176 if (!validate_arg (arg, POINTER_TYPE))
7177 return NULL_TREE;
7178 else
7180 tree len = c_strlen (arg, 0);
7182 if (len)
7184 /* Convert from the internal "sizetype" type to "size_t". */
7185 if (size_type_node)
7186 len = fold_convert (size_type_node, len);
7187 return len;
7190 return NULL_TREE;
7194 /* Fold a call to __builtin_inf or __builtin_huge_val. */
7196 static tree
7197 fold_builtin_inf (tree type, int warn)
7199 REAL_VALUE_TYPE real;
7201 /* __builtin_inff is intended to be usable to define INFINITY on all
7202 targets. If an infinity is not available, INFINITY expands "to a
7203 positive constant of type float that overflows at translation
7204 time", footnote "In this case, using INFINITY will violate the
7205 constraint in 6.4.4 and thus require a diagnostic." (C99 7.12#4).
7206 Thus we pedwarn to ensure this constraint violation is
7207 diagnosed. */
7208 if (!MODE_HAS_INFINITIES (TYPE_MODE (type)) && warn)
7209 pedwarn ("target format does not support infinity");
7211 real_inf (&real);
7212 return build_real (type, real);
7215 /* Fold a call to __builtin_nan or __builtin_nans with argument ARG. */
7217 static tree
7218 fold_builtin_nan (tree arg, tree type, int quiet)
7220 REAL_VALUE_TYPE real;
7221 const char *str;
7223 if (!validate_arg (arg, POINTER_TYPE))
7224 return NULL_TREE;
7225 str = c_getstr (arg);
7226 if (!str)
7227 return NULL_TREE;
7229 if (!real_nan (&real, str, quiet, TYPE_MODE (type)))
7230 return NULL_TREE;
7232 return build_real (type, real);
7235 /* Return true if the floating point expression T has an integer value.
7236 We also allow +Inf, -Inf and NaN to be considered integer values. */
7238 static bool
7239 integer_valued_real_p (tree t)
7241 switch (TREE_CODE (t))
7243 case FLOAT_EXPR:
7244 return true;
7246 case ABS_EXPR:
7247 case SAVE_EXPR:
7248 case NON_LVALUE_EXPR:
7249 return integer_valued_real_p (TREE_OPERAND (t, 0));
7251 case COMPOUND_EXPR:
7252 case MODIFY_EXPR:
7253 case BIND_EXPR:
7254 return integer_valued_real_p (GENERIC_TREE_OPERAND (t, 1));
7256 case PLUS_EXPR:
7257 case MINUS_EXPR:
7258 case MULT_EXPR:
7259 case MIN_EXPR:
7260 case MAX_EXPR:
7261 return integer_valued_real_p (TREE_OPERAND (t, 0))
7262 && integer_valued_real_p (TREE_OPERAND (t, 1));
7264 case COND_EXPR:
7265 return integer_valued_real_p (TREE_OPERAND (t, 1))
7266 && integer_valued_real_p (TREE_OPERAND (t, 2));
7268 case REAL_CST:
7269 return real_isinteger (TREE_REAL_CST_PTR (t), TYPE_MODE (TREE_TYPE (t)));
7271 case NOP_EXPR:
7273 tree type = TREE_TYPE (TREE_OPERAND (t, 0));
7274 if (TREE_CODE (type) == INTEGER_TYPE)
7275 return true;
7276 if (TREE_CODE (type) == REAL_TYPE)
7277 return integer_valued_real_p (TREE_OPERAND (t, 0));
7278 break;
7281 case CALL_EXPR:
7282 switch (builtin_mathfn_code (t))
7284 CASE_FLT_FN (BUILT_IN_CEIL):
7285 CASE_FLT_FN (BUILT_IN_FLOOR):
7286 CASE_FLT_FN (BUILT_IN_NEARBYINT):
7287 CASE_FLT_FN (BUILT_IN_RINT):
7288 CASE_FLT_FN (BUILT_IN_ROUND):
7289 CASE_FLT_FN (BUILT_IN_TRUNC):
7290 return true;
7292 CASE_FLT_FN (BUILT_IN_FMIN):
7293 CASE_FLT_FN (BUILT_IN_FMAX):
7294 return integer_valued_real_p (CALL_EXPR_ARG (t, 0))
7295 && integer_valued_real_p (CALL_EXPR_ARG (t, 1));
7297 default:
7298 break;
7300 break;
7302 default:
7303 break;
7305 return false;
7308 /* FNDECL is assumed to be a builtin where truncation can be propagated
7309 across (for instance floor((double)f) == (double)floorf (f).
7310 Do the transformation for a call with argument ARG. */
7312 static tree
7313 fold_trunc_transparent_mathfn (tree fndecl, tree arg)
7315 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
7317 if (!validate_arg (arg, REAL_TYPE))
7318 return NULL_TREE;
7320 /* Integer rounding functions are idempotent. */
7321 if (fcode == builtin_mathfn_code (arg))
7322 return arg;
7324 /* If argument is already integer valued, and we don't need to worry
7325 about setting errno, there's no need to perform rounding. */
7326 if (! flag_errno_math && integer_valued_real_p (arg))
7327 return arg;
7329 if (optimize)
7331 tree arg0 = strip_float_extensions (arg);
7332 tree ftype = TREE_TYPE (TREE_TYPE (fndecl));
7333 tree newtype = TREE_TYPE (arg0);
7334 tree decl;
7336 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
7337 && (decl = mathfn_built_in (newtype, fcode)))
7338 return fold_convert (ftype,
7339 build_call_expr (decl, 1,
7340 fold_convert (newtype, arg0)));
7342 return NULL_TREE;
7345 /* FNDECL is assumed to be builtin which can narrow the FP type of
7346 the argument, for instance lround((double)f) -> lroundf (f).
7347 Do the transformation for a call with argument ARG. */
7349 static tree
7350 fold_fixed_mathfn (tree fndecl, tree arg)
7352 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
7354 if (!validate_arg (arg, REAL_TYPE))
7355 return NULL_TREE;
7357 /* If argument is already integer valued, and we don't need to worry
7358 about setting errno, there's no need to perform rounding. */
7359 if (! flag_errno_math && integer_valued_real_p (arg))
7360 return fold_build1 (FIX_TRUNC_EXPR, TREE_TYPE (TREE_TYPE (fndecl)), arg);
7362 if (optimize)
7364 tree ftype = TREE_TYPE (arg);
7365 tree arg0 = strip_float_extensions (arg);
7366 tree newtype = TREE_TYPE (arg0);
7367 tree decl;
7369 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
7370 && (decl = mathfn_built_in (newtype, fcode)))
7371 return build_call_expr (decl, 1, fold_convert (newtype, arg0));
7374 /* Canonicalize llround (x) to lround (x) on LP64 targets where
7375 sizeof (long long) == sizeof (long). */
7376 if (TYPE_PRECISION (long_long_integer_type_node)
7377 == TYPE_PRECISION (long_integer_type_node))
7379 tree newfn = NULL_TREE;
7380 switch (fcode)
7382 CASE_FLT_FN (BUILT_IN_LLCEIL):
7383 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LCEIL);
7384 break;
7386 CASE_FLT_FN (BUILT_IN_LLFLOOR):
7387 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LFLOOR);
7388 break;
7390 CASE_FLT_FN (BUILT_IN_LLROUND):
7391 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LROUND);
7392 break;
7394 CASE_FLT_FN (BUILT_IN_LLRINT):
7395 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LRINT);
7396 break;
7398 default:
7399 break;
7402 if (newfn)
7404 tree newcall = build_call_expr(newfn, 1, arg);
7405 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), newcall);
7409 return NULL_TREE;
7412 /* Fold call to builtin cabs, cabsf or cabsl with argument ARG. TYPE is the
7413 return type. Return NULL_TREE if no simplification can be made. */
7415 static tree
7416 fold_builtin_cabs (tree arg, tree type, tree fndecl)
7418 tree res;
7420 if (TREE_CODE (TREE_TYPE (arg)) != COMPLEX_TYPE
7421 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
7422 return NULL_TREE;
7424 /* Calculate the result when the argument is a constant. */
7425 if (TREE_CODE (arg) == COMPLEX_CST
7426 && (res = do_mpfr_arg2 (TREE_REALPART (arg), TREE_IMAGPART (arg),
7427 type, mpfr_hypot)))
7428 return res;
7430 if (TREE_CODE (arg) == COMPLEX_EXPR)
7432 tree real = TREE_OPERAND (arg, 0);
7433 tree imag = TREE_OPERAND (arg, 1);
7435 /* If either part is zero, cabs is fabs of the other. */
7436 if (real_zerop (real))
7437 return fold_build1 (ABS_EXPR, type, imag);
7438 if (real_zerop (imag))
7439 return fold_build1 (ABS_EXPR, type, real);
7441 /* cabs(x+xi) -> fabs(x)*sqrt(2). */
7442 if (flag_unsafe_math_optimizations
7443 && operand_equal_p (real, imag, OEP_PURE_SAME))
7445 const REAL_VALUE_TYPE sqrt2_trunc
7446 = real_value_truncate (TYPE_MODE (type), dconstsqrt2);
7447 STRIP_NOPS (real);
7448 return fold_build2 (MULT_EXPR, type,
7449 fold_build1 (ABS_EXPR, type, real),
7450 build_real (type, sqrt2_trunc));
7454 /* Optimize cabs(-z) and cabs(conj(z)) as cabs(z). */
7455 if (TREE_CODE (arg) == NEGATE_EXPR
7456 || TREE_CODE (arg) == CONJ_EXPR)
7457 return build_call_expr (fndecl, 1, TREE_OPERAND (arg, 0));
7459 /* Don't do this when optimizing for size. */
7460 if (flag_unsafe_math_optimizations
7461 && optimize && !optimize_size)
7463 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
7465 if (sqrtfn != NULL_TREE)
7467 tree rpart, ipart, result;
7469 arg = builtin_save_expr (arg);
7471 rpart = fold_build1 (REALPART_EXPR, type, arg);
7472 ipart = fold_build1 (IMAGPART_EXPR, type, arg);
7474 rpart = builtin_save_expr (rpart);
7475 ipart = builtin_save_expr (ipart);
7477 result = fold_build2 (PLUS_EXPR, type,
7478 fold_build2 (MULT_EXPR, type,
7479 rpart, rpart),
7480 fold_build2 (MULT_EXPR, type,
7481 ipart, ipart));
7483 return build_call_expr (sqrtfn, 1, result);
7487 return NULL_TREE;
7490 /* Fold a builtin function call to sqrt, sqrtf, or sqrtl with argument ARG.
7491 Return NULL_TREE if no simplification can be made. */
7493 static tree
7494 fold_builtin_sqrt (tree arg, tree type)
7497 enum built_in_function fcode;
7498 tree res;
7500 if (!validate_arg (arg, REAL_TYPE))
7501 return NULL_TREE;
7503 /* Calculate the result when the argument is a constant. */
7504 if ((res = do_mpfr_arg1 (arg, type, mpfr_sqrt, &dconst0, NULL, true)))
7505 return res;
7507 /* Optimize sqrt(expN(x)) = expN(x*0.5). */
7508 fcode = builtin_mathfn_code (arg);
7509 if (flag_unsafe_math_optimizations && BUILTIN_EXPONENT_P (fcode))
7511 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7512 arg = fold_build2 (MULT_EXPR, type,
7513 CALL_EXPR_ARG (arg, 0),
7514 build_real (type, dconsthalf));
7515 return build_call_expr (expfn, 1, arg);
7518 /* Optimize sqrt(Nroot(x)) -> pow(x,1/(2*N)). */
7519 if (flag_unsafe_math_optimizations && BUILTIN_ROOT_P (fcode))
7521 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7523 if (powfn)
7525 tree arg0 = CALL_EXPR_ARG (arg, 0);
7526 tree tree_root;
7527 /* The inner root was either sqrt or cbrt. */
7528 REAL_VALUE_TYPE dconstroot =
7529 BUILTIN_SQRT_P (fcode) ? dconsthalf : dconstthird;
7531 /* Adjust for the outer root. */
7532 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7533 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7534 tree_root = build_real (type, dconstroot);
7535 return build_call_expr (powfn, 2, arg0, tree_root);
7539 /* Optimize sqrt(pow(x,y)) = pow(|x|,y*0.5). */
7540 if (flag_unsafe_math_optimizations
7541 && (fcode == BUILT_IN_POW
7542 || fcode == BUILT_IN_POWF
7543 || fcode == BUILT_IN_POWL))
7545 tree powfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7546 tree arg0 = CALL_EXPR_ARG (arg, 0);
7547 tree arg1 = CALL_EXPR_ARG (arg, 1);
7548 tree narg1;
7549 if (!tree_expr_nonnegative_p (arg0))
7550 arg0 = build1 (ABS_EXPR, type, arg0);
7551 narg1 = fold_build2 (MULT_EXPR, type, arg1,
7552 build_real (type, dconsthalf));
7553 return build_call_expr (powfn, 2, arg0, narg1);
7556 return NULL_TREE;
7559 /* Fold a builtin function call to cbrt, cbrtf, or cbrtl with argument ARG.
7560 Return NULL_TREE if no simplification can be made. */
7562 static tree
7563 fold_builtin_cbrt (tree arg, tree type)
7565 const enum built_in_function fcode = builtin_mathfn_code (arg);
7566 tree res;
7568 if (!validate_arg (arg, REAL_TYPE))
7569 return NULL_TREE;
7571 /* Calculate the result when the argument is a constant. */
7572 if ((res = do_mpfr_arg1 (arg, type, mpfr_cbrt, NULL, NULL, 0)))
7573 return res;
7575 if (flag_unsafe_math_optimizations)
7577 /* Optimize cbrt(expN(x)) -> expN(x/3). */
7578 if (BUILTIN_EXPONENT_P (fcode))
7580 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7581 const REAL_VALUE_TYPE third_trunc =
7582 real_value_truncate (TYPE_MODE (type), dconstthird);
7583 arg = fold_build2 (MULT_EXPR, type,
7584 CALL_EXPR_ARG (arg, 0),
7585 build_real (type, third_trunc));
7586 return build_call_expr (expfn, 1, arg);
7589 /* Optimize cbrt(sqrt(x)) -> pow(x,1/6). */
7590 if (BUILTIN_SQRT_P (fcode))
7592 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7594 if (powfn)
7596 tree arg0 = CALL_EXPR_ARG (arg, 0);
7597 tree tree_root;
7598 REAL_VALUE_TYPE dconstroot = dconstthird;
7600 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7601 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7602 tree_root = build_real (type, dconstroot);
7603 return build_call_expr (powfn, 2, arg0, tree_root);
7607 /* Optimize cbrt(cbrt(x)) -> pow(x,1/9) iff x is nonnegative. */
7608 if (BUILTIN_CBRT_P (fcode))
7610 tree arg0 = CALL_EXPR_ARG (arg, 0);
7611 if (tree_expr_nonnegative_p (arg0))
7613 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7615 if (powfn)
7617 tree tree_root;
7618 REAL_VALUE_TYPE dconstroot;
7620 real_arithmetic (&dconstroot, MULT_EXPR, &dconstthird, &dconstthird);
7621 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7622 tree_root = build_real (type, dconstroot);
7623 return build_call_expr (powfn, 2, arg0, tree_root);
7628 /* Optimize cbrt(pow(x,y)) -> pow(x,y/3) iff x is nonnegative. */
7629 if (fcode == BUILT_IN_POW
7630 || fcode == BUILT_IN_POWF
7631 || fcode == BUILT_IN_POWL)
7633 tree arg00 = CALL_EXPR_ARG (arg, 0);
7634 tree arg01 = CALL_EXPR_ARG (arg, 1);
7635 if (tree_expr_nonnegative_p (arg00))
7637 tree powfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7638 const REAL_VALUE_TYPE dconstroot
7639 = real_value_truncate (TYPE_MODE (type), dconstthird);
7640 tree narg01 = fold_build2 (MULT_EXPR, type, arg01,
7641 build_real (type, dconstroot));
7642 return build_call_expr (powfn, 2, arg00, narg01);
7646 return NULL_TREE;
7649 /* Fold function call to builtin cos, cosf, or cosl with argument ARG.
7650 TYPE is the type of the return value. Return NULL_TREE if no
7651 simplification can be made. */
7653 static tree
7654 fold_builtin_cos (tree arg, tree type, tree fndecl)
7656 tree res, narg;
7658 if (!validate_arg (arg, REAL_TYPE))
7659 return NULL_TREE;
7661 /* Calculate the result when the argument is a constant. */
7662 if ((res = do_mpfr_arg1 (arg, type, mpfr_cos, NULL, NULL, 0)))
7663 return res;
7665 /* Optimize cos(-x) into cos (x). */
7666 if ((narg = fold_strip_sign_ops (arg)))
7667 return build_call_expr (fndecl, 1, narg);
7669 return NULL_TREE;
7672 /* Fold function call to builtin cosh, coshf, or coshl with argument ARG.
7673 Return NULL_TREE if no simplification can be made. */
7675 static tree
7676 fold_builtin_cosh (tree arg, tree type, tree fndecl)
7678 if (validate_arg (arg, REAL_TYPE))
7680 tree res, narg;
7682 /* Calculate the result when the argument is a constant. */
7683 if ((res = do_mpfr_arg1 (arg, type, mpfr_cosh, NULL, NULL, 0)))
7684 return res;
7686 /* Optimize cosh(-x) into cosh (x). */
7687 if ((narg = fold_strip_sign_ops (arg)))
7688 return build_call_expr (fndecl, 1, narg);
7691 return NULL_TREE;
7694 /* Fold function call to builtin tan, tanf, or tanl with argument ARG.
7695 Return NULL_TREE if no simplification can be made. */
7697 static tree
7698 fold_builtin_tan (tree arg, tree type)
7700 enum built_in_function fcode;
7701 tree res;
7703 if (!validate_arg (arg, REAL_TYPE))
7704 return NULL_TREE;
7706 /* Calculate the result when the argument is a constant. */
7707 if ((res = do_mpfr_arg1 (arg, type, mpfr_tan, NULL, NULL, 0)))
7708 return res;
7710 /* Optimize tan(atan(x)) = x. */
7711 fcode = builtin_mathfn_code (arg);
7712 if (flag_unsafe_math_optimizations
7713 && (fcode == BUILT_IN_ATAN
7714 || fcode == BUILT_IN_ATANF
7715 || fcode == BUILT_IN_ATANL))
7716 return CALL_EXPR_ARG (arg, 0);
7718 return NULL_TREE;
7721 /* Fold function call to builtin sincos, sincosf, or sincosl. Return
7722 NULL_TREE if no simplification can be made. */
7724 static tree
7725 fold_builtin_sincos (tree arg0, tree arg1, tree arg2)
7727 tree type;
7728 tree res, fn, call;
7730 if (!validate_arg (arg0, REAL_TYPE)
7731 || !validate_arg (arg1, POINTER_TYPE)
7732 || !validate_arg (arg2, POINTER_TYPE))
7733 return NULL_TREE;
7735 type = TREE_TYPE (arg0);
7737 /* Calculate the result when the argument is a constant. */
7738 if ((res = do_mpfr_sincos (arg0, arg1, arg2)))
7739 return res;
7741 /* Canonicalize sincos to cexpi. */
7742 if (!TARGET_C99_FUNCTIONS)
7743 return NULL_TREE;
7744 fn = mathfn_built_in (type, BUILT_IN_CEXPI);
7745 if (!fn)
7746 return NULL_TREE;
7748 call = build_call_expr (fn, 1, arg0);
7749 call = builtin_save_expr (call);
7751 return build2 (COMPOUND_EXPR, type,
7752 build2 (MODIFY_EXPR, void_type_node,
7753 build_fold_indirect_ref (arg1),
7754 build1 (IMAGPART_EXPR, type, call)),
7755 build2 (MODIFY_EXPR, void_type_node,
7756 build_fold_indirect_ref (arg2),
7757 build1 (REALPART_EXPR, type, call)));
7760 /* Fold function call to builtin cexp, cexpf, or cexpl. Return
7761 NULL_TREE if no simplification can be made. */
7763 static tree
7764 fold_builtin_cexp (tree arg0, tree type)
7766 tree rtype;
7767 tree realp, imagp, ifn;
7769 if (!validate_arg (arg0, COMPLEX_TYPE))
7770 return NULL_TREE;
7772 rtype = TREE_TYPE (TREE_TYPE (arg0));
7774 /* In case we can figure out the real part of arg0 and it is constant zero
7775 fold to cexpi. */
7776 if (!TARGET_C99_FUNCTIONS)
7777 return NULL_TREE;
7778 ifn = mathfn_built_in (rtype, BUILT_IN_CEXPI);
7779 if (!ifn)
7780 return NULL_TREE;
7782 if ((realp = fold_unary (REALPART_EXPR, rtype, arg0))
7783 && real_zerop (realp))
7785 tree narg = fold_build1 (IMAGPART_EXPR, rtype, arg0);
7786 return build_call_expr (ifn, 1, narg);
7789 /* In case we can easily decompose real and imaginary parts split cexp
7790 to exp (r) * cexpi (i). */
7791 if (flag_unsafe_math_optimizations
7792 && realp)
7794 tree rfn, rcall, icall;
7796 rfn = mathfn_built_in (rtype, BUILT_IN_EXP);
7797 if (!rfn)
7798 return NULL_TREE;
7800 imagp = fold_unary (IMAGPART_EXPR, rtype, arg0);
7801 if (!imagp)
7802 return NULL_TREE;
7804 icall = build_call_expr (ifn, 1, imagp);
7805 icall = builtin_save_expr (icall);
7806 rcall = build_call_expr (rfn, 1, realp);
7807 rcall = builtin_save_expr (rcall);
7808 return fold_build2 (COMPLEX_EXPR, type,
7809 fold_build2 (MULT_EXPR, rtype,
7810 rcall,
7811 fold_build1 (REALPART_EXPR, rtype, icall)),
7812 fold_build2 (MULT_EXPR, rtype,
7813 rcall,
7814 fold_build1 (IMAGPART_EXPR, rtype, icall)));
7817 return NULL_TREE;
7820 /* Fold function call to builtin trunc, truncf or truncl with argument ARG.
7821 Return NULL_TREE if no simplification can be made. */
7823 static tree
7824 fold_builtin_trunc (tree fndecl, tree arg)
7826 if (!validate_arg (arg, REAL_TYPE))
7827 return NULL_TREE;
7829 /* Optimize trunc of constant value. */
7830 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7832 REAL_VALUE_TYPE r, x;
7833 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7835 x = TREE_REAL_CST (arg);
7836 real_trunc (&r, TYPE_MODE (type), &x);
7837 return build_real (type, r);
7840 return fold_trunc_transparent_mathfn (fndecl, arg);
7843 /* Fold function call to builtin floor, floorf or floorl with argument ARG.
7844 Return NULL_TREE if no simplification can be made. */
7846 static tree
7847 fold_builtin_floor (tree fndecl, tree arg)
7849 if (!validate_arg (arg, REAL_TYPE))
7850 return NULL_TREE;
7852 /* Optimize floor of constant value. */
7853 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7855 REAL_VALUE_TYPE x;
7857 x = TREE_REAL_CST (arg);
7858 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7860 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7861 REAL_VALUE_TYPE r;
7863 real_floor (&r, TYPE_MODE (type), &x);
7864 return build_real (type, r);
7868 /* Fold floor (x) where x is nonnegative to trunc (x). */
7869 if (tree_expr_nonnegative_p (arg))
7871 tree truncfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_TRUNC);
7872 if (truncfn)
7873 return build_call_expr (truncfn, 1, arg);
7876 return fold_trunc_transparent_mathfn (fndecl, arg);
7879 /* Fold function call to builtin ceil, ceilf or ceill with argument ARG.
7880 Return NULL_TREE if no simplification can be made. */
7882 static tree
7883 fold_builtin_ceil (tree fndecl, tree arg)
7885 if (!validate_arg (arg, REAL_TYPE))
7886 return NULL_TREE;
7888 /* Optimize ceil of constant value. */
7889 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7891 REAL_VALUE_TYPE x;
7893 x = TREE_REAL_CST (arg);
7894 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7896 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7897 REAL_VALUE_TYPE r;
7899 real_ceil (&r, TYPE_MODE (type), &x);
7900 return build_real (type, r);
7904 return fold_trunc_transparent_mathfn (fndecl, arg);
7907 /* Fold function call to builtin round, roundf or roundl with argument ARG.
7908 Return NULL_TREE if no simplification can be made. */
7910 static tree
7911 fold_builtin_round (tree fndecl, tree arg)
7913 if (!validate_arg (arg, REAL_TYPE))
7914 return NULL_TREE;
7916 /* Optimize round of constant value. */
7917 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7919 REAL_VALUE_TYPE x;
7921 x = TREE_REAL_CST (arg);
7922 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7924 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7925 REAL_VALUE_TYPE r;
7927 real_round (&r, TYPE_MODE (type), &x);
7928 return build_real (type, r);
7932 return fold_trunc_transparent_mathfn (fndecl, arg);
7935 /* Fold function call to builtin lround, lroundf or lroundl (or the
7936 corresponding long long versions) and other rounding functions. ARG
7937 is the argument to the call. Return NULL_TREE if no simplification
7938 can be made. */
7940 static tree
7941 fold_builtin_int_roundingfn (tree fndecl, tree arg)
7943 if (!validate_arg (arg, REAL_TYPE))
7944 return NULL_TREE;
7946 /* Optimize lround of constant value. */
7947 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7949 const REAL_VALUE_TYPE x = TREE_REAL_CST (arg);
7951 if (real_isfinite (&x))
7953 tree itype = TREE_TYPE (TREE_TYPE (fndecl));
7954 tree ftype = TREE_TYPE (arg);
7955 unsigned HOST_WIDE_INT lo2;
7956 HOST_WIDE_INT hi, lo;
7957 REAL_VALUE_TYPE r;
7959 switch (DECL_FUNCTION_CODE (fndecl))
7961 CASE_FLT_FN (BUILT_IN_LFLOOR):
7962 CASE_FLT_FN (BUILT_IN_LLFLOOR):
7963 real_floor (&r, TYPE_MODE (ftype), &x);
7964 break;
7966 CASE_FLT_FN (BUILT_IN_LCEIL):
7967 CASE_FLT_FN (BUILT_IN_LLCEIL):
7968 real_ceil (&r, TYPE_MODE (ftype), &x);
7969 break;
7971 CASE_FLT_FN (BUILT_IN_LROUND):
7972 CASE_FLT_FN (BUILT_IN_LLROUND):
7973 real_round (&r, TYPE_MODE (ftype), &x);
7974 break;
7976 default:
7977 gcc_unreachable ();
7980 REAL_VALUE_TO_INT (&lo, &hi, r);
7981 if (!fit_double_type (lo, hi, &lo2, &hi, itype))
7982 return build_int_cst_wide (itype, lo2, hi);
7986 switch (DECL_FUNCTION_CODE (fndecl))
7988 CASE_FLT_FN (BUILT_IN_LFLOOR):
7989 CASE_FLT_FN (BUILT_IN_LLFLOOR):
7990 /* Fold lfloor (x) where x is nonnegative to FIX_TRUNC (x). */
7991 if (tree_expr_nonnegative_p (arg))
7992 return fold_build1 (FIX_TRUNC_EXPR, TREE_TYPE (TREE_TYPE (fndecl)),
7993 arg);
7994 break;
7995 default:;
7998 return fold_fixed_mathfn (fndecl, arg);
8001 /* Fold function call to builtin ffs, clz, ctz, popcount and parity
8002 and their long and long long variants (i.e. ffsl and ffsll). ARG is
8003 the argument to the call. Return NULL_TREE if no simplification can
8004 be made. */
8006 static tree
8007 fold_builtin_bitop (tree fndecl, tree arg)
8009 if (!validate_arg (arg, INTEGER_TYPE))
8010 return NULL_TREE;
8012 /* Optimize for constant argument. */
8013 if (TREE_CODE (arg) == INTEGER_CST && !TREE_OVERFLOW (arg))
8015 HOST_WIDE_INT hi, width, result;
8016 unsigned HOST_WIDE_INT lo;
8017 tree type;
8019 type = TREE_TYPE (arg);
8020 width = TYPE_PRECISION (type);
8021 lo = TREE_INT_CST_LOW (arg);
8023 /* Clear all the bits that are beyond the type's precision. */
8024 if (width > HOST_BITS_PER_WIDE_INT)
8026 hi = TREE_INT_CST_HIGH (arg);
8027 if (width < 2 * HOST_BITS_PER_WIDE_INT)
8028 hi &= ~((HOST_WIDE_INT) (-1) >> (width - HOST_BITS_PER_WIDE_INT));
8030 else
8032 hi = 0;
8033 if (width < HOST_BITS_PER_WIDE_INT)
8034 lo &= ~((unsigned HOST_WIDE_INT) (-1) << width);
8037 switch (DECL_FUNCTION_CODE (fndecl))
8039 CASE_INT_FN (BUILT_IN_FFS):
8040 if (lo != 0)
8041 result = exact_log2 (lo & -lo) + 1;
8042 else if (hi != 0)
8043 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi) + 1;
8044 else
8045 result = 0;
8046 break;
8048 CASE_INT_FN (BUILT_IN_CLZ):
8049 if (hi != 0)
8050 result = width - floor_log2 (hi) - 1 - HOST_BITS_PER_WIDE_INT;
8051 else if (lo != 0)
8052 result = width - floor_log2 (lo) - 1;
8053 else if (! CLZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
8054 result = width;
8055 break;
8057 CASE_INT_FN (BUILT_IN_CTZ):
8058 if (lo != 0)
8059 result = exact_log2 (lo & -lo);
8060 else if (hi != 0)
8061 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi);
8062 else if (! CTZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
8063 result = width;
8064 break;
8066 CASE_INT_FN (BUILT_IN_POPCOUNT):
8067 result = 0;
8068 while (lo)
8069 result++, lo &= lo - 1;
8070 while (hi)
8071 result++, hi &= hi - 1;
8072 break;
8074 CASE_INT_FN (BUILT_IN_PARITY):
8075 result = 0;
8076 while (lo)
8077 result++, lo &= lo - 1;
8078 while (hi)
8079 result++, hi &= hi - 1;
8080 result &= 1;
8081 break;
8083 default:
8084 gcc_unreachable ();
8087 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), result);
8090 return NULL_TREE;
8093 /* Fold function call to builtin_bswap and the long and long long
8094 variants. Return NULL_TREE if no simplification can be made. */
8095 static tree
8096 fold_builtin_bswap (tree fndecl, tree arg)
8098 if (! validate_arg (arg, INTEGER_TYPE))
8099 return NULL_TREE;
8101 /* Optimize constant value. */
8102 if (TREE_CODE (arg) == INTEGER_CST && !TREE_OVERFLOW (arg))
8104 HOST_WIDE_INT hi, width, r_hi = 0;
8105 unsigned HOST_WIDE_INT lo, r_lo = 0;
8106 tree type;
8108 type = TREE_TYPE (arg);
8109 width = TYPE_PRECISION (type);
8110 lo = TREE_INT_CST_LOW (arg);
8111 hi = TREE_INT_CST_HIGH (arg);
8113 switch (DECL_FUNCTION_CODE (fndecl))
8115 case BUILT_IN_BSWAP32:
8116 case BUILT_IN_BSWAP64:
8118 int s;
8120 for (s = 0; s < width; s += 8)
8122 int d = width - s - 8;
8123 unsigned HOST_WIDE_INT byte;
8125 if (s < HOST_BITS_PER_WIDE_INT)
8126 byte = (lo >> s) & 0xff;
8127 else
8128 byte = (hi >> (s - HOST_BITS_PER_WIDE_INT)) & 0xff;
8130 if (d < HOST_BITS_PER_WIDE_INT)
8131 r_lo |= byte << d;
8132 else
8133 r_hi |= byte << (d - HOST_BITS_PER_WIDE_INT);
8137 break;
8139 default:
8140 gcc_unreachable ();
8143 if (width < HOST_BITS_PER_WIDE_INT)
8144 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), r_lo);
8145 else
8146 return build_int_cst_wide (TREE_TYPE (TREE_TYPE (fndecl)), r_lo, r_hi);
8149 return NULL_TREE;
8152 /* Return true if EXPR is the real constant contained in VALUE. */
8154 static bool
8155 real_dconstp (tree expr, const REAL_VALUE_TYPE *value)
8157 STRIP_NOPS (expr);
8159 return ((TREE_CODE (expr) == REAL_CST
8160 && !TREE_OVERFLOW (expr)
8161 && REAL_VALUES_EQUAL (TREE_REAL_CST (expr), *value))
8162 || (TREE_CODE (expr) == COMPLEX_CST
8163 && real_dconstp (TREE_REALPART (expr), value)
8164 && real_zerop (TREE_IMAGPART (expr))));
8167 /* A subroutine of fold_builtin to fold the various logarithmic
8168 functions. Return NULL_TREE if no simplification can me made.
8169 FUNC is the corresponding MPFR logarithm function. */
8171 static tree
8172 fold_builtin_logarithm (tree fndecl, tree arg,
8173 int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t))
8175 if (validate_arg (arg, REAL_TYPE))
8177 tree type = TREE_TYPE (TREE_TYPE (fndecl));
8178 tree res;
8179 const enum built_in_function fcode = builtin_mathfn_code (arg);
8181 /* Optimize log(e) = 1.0. We're never passed an exact 'e',
8182 instead we'll look for 'e' truncated to MODE. So only do
8183 this if flag_unsafe_math_optimizations is set. */
8184 if (flag_unsafe_math_optimizations && func == mpfr_log)
8186 const REAL_VALUE_TYPE e_truncated =
8187 real_value_truncate (TYPE_MODE (type), dconste);
8188 if (real_dconstp (arg, &e_truncated))
8189 return build_real (type, dconst1);
8192 /* Calculate the result when the argument is a constant. */
8193 if ((res = do_mpfr_arg1 (arg, type, func, &dconst0, NULL, false)))
8194 return res;
8196 /* Special case, optimize logN(expN(x)) = x. */
8197 if (flag_unsafe_math_optimizations
8198 && ((func == mpfr_log
8199 && (fcode == BUILT_IN_EXP
8200 || fcode == BUILT_IN_EXPF
8201 || fcode == BUILT_IN_EXPL))
8202 || (func == mpfr_log2
8203 && (fcode == BUILT_IN_EXP2
8204 || fcode == BUILT_IN_EXP2F
8205 || fcode == BUILT_IN_EXP2L))
8206 || (func == mpfr_log10 && (BUILTIN_EXP10_P (fcode)))))
8207 return fold_convert (type, CALL_EXPR_ARG (arg, 0));
8209 /* Optimize logN(func()) for various exponential functions. We
8210 want to determine the value "x" and the power "exponent" in
8211 order to transform logN(x**exponent) into exponent*logN(x). */
8212 if (flag_unsafe_math_optimizations)
8214 tree exponent = 0, x = 0;
8216 switch (fcode)
8218 CASE_FLT_FN (BUILT_IN_EXP):
8219 /* Prepare to do logN(exp(exponent) -> exponent*logN(e). */
8220 x = build_real (type,
8221 real_value_truncate (TYPE_MODE (type), dconste));
8222 exponent = CALL_EXPR_ARG (arg, 0);
8223 break;
8224 CASE_FLT_FN (BUILT_IN_EXP2):
8225 /* Prepare to do logN(exp2(exponent) -> exponent*logN(2). */
8226 x = build_real (type, dconst2);
8227 exponent = CALL_EXPR_ARG (arg, 0);
8228 break;
8229 CASE_FLT_FN (BUILT_IN_EXP10):
8230 CASE_FLT_FN (BUILT_IN_POW10):
8231 /* Prepare to do logN(exp10(exponent) -> exponent*logN(10). */
8232 x = build_real (type, dconst10);
8233 exponent = CALL_EXPR_ARG (arg, 0);
8234 break;
8235 CASE_FLT_FN (BUILT_IN_SQRT):
8236 /* Prepare to do logN(sqrt(x) -> 0.5*logN(x). */
8237 x = CALL_EXPR_ARG (arg, 0);
8238 exponent = build_real (type, dconsthalf);
8239 break;
8240 CASE_FLT_FN (BUILT_IN_CBRT):
8241 /* Prepare to do logN(cbrt(x) -> (1/3)*logN(x). */
8242 x = CALL_EXPR_ARG (arg, 0);
8243 exponent = build_real (type, real_value_truncate (TYPE_MODE (type),
8244 dconstthird));
8245 break;
8246 CASE_FLT_FN (BUILT_IN_POW):
8247 /* Prepare to do logN(pow(x,exponent) -> exponent*logN(x). */
8248 x = CALL_EXPR_ARG (arg, 0);
8249 exponent = CALL_EXPR_ARG (arg, 1);
8250 break;
8251 default:
8252 break;
8255 /* Now perform the optimization. */
8256 if (x && exponent)
8258 tree logfn = build_call_expr (fndecl, 1, x);
8259 return fold_build2 (MULT_EXPR, type, exponent, logfn);
8264 return NULL_TREE;
8267 /* Fold a builtin function call to hypot, hypotf, or hypotl. Return
8268 NULL_TREE if no simplification can be made. */
8270 static tree
8271 fold_builtin_hypot (tree fndecl, tree arg0, tree arg1, tree type)
8273 tree res, narg0, narg1;
8275 if (!validate_arg (arg0, REAL_TYPE)
8276 || !validate_arg (arg1, REAL_TYPE))
8277 return NULL_TREE;
8279 /* Calculate the result when the argument is a constant. */
8280 if ((res = do_mpfr_arg2 (arg0, arg1, type, mpfr_hypot)))
8281 return res;
8283 /* If either argument to hypot has a negate or abs, strip that off.
8284 E.g. hypot(-x,fabs(y)) -> hypot(x,y). */
8285 narg0 = fold_strip_sign_ops (arg0);
8286 narg1 = fold_strip_sign_ops (arg1);
8287 if (narg0 || narg1)
8289 return build_call_expr (fndecl, 2, narg0 ? narg0 : arg0,
8290 narg1 ? narg1 : arg1);
8293 /* If either argument is zero, hypot is fabs of the other. */
8294 if (real_zerop (arg0))
8295 return fold_build1 (ABS_EXPR, type, arg1);
8296 else if (real_zerop (arg1))
8297 return fold_build1 (ABS_EXPR, type, arg0);
8299 /* hypot(x,x) -> fabs(x)*sqrt(2). */
8300 if (flag_unsafe_math_optimizations
8301 && operand_equal_p (arg0, arg1, OEP_PURE_SAME))
8303 const REAL_VALUE_TYPE sqrt2_trunc
8304 = real_value_truncate (TYPE_MODE (type), dconstsqrt2);
8305 return fold_build2 (MULT_EXPR, type,
8306 fold_build1 (ABS_EXPR, type, arg0),
8307 build_real (type, sqrt2_trunc));
8310 return NULL_TREE;
8314 /* Fold a builtin function call to pow, powf, or powl. Return
8315 NULL_TREE if no simplification can be made. */
8316 static tree
8317 fold_builtin_pow (tree fndecl, tree arg0, tree arg1, tree type)
8319 tree res;
8321 if (!validate_arg (arg0, REAL_TYPE)
8322 || !validate_arg (arg1, REAL_TYPE))
8323 return NULL_TREE;
8325 /* Calculate the result when the argument is a constant. */
8326 if ((res = do_mpfr_arg2 (arg0, arg1, type, mpfr_pow)))
8327 return res;
8329 /* Optimize pow(1.0,y) = 1.0. */
8330 if (real_onep (arg0))
8331 return omit_one_operand (type, build_real (type, dconst1), arg1);
8333 if (TREE_CODE (arg1) == REAL_CST
8334 && !TREE_OVERFLOW (arg1))
8336 REAL_VALUE_TYPE cint;
8337 REAL_VALUE_TYPE c;
8338 HOST_WIDE_INT n;
8340 c = TREE_REAL_CST (arg1);
8342 /* Optimize pow(x,0.0) = 1.0. */
8343 if (REAL_VALUES_EQUAL (c, dconst0))
8344 return omit_one_operand (type, build_real (type, dconst1),
8345 arg0);
8347 /* Optimize pow(x,1.0) = x. */
8348 if (REAL_VALUES_EQUAL (c, dconst1))
8349 return arg0;
8351 /* Optimize pow(x,-1.0) = 1.0/x. */
8352 if (REAL_VALUES_EQUAL (c, dconstm1))
8353 return fold_build2 (RDIV_EXPR, type,
8354 build_real (type, dconst1), arg0);
8356 /* Optimize pow(x,0.5) = sqrt(x). */
8357 if (flag_unsafe_math_optimizations
8358 && REAL_VALUES_EQUAL (c, dconsthalf))
8360 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
8362 if (sqrtfn != NULL_TREE)
8363 return build_call_expr (sqrtfn, 1, arg0);
8366 /* Optimize pow(x,1.0/3.0) = cbrt(x). */
8367 if (flag_unsafe_math_optimizations)
8369 const REAL_VALUE_TYPE dconstroot
8370 = real_value_truncate (TYPE_MODE (type), dconstthird);
8372 if (REAL_VALUES_EQUAL (c, dconstroot))
8374 tree cbrtfn = mathfn_built_in (type, BUILT_IN_CBRT);
8375 if (cbrtfn != NULL_TREE)
8376 return build_call_expr (cbrtfn, 1, arg0);
8380 /* Check for an integer exponent. */
8381 n = real_to_integer (&c);
8382 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
8383 if (real_identical (&c, &cint))
8385 /* Attempt to evaluate pow at compile-time. */
8386 if (TREE_CODE (arg0) == REAL_CST
8387 && !TREE_OVERFLOW (arg0))
8389 REAL_VALUE_TYPE x;
8390 bool inexact;
8392 x = TREE_REAL_CST (arg0);
8393 inexact = real_powi (&x, TYPE_MODE (type), &x, n);
8394 if (flag_unsafe_math_optimizations || !inexact)
8395 return build_real (type, x);
8398 /* Strip sign ops from even integer powers. */
8399 if ((n & 1) == 0 && flag_unsafe_math_optimizations)
8401 tree narg0 = fold_strip_sign_ops (arg0);
8402 if (narg0)
8403 return build_call_expr (fndecl, 2, narg0, arg1);
8408 if (flag_unsafe_math_optimizations)
8410 const enum built_in_function fcode = builtin_mathfn_code (arg0);
8412 /* Optimize pow(expN(x),y) = expN(x*y). */
8413 if (BUILTIN_EXPONENT_P (fcode))
8415 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg0), 0);
8416 tree arg = CALL_EXPR_ARG (arg0, 0);
8417 arg = fold_build2 (MULT_EXPR, type, arg, arg1);
8418 return build_call_expr (expfn, 1, arg);
8421 /* Optimize pow(sqrt(x),y) = pow(x,y*0.5). */
8422 if (BUILTIN_SQRT_P (fcode))
8424 tree narg0 = CALL_EXPR_ARG (arg0, 0);
8425 tree narg1 = fold_build2 (MULT_EXPR, type, arg1,
8426 build_real (type, dconsthalf));
8427 return build_call_expr (fndecl, 2, narg0, narg1);
8430 /* Optimize pow(cbrt(x),y) = pow(x,y/3) iff x is nonnegative. */
8431 if (BUILTIN_CBRT_P (fcode))
8433 tree arg = CALL_EXPR_ARG (arg0, 0);
8434 if (tree_expr_nonnegative_p (arg))
8436 const REAL_VALUE_TYPE dconstroot
8437 = real_value_truncate (TYPE_MODE (type), dconstthird);
8438 tree narg1 = fold_build2 (MULT_EXPR, type, arg1,
8439 build_real (type, dconstroot));
8440 return build_call_expr (fndecl, 2, arg, narg1);
8444 /* Optimize pow(pow(x,y),z) = pow(x,y*z). */
8445 if (fcode == BUILT_IN_POW
8446 || fcode == BUILT_IN_POWF
8447 || fcode == BUILT_IN_POWL)
8449 tree arg00 = CALL_EXPR_ARG (arg0, 0);
8450 tree arg01 = CALL_EXPR_ARG (arg0, 1);
8451 tree narg1 = fold_build2 (MULT_EXPR, type, arg01, arg1);
8452 return build_call_expr (fndecl, 2, arg00, narg1);
8456 return NULL_TREE;
8459 /* Fold a builtin function call to powi, powif, or powil with argument ARG.
8460 Return NULL_TREE if no simplification can be made. */
8461 static tree
8462 fold_builtin_powi (tree fndecl ATTRIBUTE_UNUSED,
8463 tree arg0, tree arg1, tree type)
8465 if (!validate_arg (arg0, REAL_TYPE)
8466 || !validate_arg (arg1, INTEGER_TYPE))
8467 return NULL_TREE;
8469 /* Optimize pow(1.0,y) = 1.0. */
8470 if (real_onep (arg0))
8471 return omit_one_operand (type, build_real (type, dconst1), arg1);
8473 if (host_integerp (arg1, 0))
8475 HOST_WIDE_INT c = TREE_INT_CST_LOW (arg1);
8477 /* Evaluate powi at compile-time. */
8478 if (TREE_CODE (arg0) == REAL_CST
8479 && !TREE_OVERFLOW (arg0))
8481 REAL_VALUE_TYPE x;
8482 x = TREE_REAL_CST (arg0);
8483 real_powi (&x, TYPE_MODE (type), &x, c);
8484 return build_real (type, x);
8487 /* Optimize pow(x,0) = 1.0. */
8488 if (c == 0)
8489 return omit_one_operand (type, build_real (type, dconst1),
8490 arg0);
8492 /* Optimize pow(x,1) = x. */
8493 if (c == 1)
8494 return arg0;
8496 /* Optimize pow(x,-1) = 1.0/x. */
8497 if (c == -1)
8498 return fold_build2 (RDIV_EXPR, type,
8499 build_real (type, dconst1), arg0);
8502 return NULL_TREE;
8505 /* A subroutine of fold_builtin to fold the various exponent
8506 functions. Return NULL_TREE if no simplification can be made.
8507 FUNC is the corresponding MPFR exponent function. */
8509 static tree
8510 fold_builtin_exponent (tree fndecl, tree arg,
8511 int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t))
8513 if (validate_arg (arg, REAL_TYPE))
8515 tree type = TREE_TYPE (TREE_TYPE (fndecl));
8516 tree res;
8518 /* Calculate the result when the argument is a constant. */
8519 if ((res = do_mpfr_arg1 (arg, type, func, NULL, NULL, 0)))
8520 return res;
8522 /* Optimize expN(logN(x)) = x. */
8523 if (flag_unsafe_math_optimizations)
8525 const enum built_in_function fcode = builtin_mathfn_code (arg);
8527 if ((func == mpfr_exp
8528 && (fcode == BUILT_IN_LOG
8529 || fcode == BUILT_IN_LOGF
8530 || fcode == BUILT_IN_LOGL))
8531 || (func == mpfr_exp2
8532 && (fcode == BUILT_IN_LOG2
8533 || fcode == BUILT_IN_LOG2F
8534 || fcode == BUILT_IN_LOG2L))
8535 || (func == mpfr_exp10
8536 && (fcode == BUILT_IN_LOG10
8537 || fcode == BUILT_IN_LOG10F
8538 || fcode == BUILT_IN_LOG10L)))
8539 return fold_convert (type, CALL_EXPR_ARG (arg, 0));
8543 return NULL_TREE;
8546 /* Return true if VAR is a VAR_DECL or a component thereof. */
8548 static bool
8549 var_decl_component_p (tree var)
8551 tree inner = var;
8552 while (handled_component_p (inner))
8553 inner = TREE_OPERAND (inner, 0);
8554 return SSA_VAR_P (inner);
8557 /* Fold function call to builtin memset. Return
8558 NULL_TREE if no simplification can be made. */
8560 static tree
8561 fold_builtin_memset (tree dest, tree c, tree len, tree type, bool ignore)
8563 tree var, ret;
8564 unsigned HOST_WIDE_INT length, cval;
8566 if (! validate_arg (dest, POINTER_TYPE)
8567 || ! validate_arg (c, INTEGER_TYPE)
8568 || ! validate_arg (len, INTEGER_TYPE))
8569 return NULL_TREE;
8571 if (! host_integerp (len, 1))
8572 return NULL_TREE;
8574 /* If the LEN parameter is zero, return DEST. */
8575 if (integer_zerop (len))
8576 return omit_one_operand (type, dest, c);
8578 if (! host_integerp (c, 1) || TREE_SIDE_EFFECTS (dest))
8579 return NULL_TREE;
8581 var = dest;
8582 STRIP_NOPS (var);
8583 if (TREE_CODE (var) != ADDR_EXPR)
8584 return NULL_TREE;
8586 var = TREE_OPERAND (var, 0);
8587 if (TREE_THIS_VOLATILE (var))
8588 return NULL_TREE;
8590 if (!INTEGRAL_TYPE_P (TREE_TYPE (var))
8591 && !POINTER_TYPE_P (TREE_TYPE (var)))
8592 return NULL_TREE;
8594 if (! var_decl_component_p (var))
8595 return NULL_TREE;
8597 length = tree_low_cst (len, 1);
8598 if (GET_MODE_SIZE (TYPE_MODE (TREE_TYPE (var))) != length
8599 || get_pointer_alignment (dest, BIGGEST_ALIGNMENT) / BITS_PER_UNIT
8600 < (int) length)
8601 return NULL_TREE;
8603 if (length > HOST_BITS_PER_WIDE_INT / BITS_PER_UNIT)
8604 return NULL_TREE;
8606 if (integer_zerop (c))
8607 cval = 0;
8608 else
8610 if (CHAR_BIT != 8 || BITS_PER_UNIT != 8 || HOST_BITS_PER_WIDE_INT > 64)
8611 return NULL_TREE;
8613 cval = tree_low_cst (c, 1);
8614 cval &= 0xff;
8615 cval |= cval << 8;
8616 cval |= cval << 16;
8617 cval |= (cval << 31) << 1;
8620 ret = build_int_cst_type (TREE_TYPE (var), cval);
8621 ret = build2 (MODIFY_EXPR, TREE_TYPE (var), var, ret);
8622 if (ignore)
8623 return ret;
8625 return omit_one_operand (type, dest, ret);
8628 /* Fold function call to builtin memset. Return
8629 NULL_TREE if no simplification can be made. */
8631 static tree
8632 fold_builtin_bzero (tree dest, tree size, bool ignore)
8634 if (! validate_arg (dest, POINTER_TYPE)
8635 || ! validate_arg (size, INTEGER_TYPE))
8636 return NULL_TREE;
8638 if (!ignore)
8639 return NULL_TREE;
8641 /* New argument list transforming bzero(ptr x, int y) to
8642 memset(ptr x, int 0, size_t y). This is done this way
8643 so that if it isn't expanded inline, we fallback to
8644 calling bzero instead of memset. */
8646 return fold_builtin_memset (dest, integer_zero_node,
8647 fold_convert (sizetype, size),
8648 void_type_node, ignore);
8651 /* Fold function call to builtin mem{{,p}cpy,move}. Return
8652 NULL_TREE if no simplification can be made.
8653 If ENDP is 0, return DEST (like memcpy).
8654 If ENDP is 1, return DEST+LEN (like mempcpy).
8655 If ENDP is 2, return DEST+LEN-1 (like stpcpy).
8656 If ENDP is 3, return DEST, additionally *SRC and *DEST may overlap
8657 (memmove). */
8659 static tree
8660 fold_builtin_memory_op (tree dest, tree src, tree len, tree type, bool ignore, int endp)
8662 tree destvar, srcvar, expr;
8664 if (! validate_arg (dest, POINTER_TYPE)
8665 || ! validate_arg (src, POINTER_TYPE)
8666 || ! validate_arg (len, INTEGER_TYPE))
8667 return NULL_TREE;
8669 /* If the LEN parameter is zero, return DEST. */
8670 if (integer_zerop (len))
8671 return omit_one_operand (type, dest, src);
8673 /* If SRC and DEST are the same (and not volatile), return
8674 DEST{,+LEN,+LEN-1}. */
8675 if (operand_equal_p (src, dest, 0))
8676 expr = len;
8677 else
8679 tree srctype, desttype;
8680 if (endp == 3)
8682 int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
8683 int dest_align = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
8685 /* Both DEST and SRC must be pointer types.
8686 ??? This is what old code did. Is the testing for pointer types
8687 really mandatory?
8689 If either SRC is readonly or length is 1, we can use memcpy. */
8690 if (dest_align && src_align
8691 && (readonly_data_expr (src)
8692 || (host_integerp (len, 1)
8693 && (MIN (src_align, dest_align) / BITS_PER_UNIT >=
8694 tree_low_cst (len, 1)))))
8696 tree fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8697 if (!fn)
8698 return NULL_TREE;
8699 return build_call_expr (fn, 3, dest, src, len);
8701 return NULL_TREE;
8704 if (!host_integerp (len, 0))
8705 return NULL_TREE;
8706 /* FIXME:
8707 This logic lose for arguments like (type *)malloc (sizeof (type)),
8708 since we strip the casts of up to VOID return value from malloc.
8709 Perhaps we ought to inherit type from non-VOID argument here? */
8710 STRIP_NOPS (src);
8711 STRIP_NOPS (dest);
8712 srctype = TREE_TYPE (TREE_TYPE (src));
8713 desttype = TREE_TYPE (TREE_TYPE (dest));
8714 if (!srctype || !desttype
8715 || !TYPE_SIZE_UNIT (srctype)
8716 || !TYPE_SIZE_UNIT (desttype)
8717 || TREE_CODE (TYPE_SIZE_UNIT (srctype)) != INTEGER_CST
8718 || TREE_CODE (TYPE_SIZE_UNIT (desttype)) != INTEGER_CST
8719 || !tree_int_cst_equal (TYPE_SIZE_UNIT (srctype), len)
8720 || !tree_int_cst_equal (TYPE_SIZE_UNIT (desttype), len))
8721 return NULL_TREE;
8723 if (get_pointer_alignment (dest, BIGGEST_ALIGNMENT)
8724 < (int) TYPE_ALIGN (desttype)
8725 || (get_pointer_alignment (src, BIGGEST_ALIGNMENT)
8726 < (int) TYPE_ALIGN (srctype)))
8727 return NULL_TREE;
8729 if (!ignore)
8730 dest = builtin_save_expr (dest);
8732 srcvar = build_fold_indirect_ref (src);
8733 if (TREE_THIS_VOLATILE (srcvar))
8734 return NULL_TREE;
8735 if (!tree_int_cst_equal (lang_hooks.expr_size (srcvar), len))
8736 return NULL_TREE;
8737 /* With memcpy, it is possible to bypass aliasing rules, so without
8738 this check i. e. execute/20060930-2.c would be misoptimized, because
8739 it use conflicting alias set to hold argument for the memcpy call.
8740 This check is probably unnecesary with -fno-strict-aliasing.
8741 Similarly for destvar. See also PR29286. */
8742 if (!var_decl_component_p (srcvar)
8743 /* Accept: memcpy (*char_var, "test", 1); that simplify
8744 to char_var='t'; */
8745 || is_gimple_min_invariant (srcvar)
8746 || readonly_data_expr (src))
8747 return NULL_TREE;
8749 destvar = build_fold_indirect_ref (dest);
8750 if (TREE_THIS_VOLATILE (destvar))
8751 return NULL_TREE;
8752 if (!tree_int_cst_equal (lang_hooks.expr_size (destvar), len))
8753 return NULL_TREE;
8754 if (!var_decl_component_p (destvar))
8755 return NULL_TREE;
8757 if (srctype == desttype
8758 || (gimple_in_ssa_p (cfun)
8759 && useless_type_conversion_p (desttype, srctype)))
8760 expr = srcvar;
8761 else if ((INTEGRAL_TYPE_P (TREE_TYPE (srcvar))
8762 || POINTER_TYPE_P (TREE_TYPE (srcvar)))
8763 && (INTEGRAL_TYPE_P (TREE_TYPE (destvar))
8764 || POINTER_TYPE_P (TREE_TYPE (destvar))))
8765 expr = fold_convert (TREE_TYPE (destvar), srcvar);
8766 else
8767 expr = fold_build1 (VIEW_CONVERT_EXPR, TREE_TYPE (destvar), srcvar);
8768 expr = build2 (MODIFY_EXPR, TREE_TYPE (destvar), destvar, expr);
8771 if (ignore)
8772 return expr;
8774 if (endp == 0 || endp == 3)
8775 return omit_one_operand (type, dest, expr);
8777 if (expr == len)
8778 expr = NULL_TREE;
8780 if (endp == 2)
8781 len = fold_build2 (MINUS_EXPR, TREE_TYPE (len), len,
8782 ssize_int (1));
8784 dest = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
8785 dest = fold_convert (type, dest);
8786 if (expr)
8787 dest = omit_one_operand (type, dest, expr);
8788 return dest;
8791 /* Fold function call to builtin strcpy with arguments DEST and SRC.
8792 If LEN is not NULL, it represents the length of the string to be
8793 copied. Return NULL_TREE if no simplification can be made. */
8795 tree
8796 fold_builtin_strcpy (tree fndecl, tree dest, tree src, tree len)
8798 tree fn;
8800 if (!validate_arg (dest, POINTER_TYPE)
8801 || !validate_arg (src, POINTER_TYPE))
8802 return NULL_TREE;
8804 /* If SRC and DEST are the same (and not volatile), return DEST. */
8805 if (operand_equal_p (src, dest, 0))
8806 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), dest);
8808 if (optimize_size)
8809 return NULL_TREE;
8811 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8812 if (!fn)
8813 return NULL_TREE;
8815 if (!len)
8817 len = c_strlen (src, 1);
8818 if (! len || TREE_SIDE_EFFECTS (len))
8819 return NULL_TREE;
8822 len = size_binop (PLUS_EXPR, len, ssize_int (1));
8823 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)),
8824 build_call_expr (fn, 3, dest, src, len));
8827 /* Fold function call to builtin strncpy with arguments DEST, SRC, and LEN.
8828 If SLEN is not NULL, it represents the length of the source string.
8829 Return NULL_TREE if no simplification can be made. */
8831 tree
8832 fold_builtin_strncpy (tree fndecl, tree dest, tree src, tree len, tree slen)
8834 tree fn;
8836 if (!validate_arg (dest, POINTER_TYPE)
8837 || !validate_arg (src, POINTER_TYPE)
8838 || !validate_arg (len, INTEGER_TYPE))
8839 return NULL_TREE;
8841 /* If the LEN parameter is zero, return DEST. */
8842 if (integer_zerop (len))
8843 return omit_one_operand (TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
8845 /* We can't compare slen with len as constants below if len is not a
8846 constant. */
8847 if (len == 0 || TREE_CODE (len) != INTEGER_CST)
8848 return NULL_TREE;
8850 if (!slen)
8851 slen = c_strlen (src, 1);
8853 /* Now, we must be passed a constant src ptr parameter. */
8854 if (slen == 0 || TREE_CODE (slen) != INTEGER_CST)
8855 return NULL_TREE;
8857 slen = size_binop (PLUS_EXPR, slen, ssize_int (1));
8859 /* We do not support simplification of this case, though we do
8860 support it when expanding trees into RTL. */
8861 /* FIXME: generate a call to __builtin_memset. */
8862 if (tree_int_cst_lt (slen, len))
8863 return NULL_TREE;
8865 /* OK transform into builtin memcpy. */
8866 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8867 if (!fn)
8868 return NULL_TREE;
8869 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)),
8870 build_call_expr (fn, 3, dest, src, len));
8873 /* Fold function call to builtin memchr. ARG1, ARG2 and LEN are the
8874 arguments to the call, and TYPE is its return type.
8875 Return NULL_TREE if no simplification can be made. */
8877 static tree
8878 fold_builtin_memchr (tree arg1, tree arg2, tree len, tree type)
8880 if (!validate_arg (arg1, POINTER_TYPE)
8881 || !validate_arg (arg2, INTEGER_TYPE)
8882 || !validate_arg (len, INTEGER_TYPE))
8883 return NULL_TREE;
8884 else
8886 const char *p1;
8888 if (TREE_CODE (arg2) != INTEGER_CST
8889 || !host_integerp (len, 1))
8890 return NULL_TREE;
8892 p1 = c_getstr (arg1);
8893 if (p1 && compare_tree_int (len, strlen (p1) + 1) <= 0)
8895 char c;
8896 const char *r;
8897 tree tem;
8899 if (target_char_cast (arg2, &c))
8900 return NULL_TREE;
8902 r = memchr (p1, c, tree_low_cst (len, 1));
8904 if (r == NULL)
8905 return build_int_cst (TREE_TYPE (arg1), 0);
8907 tem = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (arg1), arg1,
8908 size_int (r - p1));
8909 return fold_convert (type, tem);
8911 return NULL_TREE;
8915 /* Fold function call to builtin memcmp with arguments ARG1 and ARG2.
8916 Return NULL_TREE if no simplification can be made. */
8918 static tree
8919 fold_builtin_memcmp (tree arg1, tree arg2, tree len)
8921 const char *p1, *p2;
8923 if (!validate_arg (arg1, POINTER_TYPE)
8924 || !validate_arg (arg2, POINTER_TYPE)
8925 || !validate_arg (len, INTEGER_TYPE))
8926 return NULL_TREE;
8928 /* If the LEN parameter is zero, return zero. */
8929 if (integer_zerop (len))
8930 return omit_two_operands (integer_type_node, integer_zero_node,
8931 arg1, arg2);
8933 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
8934 if (operand_equal_p (arg1, arg2, 0))
8935 return omit_one_operand (integer_type_node, integer_zero_node, len);
8937 p1 = c_getstr (arg1);
8938 p2 = c_getstr (arg2);
8940 /* If all arguments are constant, and the value of len is not greater
8941 than the lengths of arg1 and arg2, evaluate at compile-time. */
8942 if (host_integerp (len, 1) && p1 && p2
8943 && compare_tree_int (len, strlen (p1) + 1) <= 0
8944 && compare_tree_int (len, strlen (p2) + 1) <= 0)
8946 const int r = memcmp (p1, p2, tree_low_cst (len, 1));
8948 if (r > 0)
8949 return integer_one_node;
8950 else if (r < 0)
8951 return integer_minus_one_node;
8952 else
8953 return integer_zero_node;
8956 /* If len parameter is one, return an expression corresponding to
8957 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
8958 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 1)
8960 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8961 tree cst_uchar_ptr_node
8962 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8964 tree ind1 = fold_convert (integer_type_node,
8965 build1 (INDIRECT_REF, cst_uchar_node,
8966 fold_convert (cst_uchar_ptr_node,
8967 arg1)));
8968 tree ind2 = fold_convert (integer_type_node,
8969 build1 (INDIRECT_REF, cst_uchar_node,
8970 fold_convert (cst_uchar_ptr_node,
8971 arg2)));
8972 return fold_build2 (MINUS_EXPR, integer_type_node, ind1, ind2);
8975 return NULL_TREE;
8978 /* Fold function call to builtin strcmp with arguments ARG1 and ARG2.
8979 Return NULL_TREE if no simplification can be made. */
8981 static tree
8982 fold_builtin_strcmp (tree arg1, tree arg2)
8984 const char *p1, *p2;
8986 if (!validate_arg (arg1, POINTER_TYPE)
8987 || !validate_arg (arg2, POINTER_TYPE))
8988 return NULL_TREE;
8990 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
8991 if (operand_equal_p (arg1, arg2, 0))
8992 return integer_zero_node;
8994 p1 = c_getstr (arg1);
8995 p2 = c_getstr (arg2);
8997 if (p1 && p2)
8999 const int i = strcmp (p1, p2);
9000 if (i < 0)
9001 return integer_minus_one_node;
9002 else if (i > 0)
9003 return integer_one_node;
9004 else
9005 return integer_zero_node;
9008 /* If the second arg is "", return *(const unsigned char*)arg1. */
9009 if (p2 && *p2 == '\0')
9011 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
9012 tree cst_uchar_ptr_node
9013 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
9015 return fold_convert (integer_type_node,
9016 build1 (INDIRECT_REF, cst_uchar_node,
9017 fold_convert (cst_uchar_ptr_node,
9018 arg1)));
9021 /* If the first arg is "", return -*(const unsigned char*)arg2. */
9022 if (p1 && *p1 == '\0')
9024 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
9025 tree cst_uchar_ptr_node
9026 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
9028 tree temp = fold_convert (integer_type_node,
9029 build1 (INDIRECT_REF, cst_uchar_node,
9030 fold_convert (cst_uchar_ptr_node,
9031 arg2)));
9032 return fold_build1 (NEGATE_EXPR, integer_type_node, temp);
9035 return NULL_TREE;
9038 /* Fold function call to builtin strncmp with arguments ARG1, ARG2, and LEN.
9039 Return NULL_TREE if no simplification can be made. */
9041 static tree
9042 fold_builtin_strncmp (tree arg1, tree arg2, tree len)
9044 const char *p1, *p2;
9046 if (!validate_arg (arg1, POINTER_TYPE)
9047 || !validate_arg (arg2, POINTER_TYPE)
9048 || !validate_arg (len, INTEGER_TYPE))
9049 return NULL_TREE;
9051 /* If the LEN parameter is zero, return zero. */
9052 if (integer_zerop (len))
9053 return omit_two_operands (integer_type_node, integer_zero_node,
9054 arg1, arg2);
9056 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
9057 if (operand_equal_p (arg1, arg2, 0))
9058 return omit_one_operand (integer_type_node, integer_zero_node, len);
9060 p1 = c_getstr (arg1);
9061 p2 = c_getstr (arg2);
9063 if (host_integerp (len, 1) && p1 && p2)
9065 const int i = strncmp (p1, p2, tree_low_cst (len, 1));
9066 if (i > 0)
9067 return integer_one_node;
9068 else if (i < 0)
9069 return integer_minus_one_node;
9070 else
9071 return integer_zero_node;
9074 /* If the second arg is "", and the length is greater than zero,
9075 return *(const unsigned char*)arg1. */
9076 if (p2 && *p2 == '\0'
9077 && TREE_CODE (len) == INTEGER_CST
9078 && tree_int_cst_sgn (len) == 1)
9080 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
9081 tree cst_uchar_ptr_node
9082 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
9084 return fold_convert (integer_type_node,
9085 build1 (INDIRECT_REF, cst_uchar_node,
9086 fold_convert (cst_uchar_ptr_node,
9087 arg1)));
9090 /* If the first arg is "", and the length is greater than zero,
9091 return -*(const unsigned char*)arg2. */
9092 if (p1 && *p1 == '\0'
9093 && TREE_CODE (len) == INTEGER_CST
9094 && tree_int_cst_sgn (len) == 1)
9096 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
9097 tree cst_uchar_ptr_node
9098 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
9100 tree temp = fold_convert (integer_type_node,
9101 build1 (INDIRECT_REF, cst_uchar_node,
9102 fold_convert (cst_uchar_ptr_node,
9103 arg2)));
9104 return fold_build1 (NEGATE_EXPR, integer_type_node, temp);
9107 /* If len parameter is one, return an expression corresponding to
9108 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
9109 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 1)
9111 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
9112 tree cst_uchar_ptr_node
9113 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
9115 tree ind1 = fold_convert (integer_type_node,
9116 build1 (INDIRECT_REF, cst_uchar_node,
9117 fold_convert (cst_uchar_ptr_node,
9118 arg1)));
9119 tree ind2 = fold_convert (integer_type_node,
9120 build1 (INDIRECT_REF, cst_uchar_node,
9121 fold_convert (cst_uchar_ptr_node,
9122 arg2)));
9123 return fold_build2 (MINUS_EXPR, integer_type_node, ind1, ind2);
9126 return NULL_TREE;
9129 /* Fold function call to builtin signbit, signbitf or signbitl with argument
9130 ARG. Return NULL_TREE if no simplification can be made. */
9132 static tree
9133 fold_builtin_signbit (tree arg, tree type)
9135 tree temp;
9137 if (!validate_arg (arg, REAL_TYPE))
9138 return NULL_TREE;
9140 /* If ARG is a compile-time constant, determine the result. */
9141 if (TREE_CODE (arg) == REAL_CST
9142 && !TREE_OVERFLOW (arg))
9144 REAL_VALUE_TYPE c;
9146 c = TREE_REAL_CST (arg);
9147 temp = REAL_VALUE_NEGATIVE (c) ? integer_one_node : integer_zero_node;
9148 return fold_convert (type, temp);
9151 /* If ARG is non-negative, the result is always zero. */
9152 if (tree_expr_nonnegative_p (arg))
9153 return omit_one_operand (type, integer_zero_node, arg);
9155 /* If ARG's format doesn't have signed zeros, return "arg < 0.0". */
9156 if (!HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg))))
9157 return fold_build2 (LT_EXPR, type, arg,
9158 build_real (TREE_TYPE (arg), dconst0));
9160 return NULL_TREE;
9163 /* Fold function call to builtin copysign, copysignf or copysignl with
9164 arguments ARG1 and ARG2. Return NULL_TREE if no simplification can
9165 be made. */
9167 static tree
9168 fold_builtin_copysign (tree fndecl, tree arg1, tree arg2, tree type)
9170 tree tem;
9172 if (!validate_arg (arg1, REAL_TYPE)
9173 || !validate_arg (arg2, REAL_TYPE))
9174 return NULL_TREE;
9176 /* copysign(X,X) is X. */
9177 if (operand_equal_p (arg1, arg2, 0))
9178 return fold_convert (type, arg1);
9180 /* If ARG1 and ARG2 are compile-time constants, determine the result. */
9181 if (TREE_CODE (arg1) == REAL_CST
9182 && TREE_CODE (arg2) == REAL_CST
9183 && !TREE_OVERFLOW (arg1)
9184 && !TREE_OVERFLOW (arg2))
9186 REAL_VALUE_TYPE c1, c2;
9188 c1 = TREE_REAL_CST (arg1);
9189 c2 = TREE_REAL_CST (arg2);
9190 /* c1.sign := c2.sign. */
9191 real_copysign (&c1, &c2);
9192 return build_real (type, c1);
9195 /* copysign(X, Y) is fabs(X) when Y is always non-negative.
9196 Remember to evaluate Y for side-effects. */
9197 if (tree_expr_nonnegative_p (arg2))
9198 return omit_one_operand (type,
9199 fold_build1 (ABS_EXPR, type, arg1),
9200 arg2);
9202 /* Strip sign changing operations for the first argument. */
9203 tem = fold_strip_sign_ops (arg1);
9204 if (tem)
9205 return build_call_expr (fndecl, 2, tem, arg2);
9207 return NULL_TREE;
9210 /* Fold a call to builtin isascii with argument ARG. */
9212 static tree
9213 fold_builtin_isascii (tree arg)
9215 if (!validate_arg (arg, INTEGER_TYPE))
9216 return NULL_TREE;
9217 else
9219 /* Transform isascii(c) -> ((c & ~0x7f) == 0). */
9220 arg = build2 (BIT_AND_EXPR, integer_type_node, arg,
9221 build_int_cst (NULL_TREE,
9222 ~ (unsigned HOST_WIDE_INT) 0x7f));
9223 return fold_build2 (EQ_EXPR, integer_type_node,
9224 arg, integer_zero_node);
9228 /* Fold a call to builtin toascii with argument ARG. */
9230 static tree
9231 fold_builtin_toascii (tree arg)
9233 if (!validate_arg (arg, INTEGER_TYPE))
9234 return NULL_TREE;
9236 /* Transform toascii(c) -> (c & 0x7f). */
9237 return fold_build2 (BIT_AND_EXPR, integer_type_node, arg,
9238 build_int_cst (NULL_TREE, 0x7f));
9241 /* Fold a call to builtin isdigit with argument ARG. */
9243 static tree
9244 fold_builtin_isdigit (tree arg)
9246 if (!validate_arg (arg, INTEGER_TYPE))
9247 return NULL_TREE;
9248 else
9250 /* Transform isdigit(c) -> (unsigned)(c) - '0' <= 9. */
9251 /* According to the C standard, isdigit is unaffected by locale.
9252 However, it definitely is affected by the target character set. */
9253 unsigned HOST_WIDE_INT target_digit0
9254 = lang_hooks.to_target_charset ('0');
9256 if (target_digit0 == 0)
9257 return NULL_TREE;
9259 arg = fold_convert (unsigned_type_node, arg);
9260 arg = build2 (MINUS_EXPR, unsigned_type_node, arg,
9261 build_int_cst (unsigned_type_node, target_digit0));
9262 return fold_build2 (LE_EXPR, integer_type_node, arg,
9263 build_int_cst (unsigned_type_node, 9));
9267 /* Fold a call to fabs, fabsf or fabsl with argument ARG. */
9269 static tree
9270 fold_builtin_fabs (tree arg, tree type)
9272 if (!validate_arg (arg, REAL_TYPE))
9273 return NULL_TREE;
9275 arg = fold_convert (type, arg);
9276 if (TREE_CODE (arg) == REAL_CST)
9277 return fold_abs_const (arg, type);
9278 return fold_build1 (ABS_EXPR, type, arg);
9281 /* Fold a call to abs, labs, llabs or imaxabs with argument ARG. */
9283 static tree
9284 fold_builtin_abs (tree arg, tree type)
9286 if (!validate_arg (arg, INTEGER_TYPE))
9287 return NULL_TREE;
9289 arg = fold_convert (type, arg);
9290 if (TREE_CODE (arg) == INTEGER_CST)
9291 return fold_abs_const (arg, type);
9292 return fold_build1 (ABS_EXPR, type, arg);
9295 /* Fold a call to builtin fmin or fmax. */
9297 static tree
9298 fold_builtin_fmin_fmax (tree arg0, tree arg1, tree type, bool max)
9300 if (validate_arg (arg0, REAL_TYPE) && validate_arg (arg1, REAL_TYPE))
9302 /* Calculate the result when the argument is a constant. */
9303 tree res = do_mpfr_arg2 (arg0, arg1, type, (max ? mpfr_max : mpfr_min));
9305 if (res)
9306 return res;
9308 /* If either argument is NaN, return the other one. Avoid the
9309 transformation if we get (and honor) a signalling NaN. Using
9310 omit_one_operand() ensures we create a non-lvalue. */
9311 if (TREE_CODE (arg0) == REAL_CST
9312 && real_isnan (&TREE_REAL_CST (arg0))
9313 && (! HONOR_SNANS (TYPE_MODE (TREE_TYPE (arg0)))
9314 || ! TREE_REAL_CST (arg0).signalling))
9315 return omit_one_operand (type, arg1, arg0);
9316 if (TREE_CODE (arg1) == REAL_CST
9317 && real_isnan (&TREE_REAL_CST (arg1))
9318 && (! HONOR_SNANS (TYPE_MODE (TREE_TYPE (arg1)))
9319 || ! TREE_REAL_CST (arg1).signalling))
9320 return omit_one_operand (type, arg0, arg1);
9322 /* Transform fmin/fmax(x,x) -> x. */
9323 if (operand_equal_p (arg0, arg1, OEP_PURE_SAME))
9324 return omit_one_operand (type, arg0, arg1);
9326 /* Convert fmin/fmax to MIN_EXPR/MAX_EXPR. C99 requires these
9327 functions to return the numeric arg if the other one is NaN.
9328 These tree codes don't honor that, so only transform if
9329 -ffinite-math-only is set. C99 doesn't require -0.0 to be
9330 handled, so we don't have to worry about it either. */
9331 if (flag_finite_math_only)
9332 return fold_build2 ((max ? MAX_EXPR : MIN_EXPR), type,
9333 fold_convert (type, arg0),
9334 fold_convert (type, arg1));
9336 return NULL_TREE;
9339 /* Fold a call to builtin carg(a+bi) -> atan2(b,a). */
9341 static tree
9342 fold_builtin_carg (tree arg, tree type)
9344 if (validate_arg (arg, COMPLEX_TYPE))
9346 tree atan2_fn = mathfn_built_in (type, BUILT_IN_ATAN2);
9348 if (atan2_fn)
9350 tree new_arg = builtin_save_expr (arg);
9351 tree r_arg = fold_build1 (REALPART_EXPR, type, new_arg);
9352 tree i_arg = fold_build1 (IMAGPART_EXPR, type, new_arg);
9353 return build_call_expr (atan2_fn, 2, i_arg, r_arg);
9357 return NULL_TREE;
9360 /* Fold a call to builtin logb/ilogb. */
9362 static tree
9363 fold_builtin_logb (tree arg, tree rettype)
9365 if (! validate_arg (arg, REAL_TYPE))
9366 return NULL_TREE;
9368 STRIP_NOPS (arg);
9370 if (TREE_CODE (arg) == REAL_CST && ! TREE_OVERFLOW (arg))
9372 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg);
9374 switch (value->cl)
9376 case rvc_nan:
9377 case rvc_inf:
9378 /* If arg is Inf or NaN and we're logb, return it. */
9379 if (TREE_CODE (rettype) == REAL_TYPE)
9380 return fold_convert (rettype, arg);
9381 /* Fall through... */
9382 case rvc_zero:
9383 /* Zero may set errno and/or raise an exception for logb, also
9384 for ilogb we don't know FP_ILOGB0. */
9385 return NULL_TREE;
9386 case rvc_normal:
9387 /* For normal numbers, proceed iff radix == 2. In GCC,
9388 normalized significands are in the range [0.5, 1.0). We
9389 want the exponent as if they were [1.0, 2.0) so get the
9390 exponent and subtract 1. */
9391 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (arg)))->b == 2)
9392 return fold_convert (rettype, build_int_cst (NULL_TREE,
9393 REAL_EXP (value)-1));
9394 break;
9398 return NULL_TREE;
9401 /* Fold a call to builtin significand, if radix == 2. */
9403 static tree
9404 fold_builtin_significand (tree arg, tree rettype)
9406 if (! validate_arg (arg, REAL_TYPE))
9407 return NULL_TREE;
9409 STRIP_NOPS (arg);
9411 if (TREE_CODE (arg) == REAL_CST && ! TREE_OVERFLOW (arg))
9413 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg);
9415 switch (value->cl)
9417 case rvc_zero:
9418 case rvc_nan:
9419 case rvc_inf:
9420 /* If arg is +-0, +-Inf or +-NaN, then return it. */
9421 return fold_convert (rettype, arg);
9422 case rvc_normal:
9423 /* For normal numbers, proceed iff radix == 2. */
9424 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (arg)))->b == 2)
9426 REAL_VALUE_TYPE result = *value;
9427 /* In GCC, normalized significands are in the range [0.5,
9428 1.0). We want them to be [1.0, 2.0) so set the
9429 exponent to 1. */
9430 SET_REAL_EXP (&result, 1);
9431 return build_real (rettype, result);
9433 break;
9437 return NULL_TREE;
9440 /* Fold a call to builtin frexp, we can assume the base is 2. */
9442 static tree
9443 fold_builtin_frexp (tree arg0, tree arg1, tree rettype)
9445 if (! validate_arg (arg0, REAL_TYPE) || ! validate_arg (arg1, POINTER_TYPE))
9446 return NULL_TREE;
9448 STRIP_NOPS (arg0);
9450 if (!(TREE_CODE (arg0) == REAL_CST && ! TREE_OVERFLOW (arg0)))
9451 return NULL_TREE;
9453 arg1 = build_fold_indirect_ref (arg1);
9455 /* Proceed if a valid pointer type was passed in. */
9456 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg1)) == integer_type_node)
9458 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg0);
9459 tree frac, exp;
9461 switch (value->cl)
9463 case rvc_zero:
9464 /* For +-0, return (*exp = 0, +-0). */
9465 exp = integer_zero_node;
9466 frac = arg0;
9467 break;
9468 case rvc_nan:
9469 case rvc_inf:
9470 /* For +-NaN or +-Inf, *exp is unspecified, return arg0. */
9471 return omit_one_operand (rettype, arg0, arg1);
9472 case rvc_normal:
9474 /* Since the frexp function always expects base 2, and in
9475 GCC normalized significands are already in the range
9476 [0.5, 1.0), we have exactly what frexp wants. */
9477 REAL_VALUE_TYPE frac_rvt = *value;
9478 SET_REAL_EXP (&frac_rvt, 0);
9479 frac = build_real (rettype, frac_rvt);
9480 exp = build_int_cst (NULL_TREE, REAL_EXP (value));
9482 break;
9483 default:
9484 gcc_unreachable ();
9487 /* Create the COMPOUND_EXPR (*arg1 = trunc, frac). */
9488 arg1 = fold_build2 (MODIFY_EXPR, rettype, arg1, exp);
9489 TREE_SIDE_EFFECTS (arg1) = 1;
9490 return fold_build2 (COMPOUND_EXPR, rettype, arg1, frac);
9493 return NULL_TREE;
9496 /* Fold a call to builtin ldexp or scalbn/scalbln. If LDEXP is true
9497 then we can assume the base is two. If it's false, then we have to
9498 check the mode of the TYPE parameter in certain cases. */
9500 static tree
9501 fold_builtin_load_exponent (tree arg0, tree arg1, tree type, bool ldexp)
9503 if (validate_arg (arg0, REAL_TYPE) && validate_arg (arg1, INTEGER_TYPE))
9505 STRIP_NOPS (arg0);
9506 STRIP_NOPS (arg1);
9508 /* If arg0 is 0, Inf or NaN, or if arg1 is 0, then return arg0. */
9509 if (real_zerop (arg0) || integer_zerop (arg1)
9510 || (TREE_CODE (arg0) == REAL_CST
9511 && !real_isfinite (&TREE_REAL_CST (arg0))))
9512 return omit_one_operand (type, arg0, arg1);
9514 /* If both arguments are constant, then try to evaluate it. */
9515 if ((ldexp || REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2)
9516 && TREE_CODE (arg0) == REAL_CST && !TREE_OVERFLOW (arg0)
9517 && host_integerp (arg1, 0))
9519 /* Bound the maximum adjustment to twice the range of the
9520 mode's valid exponents. Use abs to ensure the range is
9521 positive as a sanity check. */
9522 const long max_exp_adj = 2 *
9523 labs (REAL_MODE_FORMAT (TYPE_MODE (type))->emax
9524 - REAL_MODE_FORMAT (TYPE_MODE (type))->emin);
9526 /* Get the user-requested adjustment. */
9527 const HOST_WIDE_INT req_exp_adj = tree_low_cst (arg1, 0);
9529 /* The requested adjustment must be inside this range. This
9530 is a preliminary cap to avoid things like overflow, we
9531 may still fail to compute the result for other reasons. */
9532 if (-max_exp_adj < req_exp_adj && req_exp_adj < max_exp_adj)
9534 REAL_VALUE_TYPE initial_result;
9536 real_ldexp (&initial_result, &TREE_REAL_CST (arg0), req_exp_adj);
9538 /* Ensure we didn't overflow. */
9539 if (! real_isinf (&initial_result))
9541 const REAL_VALUE_TYPE trunc_result
9542 = real_value_truncate (TYPE_MODE (type), initial_result);
9544 /* Only proceed if the target mode can hold the
9545 resulting value. */
9546 if (REAL_VALUES_EQUAL (initial_result, trunc_result))
9547 return build_real (type, trunc_result);
9553 return NULL_TREE;
9556 /* Fold a call to builtin modf. */
9558 static tree
9559 fold_builtin_modf (tree arg0, tree arg1, tree rettype)
9561 if (! validate_arg (arg0, REAL_TYPE) || ! validate_arg (arg1, POINTER_TYPE))
9562 return NULL_TREE;
9564 STRIP_NOPS (arg0);
9566 if (!(TREE_CODE (arg0) == REAL_CST && ! TREE_OVERFLOW (arg0)))
9567 return NULL_TREE;
9569 arg1 = build_fold_indirect_ref (arg1);
9571 /* Proceed if a valid pointer type was passed in. */
9572 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg1)) == TYPE_MAIN_VARIANT (rettype))
9574 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg0);
9575 REAL_VALUE_TYPE trunc, frac;
9577 switch (value->cl)
9579 case rvc_nan:
9580 case rvc_zero:
9581 /* For +-NaN or +-0, return (*arg1 = arg0, arg0). */
9582 trunc = frac = *value;
9583 break;
9584 case rvc_inf:
9585 /* For +-Inf, return (*arg1 = arg0, +-0). */
9586 frac = dconst0;
9587 frac.sign = value->sign;
9588 trunc = *value;
9589 break;
9590 case rvc_normal:
9591 /* Return (*arg1 = trunc(arg0), arg0-trunc(arg0)). */
9592 real_trunc (&trunc, VOIDmode, value);
9593 real_arithmetic (&frac, MINUS_EXPR, value, &trunc);
9594 /* If the original number was negative and already
9595 integral, then the fractional part is -0.0. */
9596 if (value->sign && frac.cl == rvc_zero)
9597 frac.sign = value->sign;
9598 break;
9601 /* Create the COMPOUND_EXPR (*arg1 = trunc, frac). */
9602 arg1 = fold_build2 (MODIFY_EXPR, rettype, arg1,
9603 build_real (rettype, trunc));
9604 TREE_SIDE_EFFECTS (arg1) = 1;
9605 return fold_build2 (COMPOUND_EXPR, rettype, arg1,
9606 build_real (rettype, frac));
9609 return NULL_TREE;
9612 /* Fold a call to __builtin_isnan(), __builtin_isinf, __builtin_finite.
9613 ARG is the argument for the call. */
9615 static tree
9616 fold_builtin_classify (tree fndecl, tree arg, int builtin_index)
9618 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9619 REAL_VALUE_TYPE r;
9621 if (!validate_arg (arg, REAL_TYPE))
9623 error ("non-floating-point argument to function %qs",
9624 IDENTIFIER_POINTER (DECL_NAME (fndecl)));
9625 return error_mark_node;
9628 switch (builtin_index)
9630 case BUILT_IN_ISINF:
9631 if (!HONOR_INFINITIES (TYPE_MODE (TREE_TYPE (arg))))
9632 return omit_one_operand (type, integer_zero_node, arg);
9634 if (TREE_CODE (arg) == REAL_CST)
9636 r = TREE_REAL_CST (arg);
9637 if (real_isinf (&r))
9638 return real_compare (GT_EXPR, &r, &dconst0)
9639 ? integer_one_node : integer_minus_one_node;
9640 else
9641 return integer_zero_node;
9644 return NULL_TREE;
9646 case BUILT_IN_ISFINITE:
9647 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg)))
9648 && !HONOR_INFINITIES (TYPE_MODE (TREE_TYPE (arg))))
9649 return omit_one_operand (type, integer_one_node, arg);
9651 if (TREE_CODE (arg) == REAL_CST)
9653 r = TREE_REAL_CST (arg);
9654 return real_isfinite (&r) ? integer_one_node : integer_zero_node;
9657 return NULL_TREE;
9659 case BUILT_IN_ISNAN:
9660 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg))))
9661 return omit_one_operand (type, integer_zero_node, arg);
9663 if (TREE_CODE (arg) == REAL_CST)
9665 r = TREE_REAL_CST (arg);
9666 return real_isnan (&r) ? integer_one_node : integer_zero_node;
9669 arg = builtin_save_expr (arg);
9670 return fold_build2 (UNORDERED_EXPR, type, arg, arg);
9672 default:
9673 gcc_unreachable ();
9677 /* Fold a call to an unordered comparison function such as
9678 __builtin_isgreater(). FNDECL is the FUNCTION_DECL for the function
9679 being called and ARG0 and ARG1 are the arguments for the call.
9680 UNORDERED_CODE and ORDERED_CODE are comparison codes that give
9681 the opposite of the desired result. UNORDERED_CODE is used
9682 for modes that can hold NaNs and ORDERED_CODE is used for
9683 the rest. */
9685 static tree
9686 fold_builtin_unordered_cmp (tree fndecl, tree arg0, tree arg1,
9687 enum tree_code unordered_code,
9688 enum tree_code ordered_code)
9690 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9691 enum tree_code code;
9692 tree type0, type1;
9693 enum tree_code code0, code1;
9694 tree cmp_type = NULL_TREE;
9696 type0 = TREE_TYPE (arg0);
9697 type1 = TREE_TYPE (arg1);
9699 code0 = TREE_CODE (type0);
9700 code1 = TREE_CODE (type1);
9702 if (code0 == REAL_TYPE && code1 == REAL_TYPE)
9703 /* Choose the wider of two real types. */
9704 cmp_type = TYPE_PRECISION (type0) >= TYPE_PRECISION (type1)
9705 ? type0 : type1;
9706 else if (code0 == REAL_TYPE && code1 == INTEGER_TYPE)
9707 cmp_type = type0;
9708 else if (code0 == INTEGER_TYPE && code1 == REAL_TYPE)
9709 cmp_type = type1;
9710 else
9712 error ("non-floating-point argument to function %qs",
9713 IDENTIFIER_POINTER (DECL_NAME (fndecl)));
9714 return error_mark_node;
9717 arg0 = fold_convert (cmp_type, arg0);
9718 arg1 = fold_convert (cmp_type, arg1);
9720 if (unordered_code == UNORDERED_EXPR)
9722 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg0))))
9723 return omit_two_operands (type, integer_zero_node, arg0, arg1);
9724 return fold_build2 (UNORDERED_EXPR, type, arg0, arg1);
9727 code = HONOR_NANS (TYPE_MODE (TREE_TYPE (arg0))) ? unordered_code
9728 : ordered_code;
9729 return fold_build1 (TRUTH_NOT_EXPR, type,
9730 fold_build2 (code, type, arg0, arg1));
9733 /* Fold a call to built-in function FNDECL with 0 arguments.
9734 IGNORE is true if the result of the function call is ignored. This
9735 function returns NULL_TREE if no simplification was possible. */
9737 static tree
9738 fold_builtin_0 (tree fndecl, bool ignore ATTRIBUTE_UNUSED)
9740 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9741 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
9742 switch (fcode)
9744 CASE_FLT_FN (BUILT_IN_INF):
9745 case BUILT_IN_INFD32:
9746 case BUILT_IN_INFD64:
9747 case BUILT_IN_INFD128:
9748 return fold_builtin_inf (type, true);
9750 CASE_FLT_FN (BUILT_IN_HUGE_VAL):
9751 return fold_builtin_inf (type, false);
9753 case BUILT_IN_CLASSIFY_TYPE:
9754 return fold_builtin_classify_type (NULL_TREE);
9756 default:
9757 break;
9759 return NULL_TREE;
9762 /* Fold a call to built-in function FNDECL with 1 argument, ARG0.
9763 IGNORE is true if the result of the function call is ignored. This
9764 function returns NULL_TREE if no simplification was possible. */
9766 static tree
9767 fold_builtin_1 (tree fndecl, tree arg0, bool ignore)
9769 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9770 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
9771 switch (fcode)
9774 case BUILT_IN_CONSTANT_P:
9776 tree val = fold_builtin_constant_p (arg0);
9778 /* Gimplification will pull the CALL_EXPR for the builtin out of
9779 an if condition. When not optimizing, we'll not CSE it back.
9780 To avoid link error types of regressions, return false now. */
9781 if (!val && !optimize)
9782 val = integer_zero_node;
9784 return val;
9787 case BUILT_IN_CLASSIFY_TYPE:
9788 return fold_builtin_classify_type (arg0);
9790 case BUILT_IN_STRLEN:
9791 return fold_builtin_strlen (arg0);
9793 CASE_FLT_FN (BUILT_IN_FABS):
9794 return fold_builtin_fabs (arg0, type);
9796 case BUILT_IN_ABS:
9797 case BUILT_IN_LABS:
9798 case BUILT_IN_LLABS:
9799 case BUILT_IN_IMAXABS:
9800 return fold_builtin_abs (arg0, type);
9802 CASE_FLT_FN (BUILT_IN_CONJ):
9803 if (validate_arg (arg0, COMPLEX_TYPE))
9804 return fold_build1 (CONJ_EXPR, type, arg0);
9805 break;
9807 CASE_FLT_FN (BUILT_IN_CREAL):
9808 if (validate_arg (arg0, COMPLEX_TYPE))
9809 return non_lvalue (fold_build1 (REALPART_EXPR, type, arg0));;
9810 break;
9812 CASE_FLT_FN (BUILT_IN_CIMAG):
9813 if (validate_arg (arg0, COMPLEX_TYPE))
9814 return non_lvalue (fold_build1 (IMAGPART_EXPR, type, arg0));
9815 break;
9817 CASE_FLT_FN (BUILT_IN_CCOS):
9818 CASE_FLT_FN (BUILT_IN_CCOSH):
9819 /* These functions are "even", i.e. f(x) == f(-x). */
9820 if (validate_arg (arg0, COMPLEX_TYPE))
9822 tree narg = fold_strip_sign_ops (arg0);
9823 if (narg)
9824 return build_call_expr (fndecl, 1, narg);
9826 break;
9828 CASE_FLT_FN (BUILT_IN_CABS):
9829 return fold_builtin_cabs (arg0, type, fndecl);
9831 CASE_FLT_FN (BUILT_IN_CARG):
9832 return fold_builtin_carg (arg0, type);
9834 CASE_FLT_FN (BUILT_IN_SQRT):
9835 return fold_builtin_sqrt (arg0, type);
9837 CASE_FLT_FN (BUILT_IN_CBRT):
9838 return fold_builtin_cbrt (arg0, type);
9840 CASE_FLT_FN (BUILT_IN_ASIN):
9841 if (validate_arg (arg0, REAL_TYPE))
9842 return do_mpfr_arg1 (arg0, type, mpfr_asin,
9843 &dconstm1, &dconst1, true);
9844 break;
9846 CASE_FLT_FN (BUILT_IN_ACOS):
9847 if (validate_arg (arg0, REAL_TYPE))
9848 return do_mpfr_arg1 (arg0, type, mpfr_acos,
9849 &dconstm1, &dconst1, true);
9850 break;
9852 CASE_FLT_FN (BUILT_IN_ATAN):
9853 if (validate_arg (arg0, REAL_TYPE))
9854 return do_mpfr_arg1 (arg0, type, mpfr_atan, NULL, NULL, 0);
9855 break;
9857 CASE_FLT_FN (BUILT_IN_ASINH):
9858 if (validate_arg (arg0, REAL_TYPE))
9859 return do_mpfr_arg1 (arg0, type, mpfr_asinh, NULL, NULL, 0);
9860 break;
9862 CASE_FLT_FN (BUILT_IN_ACOSH):
9863 if (validate_arg (arg0, REAL_TYPE))
9864 return do_mpfr_arg1 (arg0, type, mpfr_acosh,
9865 &dconst1, NULL, true);
9866 break;
9868 CASE_FLT_FN (BUILT_IN_ATANH):
9869 if (validate_arg (arg0, REAL_TYPE))
9870 return do_mpfr_arg1 (arg0, type, mpfr_atanh,
9871 &dconstm1, &dconst1, false);
9872 break;
9874 CASE_FLT_FN (BUILT_IN_SIN):
9875 if (validate_arg (arg0, REAL_TYPE))
9876 return do_mpfr_arg1 (arg0, type, mpfr_sin, NULL, NULL, 0);
9877 break;
9879 CASE_FLT_FN (BUILT_IN_COS):
9880 return fold_builtin_cos (arg0, type, fndecl);
9881 break;
9883 CASE_FLT_FN (BUILT_IN_TAN):
9884 return fold_builtin_tan (arg0, type);
9886 CASE_FLT_FN (BUILT_IN_CEXP):
9887 return fold_builtin_cexp (arg0, type);
9889 CASE_FLT_FN (BUILT_IN_CEXPI):
9890 if (validate_arg (arg0, REAL_TYPE))
9891 return do_mpfr_sincos (arg0, NULL_TREE, NULL_TREE);
9892 break;
9894 CASE_FLT_FN (BUILT_IN_SINH):
9895 if (validate_arg (arg0, REAL_TYPE))
9896 return do_mpfr_arg1 (arg0, type, mpfr_sinh, NULL, NULL, 0);
9897 break;
9899 CASE_FLT_FN (BUILT_IN_COSH):
9900 return fold_builtin_cosh (arg0, type, fndecl);
9902 CASE_FLT_FN (BUILT_IN_TANH):
9903 if (validate_arg (arg0, REAL_TYPE))
9904 return do_mpfr_arg1 (arg0, type, mpfr_tanh, NULL, NULL, 0);
9905 break;
9907 CASE_FLT_FN (BUILT_IN_ERF):
9908 if (validate_arg (arg0, REAL_TYPE))
9909 return do_mpfr_arg1 (arg0, type, mpfr_erf, NULL, NULL, 0);
9910 break;
9912 CASE_FLT_FN (BUILT_IN_ERFC):
9913 if (validate_arg (arg0, REAL_TYPE))
9914 return do_mpfr_arg1 (arg0, type, mpfr_erfc, NULL, NULL, 0);
9915 break;
9917 CASE_FLT_FN (BUILT_IN_TGAMMA):
9918 if (validate_arg (arg0, REAL_TYPE))
9919 return do_mpfr_arg1 (arg0, type, mpfr_gamma, NULL, NULL, 0);
9920 break;
9922 CASE_FLT_FN (BUILT_IN_EXP):
9923 return fold_builtin_exponent (fndecl, arg0, mpfr_exp);
9925 CASE_FLT_FN (BUILT_IN_EXP2):
9926 return fold_builtin_exponent (fndecl, arg0, mpfr_exp2);
9928 CASE_FLT_FN (BUILT_IN_EXP10):
9929 CASE_FLT_FN (BUILT_IN_POW10):
9930 return fold_builtin_exponent (fndecl, arg0, mpfr_exp10);
9932 CASE_FLT_FN (BUILT_IN_EXPM1):
9933 if (validate_arg (arg0, REAL_TYPE))
9934 return do_mpfr_arg1 (arg0, type, mpfr_expm1, NULL, NULL, 0);
9935 break;
9937 CASE_FLT_FN (BUILT_IN_LOG):
9938 return fold_builtin_logarithm (fndecl, arg0, mpfr_log);
9940 CASE_FLT_FN (BUILT_IN_LOG2):
9941 return fold_builtin_logarithm (fndecl, arg0, mpfr_log2);
9943 CASE_FLT_FN (BUILT_IN_LOG10):
9944 return fold_builtin_logarithm (fndecl, arg0, mpfr_log10);
9946 CASE_FLT_FN (BUILT_IN_LOG1P):
9947 if (validate_arg (arg0, REAL_TYPE))
9948 return do_mpfr_arg1 (arg0, type, mpfr_log1p,
9949 &dconstm1, NULL, false);
9950 break;
9952 #if MPFR_VERSION >= MPFR_VERSION_NUM(2,3,0)
9953 CASE_FLT_FN (BUILT_IN_J0):
9954 if (validate_arg (arg0, REAL_TYPE))
9955 return do_mpfr_arg1 (arg0, type, mpfr_j0,
9956 NULL, NULL, 0);
9957 break;
9959 CASE_FLT_FN (BUILT_IN_J1):
9960 if (validate_arg (arg0, REAL_TYPE))
9961 return do_mpfr_arg1 (arg0, type, mpfr_j1,
9962 NULL, NULL, 0);
9963 break;
9965 CASE_FLT_FN (BUILT_IN_Y0):
9966 if (validate_arg (arg0, REAL_TYPE))
9967 return do_mpfr_arg1 (arg0, type, mpfr_y0,
9968 &dconst0, NULL, false);
9969 break;
9971 CASE_FLT_FN (BUILT_IN_Y1):
9972 if (validate_arg (arg0, REAL_TYPE))
9973 return do_mpfr_arg1 (arg0, type, mpfr_y1,
9974 &dconst0, NULL, false);
9975 break;
9976 #endif
9978 CASE_FLT_FN (BUILT_IN_NAN):
9979 case BUILT_IN_NAND32:
9980 case BUILT_IN_NAND64:
9981 case BUILT_IN_NAND128:
9982 return fold_builtin_nan (arg0, type, true);
9984 CASE_FLT_FN (BUILT_IN_NANS):
9985 return fold_builtin_nan (arg0, type, false);
9987 CASE_FLT_FN (BUILT_IN_FLOOR):
9988 return fold_builtin_floor (fndecl, arg0);
9990 CASE_FLT_FN (BUILT_IN_CEIL):
9991 return fold_builtin_ceil (fndecl, arg0);
9993 CASE_FLT_FN (BUILT_IN_TRUNC):
9994 return fold_builtin_trunc (fndecl, arg0);
9996 CASE_FLT_FN (BUILT_IN_ROUND):
9997 return fold_builtin_round (fndecl, arg0);
9999 CASE_FLT_FN (BUILT_IN_NEARBYINT):
10000 CASE_FLT_FN (BUILT_IN_RINT):
10001 return fold_trunc_transparent_mathfn (fndecl, arg0);
10003 CASE_FLT_FN (BUILT_IN_LCEIL):
10004 CASE_FLT_FN (BUILT_IN_LLCEIL):
10005 CASE_FLT_FN (BUILT_IN_LFLOOR):
10006 CASE_FLT_FN (BUILT_IN_LLFLOOR):
10007 CASE_FLT_FN (BUILT_IN_LROUND):
10008 CASE_FLT_FN (BUILT_IN_LLROUND):
10009 return fold_builtin_int_roundingfn (fndecl, arg0);
10011 CASE_FLT_FN (BUILT_IN_LRINT):
10012 CASE_FLT_FN (BUILT_IN_LLRINT):
10013 return fold_fixed_mathfn (fndecl, arg0);
10015 case BUILT_IN_BSWAP32:
10016 case BUILT_IN_BSWAP64:
10017 return fold_builtin_bswap (fndecl, arg0);
10019 CASE_INT_FN (BUILT_IN_FFS):
10020 CASE_INT_FN (BUILT_IN_CLZ):
10021 CASE_INT_FN (BUILT_IN_CTZ):
10022 CASE_INT_FN (BUILT_IN_POPCOUNT):
10023 CASE_INT_FN (BUILT_IN_PARITY):
10024 return fold_builtin_bitop (fndecl, arg0);
10026 CASE_FLT_FN (BUILT_IN_SIGNBIT):
10027 return fold_builtin_signbit (arg0, type);
10029 CASE_FLT_FN (BUILT_IN_SIGNIFICAND):
10030 return fold_builtin_significand (arg0, type);
10032 CASE_FLT_FN (BUILT_IN_ILOGB):
10033 CASE_FLT_FN (BUILT_IN_LOGB):
10034 return fold_builtin_logb (arg0, type);
10036 case BUILT_IN_ISASCII:
10037 return fold_builtin_isascii (arg0);
10039 case BUILT_IN_TOASCII:
10040 return fold_builtin_toascii (arg0);
10042 case BUILT_IN_ISDIGIT:
10043 return fold_builtin_isdigit (arg0);
10045 CASE_FLT_FN (BUILT_IN_FINITE):
10046 case BUILT_IN_FINITED32:
10047 case BUILT_IN_FINITED64:
10048 case BUILT_IN_FINITED128:
10049 case BUILT_IN_ISFINITE:
10050 return fold_builtin_classify (fndecl, arg0, BUILT_IN_ISFINITE);
10052 CASE_FLT_FN (BUILT_IN_ISINF):
10053 case BUILT_IN_ISINFD32:
10054 case BUILT_IN_ISINFD64:
10055 case BUILT_IN_ISINFD128:
10056 return fold_builtin_classify (fndecl, arg0, BUILT_IN_ISINF);
10058 CASE_FLT_FN (BUILT_IN_ISNAN):
10059 case BUILT_IN_ISNAND32:
10060 case BUILT_IN_ISNAND64:
10061 case BUILT_IN_ISNAND128:
10062 return fold_builtin_classify (fndecl, arg0, BUILT_IN_ISNAN);
10064 case BUILT_IN_PRINTF:
10065 case BUILT_IN_PRINTF_UNLOCKED:
10066 case BUILT_IN_VPRINTF:
10067 return fold_builtin_printf (fndecl, arg0, NULL_TREE, ignore, fcode);
10069 default:
10070 break;
10073 return NULL_TREE;
10077 /* Fold a call to built-in function FNDECL with 2 arguments, ARG0 and ARG1.
10078 IGNORE is true if the result of the function call is ignored. This
10079 function returns NULL_TREE if no simplification was possible. */
10081 static tree
10082 fold_builtin_2 (tree fndecl, tree arg0, tree arg1, bool ignore)
10084 tree type = TREE_TYPE (TREE_TYPE (fndecl));
10085 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10087 switch (fcode)
10089 #if MPFR_VERSION >= MPFR_VERSION_NUM(2,3,0)
10090 CASE_FLT_FN (BUILT_IN_JN):
10091 if (validate_arg (arg0, INTEGER_TYPE)
10092 && validate_arg (arg1, REAL_TYPE))
10093 return do_mpfr_bessel_n (arg0, arg1, type, mpfr_jn, NULL, 0);
10094 break;
10096 CASE_FLT_FN (BUILT_IN_YN):
10097 if (validate_arg (arg0, INTEGER_TYPE)
10098 && validate_arg (arg1, REAL_TYPE))
10099 return do_mpfr_bessel_n (arg0, arg1, type, mpfr_yn,
10100 &dconst0, false);
10101 break;
10103 CASE_FLT_FN (BUILT_IN_DREM):
10104 CASE_FLT_FN (BUILT_IN_REMAINDER):
10105 if (validate_arg (arg0, REAL_TYPE)
10106 && validate_arg(arg1, REAL_TYPE))
10107 return do_mpfr_arg2 (arg0, arg1, type, mpfr_remainder);
10108 break;
10110 CASE_FLT_FN_REENT (BUILT_IN_GAMMA): /* GAMMA_R */
10111 CASE_FLT_FN_REENT (BUILT_IN_LGAMMA): /* LGAMMA_R */
10112 if (validate_arg (arg0, REAL_TYPE)
10113 && validate_arg(arg1, POINTER_TYPE))
10114 return do_mpfr_lgamma_r (arg0, arg1, type);
10115 break;
10116 #endif
10118 CASE_FLT_FN (BUILT_IN_ATAN2):
10119 if (validate_arg (arg0, REAL_TYPE)
10120 && validate_arg(arg1, REAL_TYPE))
10121 return do_mpfr_arg2 (arg0, arg1, type, mpfr_atan2);
10122 break;
10124 CASE_FLT_FN (BUILT_IN_FDIM):
10125 if (validate_arg (arg0, REAL_TYPE)
10126 && validate_arg(arg1, REAL_TYPE))
10127 return do_mpfr_arg2 (arg0, arg1, type, mpfr_dim);
10128 break;
10130 CASE_FLT_FN (BUILT_IN_HYPOT):
10131 return fold_builtin_hypot (fndecl, arg0, arg1, type);
10133 CASE_FLT_FN (BUILT_IN_LDEXP):
10134 return fold_builtin_load_exponent (arg0, arg1, type, /*ldexp=*/true);
10135 CASE_FLT_FN (BUILT_IN_SCALBN):
10136 CASE_FLT_FN (BUILT_IN_SCALBLN):
10137 return fold_builtin_load_exponent (arg0, arg1, type, /*ldexp=*/false);
10139 CASE_FLT_FN (BUILT_IN_FREXP):
10140 return fold_builtin_frexp (arg0, arg1, type);
10142 CASE_FLT_FN (BUILT_IN_MODF):
10143 return fold_builtin_modf (arg0, arg1, type);
10145 case BUILT_IN_BZERO:
10146 return fold_builtin_bzero (arg0, arg1, ignore);
10148 case BUILT_IN_FPUTS:
10149 return fold_builtin_fputs (arg0, arg1, ignore, false, NULL_TREE);
10151 case BUILT_IN_FPUTS_UNLOCKED:
10152 return fold_builtin_fputs (arg0, arg1, ignore, true, NULL_TREE);
10154 case BUILT_IN_STRSTR:
10155 return fold_builtin_strstr (arg0, arg1, type);
10157 case BUILT_IN_STRCAT:
10158 return fold_builtin_strcat (arg0, arg1);
10160 case BUILT_IN_STRSPN:
10161 return fold_builtin_strspn (arg0, arg1);
10163 case BUILT_IN_STRCSPN:
10164 return fold_builtin_strcspn (arg0, arg1);
10166 case BUILT_IN_STRCHR:
10167 case BUILT_IN_INDEX:
10168 return fold_builtin_strchr (arg0, arg1, type);
10170 case BUILT_IN_STRRCHR:
10171 case BUILT_IN_RINDEX:
10172 return fold_builtin_strrchr (arg0, arg1, type);
10174 case BUILT_IN_STRCPY:
10175 return fold_builtin_strcpy (fndecl, arg0, arg1, NULL_TREE);
10177 case BUILT_IN_STRCMP:
10178 return fold_builtin_strcmp (arg0, arg1);
10180 case BUILT_IN_STRPBRK:
10181 return fold_builtin_strpbrk (arg0, arg1, type);
10183 case BUILT_IN_EXPECT:
10184 return fold_builtin_expect (arg0, arg1);
10186 CASE_FLT_FN (BUILT_IN_POW):
10187 return fold_builtin_pow (fndecl, arg0, arg1, type);
10189 CASE_FLT_FN (BUILT_IN_POWI):
10190 return fold_builtin_powi (fndecl, arg0, arg1, type);
10192 CASE_FLT_FN (BUILT_IN_COPYSIGN):
10193 return fold_builtin_copysign (fndecl, arg0, arg1, type);
10195 CASE_FLT_FN (BUILT_IN_FMIN):
10196 return fold_builtin_fmin_fmax (arg0, arg1, type, /*max=*/false);
10198 CASE_FLT_FN (BUILT_IN_FMAX):
10199 return fold_builtin_fmin_fmax (arg0, arg1, type, /*max=*/true);
10201 case BUILT_IN_ISGREATER:
10202 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNLE_EXPR, LE_EXPR);
10203 case BUILT_IN_ISGREATEREQUAL:
10204 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNLT_EXPR, LT_EXPR);
10205 case BUILT_IN_ISLESS:
10206 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNGE_EXPR, GE_EXPR);
10207 case BUILT_IN_ISLESSEQUAL:
10208 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNGT_EXPR, GT_EXPR);
10209 case BUILT_IN_ISLESSGREATER:
10210 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNEQ_EXPR, EQ_EXPR);
10211 case BUILT_IN_ISUNORDERED:
10212 return fold_builtin_unordered_cmp (fndecl, arg0, arg1, UNORDERED_EXPR,
10213 NOP_EXPR);
10215 /* We do the folding for va_start in the expander. */
10216 case BUILT_IN_VA_START:
10217 break;
10219 case BUILT_IN_SPRINTF:
10220 return fold_builtin_sprintf (arg0, arg1, NULL_TREE, ignore);
10222 case BUILT_IN_OBJECT_SIZE:
10223 return fold_builtin_object_size (arg0, arg1);
10225 case BUILT_IN_PRINTF:
10226 case BUILT_IN_PRINTF_UNLOCKED:
10227 case BUILT_IN_VPRINTF:
10228 return fold_builtin_printf (fndecl, arg0, arg1, ignore, fcode);
10230 case BUILT_IN_PRINTF_CHK:
10231 case BUILT_IN_VPRINTF_CHK:
10232 if (!validate_arg (arg0, INTEGER_TYPE)
10233 || TREE_SIDE_EFFECTS (arg0))
10234 return NULL_TREE;
10235 else
10236 return fold_builtin_printf (fndecl, arg1, NULL_TREE, ignore, fcode);
10237 break;
10239 case BUILT_IN_FPRINTF:
10240 case BUILT_IN_FPRINTF_UNLOCKED:
10241 case BUILT_IN_VFPRINTF:
10242 return fold_builtin_fprintf (fndecl, arg0, arg1, NULL_TREE,
10243 ignore, fcode);
10245 default:
10246 break;
10248 return NULL_TREE;
10251 /* Fold a call to built-in function FNDECL with 3 arguments, ARG0, ARG1,
10252 and ARG2. IGNORE is true if the result of the function call is ignored.
10253 This function returns NULL_TREE if no simplification was possible. */
10255 static tree
10256 fold_builtin_3 (tree fndecl, tree arg0, tree arg1, tree arg2, bool ignore)
10258 tree type = TREE_TYPE (TREE_TYPE (fndecl));
10259 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10260 switch (fcode)
10263 CASE_FLT_FN (BUILT_IN_SINCOS):
10264 return fold_builtin_sincos (arg0, arg1, arg2);
10266 CASE_FLT_FN (BUILT_IN_FMA):
10267 if (validate_arg (arg0, REAL_TYPE)
10268 && validate_arg(arg1, REAL_TYPE)
10269 && validate_arg(arg2, REAL_TYPE))
10270 return do_mpfr_arg3 (arg0, arg1, arg2, type, mpfr_fma);
10271 break;
10273 #if MPFR_VERSION >= MPFR_VERSION_NUM(2,3,0)
10274 CASE_FLT_FN (BUILT_IN_REMQUO):
10275 if (validate_arg (arg0, REAL_TYPE)
10276 && validate_arg(arg1, REAL_TYPE)
10277 && validate_arg(arg2, POINTER_TYPE))
10278 return do_mpfr_remquo (arg0, arg1, arg2);
10279 break;
10280 #endif
10282 case BUILT_IN_MEMSET:
10283 return fold_builtin_memset (arg0, arg1, arg2, type, ignore);
10285 case BUILT_IN_BCOPY:
10286 return fold_builtin_memory_op (arg1, arg0, arg2, void_type_node, true, /*endp=*/3);
10288 case BUILT_IN_MEMCPY:
10289 return fold_builtin_memory_op (arg0, arg1, arg2, type, ignore, /*endp=*/0);
10291 case BUILT_IN_MEMPCPY:
10292 return fold_builtin_memory_op (arg0, arg1, arg2, type, ignore, /*endp=*/1);
10294 case BUILT_IN_MEMMOVE:
10295 return fold_builtin_memory_op (arg0, arg1, arg2, type, ignore, /*endp=*/3);
10297 case BUILT_IN_STRNCAT:
10298 return fold_builtin_strncat (arg0, arg1, arg2);
10300 case BUILT_IN_STRNCPY:
10301 return fold_builtin_strncpy (fndecl, arg0, arg1, arg2, NULL_TREE);
10303 case BUILT_IN_STRNCMP:
10304 return fold_builtin_strncmp (arg0, arg1, arg2);
10306 case BUILT_IN_MEMCHR:
10307 return fold_builtin_memchr (arg0, arg1, arg2, type);
10309 case BUILT_IN_BCMP:
10310 case BUILT_IN_MEMCMP:
10311 return fold_builtin_memcmp (arg0, arg1, arg2);;
10313 case BUILT_IN_SPRINTF:
10314 return fold_builtin_sprintf (arg0, arg1, arg2, ignore);
10316 case BUILT_IN_STRCPY_CHK:
10317 case BUILT_IN_STPCPY_CHK:
10318 return fold_builtin_stxcpy_chk (fndecl, arg0, arg1, arg2, NULL_TREE,
10319 ignore, fcode);
10321 case BUILT_IN_STRCAT_CHK:
10322 return fold_builtin_strcat_chk (fndecl, arg0, arg1, arg2);
10324 case BUILT_IN_PRINTF_CHK:
10325 case BUILT_IN_VPRINTF_CHK:
10326 if (!validate_arg (arg0, INTEGER_TYPE)
10327 || TREE_SIDE_EFFECTS (arg0))
10328 return NULL_TREE;
10329 else
10330 return fold_builtin_printf (fndecl, arg1, arg2, ignore, fcode);
10331 break;
10333 case BUILT_IN_FPRINTF:
10334 case BUILT_IN_FPRINTF_UNLOCKED:
10335 case BUILT_IN_VFPRINTF:
10336 return fold_builtin_fprintf (fndecl, arg0, arg1, arg2, ignore, fcode);
10338 case BUILT_IN_FPRINTF_CHK:
10339 case BUILT_IN_VFPRINTF_CHK:
10340 if (!validate_arg (arg1, INTEGER_TYPE)
10341 || TREE_SIDE_EFFECTS (arg1))
10342 return NULL_TREE;
10343 else
10344 return fold_builtin_fprintf (fndecl, arg0, arg2, NULL_TREE,
10345 ignore, fcode);
10347 default:
10348 break;
10350 return NULL_TREE;
10353 /* Fold a call to built-in function FNDECL with 4 arguments, ARG0, ARG1,
10354 ARG2, and ARG3. IGNORE is true if the result of the function call is
10355 ignored. This function returns NULL_TREE if no simplification was
10356 possible. */
10358 static tree
10359 fold_builtin_4 (tree fndecl, tree arg0, tree arg1, tree arg2, tree arg3,
10360 bool ignore)
10362 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10364 switch (fcode)
10366 case BUILT_IN_MEMCPY_CHK:
10367 case BUILT_IN_MEMPCPY_CHK:
10368 case BUILT_IN_MEMMOVE_CHK:
10369 case BUILT_IN_MEMSET_CHK:
10370 return fold_builtin_memory_chk (fndecl, arg0, arg1, arg2, arg3,
10371 NULL_TREE, ignore,
10372 DECL_FUNCTION_CODE (fndecl));
10374 case BUILT_IN_STRNCPY_CHK:
10375 return fold_builtin_strncpy_chk (arg0, arg1, arg2, arg3, NULL_TREE);
10377 case BUILT_IN_STRNCAT_CHK:
10378 return fold_builtin_strncat_chk (fndecl, arg0, arg1, arg2, arg3);
10380 case BUILT_IN_FPRINTF_CHK:
10381 case BUILT_IN_VFPRINTF_CHK:
10382 if (!validate_arg (arg1, INTEGER_TYPE)
10383 || TREE_SIDE_EFFECTS (arg1))
10384 return NULL_TREE;
10385 else
10386 return fold_builtin_fprintf (fndecl, arg0, arg2, arg3,
10387 ignore, fcode);
10388 break;
10390 default:
10391 break;
10393 return NULL_TREE;
10396 /* Fold a call to built-in function FNDECL. ARGS is an array of NARGS
10397 arguments, where NARGS <= 4. IGNORE is true if the result of the
10398 function call is ignored. This function returns NULL_TREE if no
10399 simplification was possible. Note that this only folds builtins with
10400 fixed argument patterns. Foldings that do varargs-to-varargs
10401 transformations, or that match calls with more than 4 arguments,
10402 need to be handled with fold_builtin_varargs instead. */
10404 #define MAX_ARGS_TO_FOLD_BUILTIN 4
10406 static tree
10407 fold_builtin_n (tree fndecl, tree *args, int nargs, bool ignore)
10409 tree ret = NULL_TREE;
10410 switch (nargs)
10412 case 0:
10413 ret = fold_builtin_0 (fndecl, ignore);
10414 break;
10415 case 1:
10416 ret = fold_builtin_1 (fndecl, args[0], ignore);
10417 break;
10418 case 2:
10419 ret = fold_builtin_2 (fndecl, args[0], args[1], ignore);
10420 break;
10421 case 3:
10422 ret = fold_builtin_3 (fndecl, args[0], args[1], args[2], ignore);
10423 break;
10424 case 4:
10425 ret = fold_builtin_4 (fndecl, args[0], args[1], args[2], args[3],
10426 ignore);
10427 break;
10428 default:
10429 break;
10431 if (ret)
10433 ret = build1 (NOP_EXPR, GENERIC_TREE_TYPE (ret), ret);
10434 TREE_NO_WARNING (ret) = 1;
10435 return ret;
10437 return NULL_TREE;
10440 /* Builtins with folding operations that operate on "..." arguments
10441 need special handling; we need to store the arguments in a convenient
10442 data structure before attempting any folding. Fortunately there are
10443 only a few builtins that fall into this category. FNDECL is the
10444 function, EXP is the CALL_EXPR for the call, and IGNORE is true if the
10445 result of the function call is ignored. */
10447 static tree
10448 fold_builtin_varargs (tree fndecl, tree exp, bool ignore ATTRIBUTE_UNUSED)
10450 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10451 tree ret = NULL_TREE;
10453 switch (fcode)
10455 case BUILT_IN_SPRINTF_CHK:
10456 case BUILT_IN_VSPRINTF_CHK:
10457 ret = fold_builtin_sprintf_chk (exp, fcode);
10458 break;
10460 case BUILT_IN_SNPRINTF_CHK:
10461 case BUILT_IN_VSNPRINTF_CHK:
10462 ret = fold_builtin_snprintf_chk (exp, NULL_TREE, fcode);
10464 default:
10465 break;
10467 if (ret)
10469 ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
10470 TREE_NO_WARNING (ret) = 1;
10471 return ret;
10473 return NULL_TREE;
10476 /* A wrapper function for builtin folding that prevents warnings for
10477 "statement without effect" and the like, caused by removing the
10478 call node earlier than the warning is generated. */
10480 tree
10481 fold_call_expr (tree exp, bool ignore)
10483 tree ret = NULL_TREE;
10484 tree fndecl = get_callee_fndecl (exp);
10485 if (fndecl
10486 && TREE_CODE (fndecl) == FUNCTION_DECL
10487 && DECL_BUILT_IN (fndecl)
10488 /* If CALL_EXPR_VA_ARG_PACK is set, the arguments aren't finalized
10489 yet. Defer folding until we see all the arguments
10490 (after inlining). */
10491 && !CALL_EXPR_VA_ARG_PACK (exp))
10493 int nargs = call_expr_nargs (exp);
10495 /* Before gimplification CALL_EXPR_VA_ARG_PACK is not set, but
10496 instead last argument is __builtin_va_arg_pack (). Defer folding
10497 even in that case, until arguments are finalized. */
10498 if (nargs && TREE_CODE (CALL_EXPR_ARG (exp, nargs - 1)) == CALL_EXPR)
10500 tree fndecl2 = get_callee_fndecl (CALL_EXPR_ARG (exp, nargs - 1));
10501 if (fndecl2
10502 && TREE_CODE (fndecl2) == FUNCTION_DECL
10503 && DECL_BUILT_IN_CLASS (fndecl2) == BUILT_IN_NORMAL
10504 && DECL_FUNCTION_CODE (fndecl2) == BUILT_IN_VA_ARG_PACK)
10505 return NULL_TREE;
10508 /* FIXME: Don't use a list in this interface. */
10509 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
10510 return targetm.fold_builtin (fndecl, CALL_EXPR_ARGS (exp), ignore);
10511 else
10513 if (nargs <= MAX_ARGS_TO_FOLD_BUILTIN)
10515 tree *args = CALL_EXPR_ARGP (exp);
10516 ret = fold_builtin_n (fndecl, args, nargs, ignore);
10518 if (!ret)
10519 ret = fold_builtin_varargs (fndecl, exp, ignore);
10520 if (ret)
10522 /* Propagate location information from original call to
10523 expansion of builtin. Otherwise things like
10524 maybe_emit_chk_warning, that operate on the expansion
10525 of a builtin, will use the wrong location information. */
10526 if (CAN_HAVE_LOCATION_P (exp) && EXPR_HAS_LOCATION (exp))
10528 tree realret = ret;
10529 if (TREE_CODE (ret) == NOP_EXPR)
10530 realret = TREE_OPERAND (ret, 0);
10531 if (CAN_HAVE_LOCATION_P (realret)
10532 && !EXPR_HAS_LOCATION (realret))
10533 SET_EXPR_LOCATION (realret, EXPR_LOCATION (exp));
10535 return ret;
10539 return NULL_TREE;
10542 /* Conveniently construct a function call expression. FNDECL names the
10543 function to be called and ARGLIST is a TREE_LIST of arguments. */
10545 tree
10546 build_function_call_expr (tree fndecl, tree arglist)
10548 tree fntype = TREE_TYPE (fndecl);
10549 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10550 int n = list_length (arglist);
10551 tree *argarray = (tree *) alloca (n * sizeof (tree));
10552 int i;
10554 for (i = 0; i < n; i++, arglist = TREE_CHAIN (arglist))
10555 argarray[i] = TREE_VALUE (arglist);
10556 return fold_builtin_call_array (TREE_TYPE (fntype), fn, n, argarray);
10559 /* Conveniently construct a function call expression. FNDECL names the
10560 function to be called, N is the number of arguments, and the "..."
10561 parameters are the argument expressions. */
10563 tree
10564 build_call_expr (tree fndecl, int n, ...)
10566 va_list ap;
10567 tree fntype = TREE_TYPE (fndecl);
10568 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10569 tree *argarray = (tree *) alloca (n * sizeof (tree));
10570 int i;
10572 va_start (ap, n);
10573 for (i = 0; i < n; i++)
10574 argarray[i] = va_arg (ap, tree);
10575 va_end (ap);
10576 return fold_builtin_call_array (TREE_TYPE (fntype), fn, n, argarray);
10579 /* Construct a CALL_EXPR with type TYPE with FN as the function expression.
10580 N arguments are passed in the array ARGARRAY. */
10582 tree
10583 fold_builtin_call_array (tree type,
10584 tree fn,
10585 int n,
10586 tree *argarray)
10588 tree ret = NULL_TREE;
10589 int i;
10590 tree exp;
10592 if (TREE_CODE (fn) == ADDR_EXPR)
10594 tree fndecl = TREE_OPERAND (fn, 0);
10595 if (TREE_CODE (fndecl) == FUNCTION_DECL
10596 && DECL_BUILT_IN (fndecl))
10598 /* If last argument is __builtin_va_arg_pack (), arguments to this
10599 function are not finalized yet. Defer folding until they are. */
10600 if (n && TREE_CODE (argarray[n - 1]) == CALL_EXPR)
10602 tree fndecl2 = get_callee_fndecl (argarray[n - 1]);
10603 if (fndecl2
10604 && TREE_CODE (fndecl2) == FUNCTION_DECL
10605 && DECL_BUILT_IN_CLASS (fndecl2) == BUILT_IN_NORMAL
10606 && DECL_FUNCTION_CODE (fndecl2) == BUILT_IN_VA_ARG_PACK)
10607 return build_call_array (type, fn, n, argarray);
10609 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
10611 tree arglist = NULL_TREE;
10612 for (i = n - 1; i >= 0; i--)
10613 arglist = tree_cons (NULL_TREE, argarray[i], arglist);
10614 ret = targetm.fold_builtin (fndecl, arglist, false);
10615 if (ret)
10616 return ret;
10618 else if (n <= MAX_ARGS_TO_FOLD_BUILTIN)
10620 /* First try the transformations that don't require consing up
10621 an exp. */
10622 ret = fold_builtin_n (fndecl, argarray, n, false);
10623 if (ret)
10624 return ret;
10627 /* If we got this far, we need to build an exp. */
10628 exp = build_call_array (type, fn, n, argarray);
10629 ret = fold_builtin_varargs (fndecl, exp, false);
10630 return ret ? ret : exp;
10634 return build_call_array (type, fn, n, argarray);
10637 /* Construct a new CALL_EXPR using the tail of the argument list of EXP
10638 along with N new arguments specified as the "..." parameters. SKIP
10639 is the number of arguments in EXP to be omitted. This function is used
10640 to do varargs-to-varargs transformations. */
10642 static tree
10643 rewrite_call_expr (tree exp, int skip, tree fndecl, int n, ...)
10645 int oldnargs = call_expr_nargs (exp);
10646 int nargs = oldnargs - skip + n;
10647 tree fntype = TREE_TYPE (fndecl);
10648 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10649 tree *buffer;
10651 if (n > 0)
10653 int i, j;
10654 va_list ap;
10656 buffer = alloca (nargs * sizeof (tree));
10657 va_start (ap, n);
10658 for (i = 0; i < n; i++)
10659 buffer[i] = va_arg (ap, tree);
10660 va_end (ap);
10661 for (j = skip; j < oldnargs; j++, i++)
10662 buffer[i] = CALL_EXPR_ARG (exp, j);
10664 else
10665 buffer = CALL_EXPR_ARGP (exp) + skip;
10667 return fold (build_call_array (TREE_TYPE (exp), fn, nargs, buffer));
10670 /* Validate a single argument ARG against a tree code CODE representing
10671 a type. */
10673 static bool
10674 validate_arg (const_tree arg, enum tree_code code)
10676 if (!arg)
10677 return false;
10678 else if (code == POINTER_TYPE)
10679 return POINTER_TYPE_P (TREE_TYPE (arg));
10680 return code == TREE_CODE (TREE_TYPE (arg));
10683 /* This function validates the types of a function call argument list
10684 against a specified list of tree_codes. If the last specifier is a 0,
10685 that represents an ellipses, otherwise the last specifier must be a
10686 VOID_TYPE. */
10688 bool
10689 validate_arglist (const_tree callexpr, ...)
10691 enum tree_code code;
10692 bool res = 0;
10693 va_list ap;
10694 const_call_expr_arg_iterator iter;
10695 const_tree arg;
10697 va_start (ap, callexpr);
10698 init_const_call_expr_arg_iterator (callexpr, &iter);
10702 code = va_arg (ap, enum tree_code);
10703 switch (code)
10705 case 0:
10706 /* This signifies an ellipses, any further arguments are all ok. */
10707 res = true;
10708 goto end;
10709 case VOID_TYPE:
10710 /* This signifies an endlink, if no arguments remain, return
10711 true, otherwise return false. */
10712 res = !more_const_call_expr_args_p (&iter);
10713 goto end;
10714 default:
10715 /* If no parameters remain or the parameter's code does not
10716 match the specified code, return false. Otherwise continue
10717 checking any remaining arguments. */
10718 arg = next_const_call_expr_arg (&iter);
10719 if (!validate_arg (arg, code))
10720 goto end;
10721 break;
10724 while (1);
10726 /* We need gotos here since we can only have one VA_CLOSE in a
10727 function. */
10728 end: ;
10729 va_end (ap);
10731 return res;
10734 /* Default target-specific builtin expander that does nothing. */
10737 default_expand_builtin (tree exp ATTRIBUTE_UNUSED,
10738 rtx target ATTRIBUTE_UNUSED,
10739 rtx subtarget ATTRIBUTE_UNUSED,
10740 enum machine_mode mode ATTRIBUTE_UNUSED,
10741 int ignore ATTRIBUTE_UNUSED)
10743 return NULL_RTX;
10746 /* Returns true is EXP represents data that would potentially reside
10747 in a readonly section. */
10749 static bool
10750 readonly_data_expr (tree exp)
10752 STRIP_NOPS (exp);
10754 if (TREE_CODE (exp) != ADDR_EXPR)
10755 return false;
10757 exp = get_base_address (TREE_OPERAND (exp, 0));
10758 if (!exp)
10759 return false;
10761 /* Make sure we call decl_readonly_section only for trees it
10762 can handle (since it returns true for everything it doesn't
10763 understand). */
10764 if (TREE_CODE (exp) == STRING_CST
10765 || TREE_CODE (exp) == CONSTRUCTOR
10766 || (TREE_CODE (exp) == VAR_DECL && TREE_STATIC (exp)))
10767 return decl_readonly_section (exp, 0);
10768 else
10769 return false;
10772 /* Simplify a call to the strstr builtin. S1 and S2 are the arguments
10773 to the call, and TYPE is its return type.
10775 Return NULL_TREE if no simplification was possible, otherwise return the
10776 simplified form of the call as a tree.
10778 The simplified form may be a constant or other expression which
10779 computes the same value, but in a more efficient manner (including
10780 calls to other builtin functions).
10782 The call may contain arguments which need to be evaluated, but
10783 which are not useful to determine the result of the call. In
10784 this case we return a chain of COMPOUND_EXPRs. The LHS of each
10785 COMPOUND_EXPR will be an argument which must be evaluated.
10786 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
10787 COMPOUND_EXPR in the chain will contain the tree for the simplified
10788 form of the builtin function call. */
10790 static tree
10791 fold_builtin_strstr (tree s1, tree s2, tree type)
10793 if (!validate_arg (s1, POINTER_TYPE)
10794 || !validate_arg (s2, POINTER_TYPE))
10795 return NULL_TREE;
10796 else
10798 tree fn;
10799 const char *p1, *p2;
10801 p2 = c_getstr (s2);
10802 if (p2 == NULL)
10803 return NULL_TREE;
10805 p1 = c_getstr (s1);
10806 if (p1 != NULL)
10808 const char *r = strstr (p1, p2);
10809 tree tem;
10811 if (r == NULL)
10812 return build_int_cst (TREE_TYPE (s1), 0);
10814 /* Return an offset into the constant string argument. */
10815 tem = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (s1),
10816 s1, size_int (r - p1));
10817 return fold_convert (type, tem);
10820 /* The argument is const char *, and the result is char *, so we need
10821 a type conversion here to avoid a warning. */
10822 if (p2[0] == '\0')
10823 return fold_convert (type, s1);
10825 if (p2[1] != '\0')
10826 return NULL_TREE;
10828 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
10829 if (!fn)
10830 return NULL_TREE;
10832 /* New argument list transforming strstr(s1, s2) to
10833 strchr(s1, s2[0]). */
10834 return build_call_expr (fn, 2, s1, build_int_cst (NULL_TREE, p2[0]));
10838 /* Simplify a call to the strchr builtin. S1 and S2 are the arguments to
10839 the call, and TYPE is its return type.
10841 Return NULL_TREE if no simplification was possible, otherwise return the
10842 simplified form of the call as a tree.
10844 The simplified form may be a constant or other expression which
10845 computes the same value, but in a more efficient manner (including
10846 calls to other builtin functions).
10848 The call may contain arguments which need to be evaluated, but
10849 which are not useful to determine the result of the call. In
10850 this case we return a chain of COMPOUND_EXPRs. The LHS of each
10851 COMPOUND_EXPR will be an argument which must be evaluated.
10852 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
10853 COMPOUND_EXPR in the chain will contain the tree for the simplified
10854 form of the builtin function call. */
10856 static tree
10857 fold_builtin_strchr (tree s1, tree s2, tree type)
10859 if (!validate_arg (s1, POINTER_TYPE)
10860 || !validate_arg (s2, INTEGER_TYPE))
10861 return NULL_TREE;
10862 else
10864 const char *p1;
10866 if (TREE_CODE (s2) != INTEGER_CST)
10867 return NULL_TREE;
10869 p1 = c_getstr (s1);
10870 if (p1 != NULL)
10872 char c;
10873 const char *r;
10874 tree tem;
10876 if (target_char_cast (s2, &c))
10877 return NULL_TREE;
10879 r = strchr (p1, c);
10881 if (r == NULL)
10882 return build_int_cst (TREE_TYPE (s1), 0);
10884 /* Return an offset into the constant string argument. */
10885 tem = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (s1),
10886 s1, size_int (r - p1));
10887 return fold_convert (type, tem);
10889 return NULL_TREE;
10893 /* Simplify a call to the strrchr builtin. S1 and S2 are the arguments to
10894 the call, and TYPE is its return type.
10896 Return NULL_TREE if no simplification was possible, otherwise return the
10897 simplified form of the call as a tree.
10899 The simplified form may be a constant or other expression which
10900 computes the same value, but in a more efficient manner (including
10901 calls to other builtin functions).
10903 The call may contain arguments which need to be evaluated, but
10904 which are not useful to determine the result of the call. In
10905 this case we return a chain of COMPOUND_EXPRs. The LHS of each
10906 COMPOUND_EXPR will be an argument which must be evaluated.
10907 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
10908 COMPOUND_EXPR in the chain will contain the tree for the simplified
10909 form of the builtin function call. */
10911 static tree
10912 fold_builtin_strrchr (tree s1, tree s2, tree type)
10914 if (!validate_arg (s1, POINTER_TYPE)
10915 || !validate_arg (s2, INTEGER_TYPE))
10916 return NULL_TREE;
10917 else
10919 tree fn;
10920 const char *p1;
10922 if (TREE_CODE (s2) != INTEGER_CST)
10923 return NULL_TREE;
10925 p1 = c_getstr (s1);
10926 if (p1 != NULL)
10928 char c;
10929 const char *r;
10930 tree tem;
10932 if (target_char_cast (s2, &c))
10933 return NULL_TREE;
10935 r = strrchr (p1, c);
10937 if (r == NULL)
10938 return build_int_cst (TREE_TYPE (s1), 0);
10940 /* Return an offset into the constant string argument. */
10941 tem = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (s1),
10942 s1, size_int (r - p1));
10943 return fold_convert (type, tem);
10946 if (! integer_zerop (s2))
10947 return NULL_TREE;
10949 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
10950 if (!fn)
10951 return NULL_TREE;
10953 /* Transform strrchr(s1, '\0') to strchr(s1, '\0'). */
10954 return build_call_expr (fn, 2, s1, s2);
10958 /* Simplify a call to the strpbrk builtin. S1 and S2 are the arguments
10959 to the call, and TYPE is its return type.
10961 Return NULL_TREE if no simplification was possible, otherwise return the
10962 simplified form of the call as a tree.
10964 The simplified form may be a constant or other expression which
10965 computes the same value, but in a more efficient manner (including
10966 calls to other builtin functions).
10968 The call may contain arguments which need to be evaluated, but
10969 which are not useful to determine the result of the call. In
10970 this case we return a chain of COMPOUND_EXPRs. The LHS of each
10971 COMPOUND_EXPR will be an argument which must be evaluated.
10972 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
10973 COMPOUND_EXPR in the chain will contain the tree for the simplified
10974 form of the builtin function call. */
10976 static tree
10977 fold_builtin_strpbrk (tree s1, tree s2, tree type)
10979 if (!validate_arg (s1, POINTER_TYPE)
10980 || !validate_arg (s2, POINTER_TYPE))
10981 return NULL_TREE;
10982 else
10984 tree fn;
10985 const char *p1, *p2;
10987 p2 = c_getstr (s2);
10988 if (p2 == NULL)
10989 return NULL_TREE;
10991 p1 = c_getstr (s1);
10992 if (p1 != NULL)
10994 const char *r = strpbrk (p1, p2);
10995 tree tem;
10997 if (r == NULL)
10998 return build_int_cst (TREE_TYPE (s1), 0);
11000 /* Return an offset into the constant string argument. */
11001 tem = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (s1),
11002 s1, size_int (r - p1));
11003 return fold_convert (type, tem);
11006 if (p2[0] == '\0')
11007 /* strpbrk(x, "") == NULL.
11008 Evaluate and ignore s1 in case it had side-effects. */
11009 return omit_one_operand (TREE_TYPE (s1), integer_zero_node, s1);
11011 if (p2[1] != '\0')
11012 return NULL_TREE; /* Really call strpbrk. */
11014 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
11015 if (!fn)
11016 return NULL_TREE;
11018 /* New argument list transforming strpbrk(s1, s2) to
11019 strchr(s1, s2[0]). */
11020 return build_call_expr (fn, 2, s1, build_int_cst (NULL_TREE, p2[0]));
11024 /* Simplify a call to the strcat builtin. DST and SRC are the arguments
11025 to the call.
11027 Return NULL_TREE if no simplification was possible, otherwise return the
11028 simplified form of the call as a tree.
11030 The simplified form may be a constant or other expression which
11031 computes the same value, but in a more efficient manner (including
11032 calls to other builtin functions).
11034 The call may contain arguments which need to be evaluated, but
11035 which are not useful to determine the result of the call. In
11036 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11037 COMPOUND_EXPR will be an argument which must be evaluated.
11038 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11039 COMPOUND_EXPR in the chain will contain the tree for the simplified
11040 form of the builtin function call. */
11042 static tree
11043 fold_builtin_strcat (tree dst, tree src)
11045 if (!validate_arg (dst, POINTER_TYPE)
11046 || !validate_arg (src, POINTER_TYPE))
11047 return NULL_TREE;
11048 else
11050 const char *p = c_getstr (src);
11052 /* If the string length is zero, return the dst parameter. */
11053 if (p && *p == '\0')
11054 return dst;
11056 return NULL_TREE;
11060 /* Simplify a call to the strncat builtin. DST, SRC, and LEN are the
11061 arguments to the call.
11063 Return NULL_TREE if no simplification was possible, otherwise return the
11064 simplified form of the call as a tree.
11066 The simplified form may be a constant or other expression which
11067 computes the same value, but in a more efficient manner (including
11068 calls to other builtin functions).
11070 The call may contain arguments which need to be evaluated, but
11071 which are not useful to determine the result of the call. In
11072 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11073 COMPOUND_EXPR will be an argument which must be evaluated.
11074 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11075 COMPOUND_EXPR in the chain will contain the tree for the simplified
11076 form of the builtin function call. */
11078 static tree
11079 fold_builtin_strncat (tree dst, tree src, tree len)
11081 if (!validate_arg (dst, POINTER_TYPE)
11082 || !validate_arg (src, POINTER_TYPE)
11083 || !validate_arg (len, INTEGER_TYPE))
11084 return NULL_TREE;
11085 else
11087 const char *p = c_getstr (src);
11089 /* If the requested length is zero, or the src parameter string
11090 length is zero, return the dst parameter. */
11091 if (integer_zerop (len) || (p && *p == '\0'))
11092 return omit_two_operands (TREE_TYPE (dst), dst, src, len);
11094 /* If the requested len is greater than or equal to the string
11095 length, call strcat. */
11096 if (TREE_CODE (len) == INTEGER_CST && p
11097 && compare_tree_int (len, strlen (p)) >= 0)
11099 tree fn = implicit_built_in_decls[BUILT_IN_STRCAT];
11101 /* If the replacement _DECL isn't initialized, don't do the
11102 transformation. */
11103 if (!fn)
11104 return NULL_TREE;
11106 return build_call_expr (fn, 2, dst, src);
11108 return NULL_TREE;
11112 /* Simplify a call to the strspn builtin. S1 and S2 are the arguments
11113 to the call.
11115 Return NULL_TREE if no simplification was possible, otherwise return the
11116 simplified form of the call as a tree.
11118 The simplified form may be a constant or other expression which
11119 computes the same value, but in a more efficient manner (including
11120 calls to other builtin functions).
11122 The call may contain arguments which need to be evaluated, but
11123 which are not useful to determine the result of the call. In
11124 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11125 COMPOUND_EXPR will be an argument which must be evaluated.
11126 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11127 COMPOUND_EXPR in the chain will contain the tree for the simplified
11128 form of the builtin function call. */
11130 static tree
11131 fold_builtin_strspn (tree s1, tree s2)
11133 if (!validate_arg (s1, POINTER_TYPE)
11134 || !validate_arg (s2, POINTER_TYPE))
11135 return NULL_TREE;
11136 else
11138 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
11140 /* If both arguments are constants, evaluate at compile-time. */
11141 if (p1 && p2)
11143 const size_t r = strspn (p1, p2);
11144 return size_int (r);
11147 /* If either argument is "", return NULL_TREE. */
11148 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
11149 /* Evaluate and ignore both arguments in case either one has
11150 side-effects. */
11151 return omit_two_operands (integer_type_node, integer_zero_node,
11152 s1, s2);
11153 return NULL_TREE;
11157 /* Simplify a call to the strcspn builtin. S1 and S2 are the arguments
11158 to the call.
11160 Return NULL_TREE if no simplification was possible, otherwise return the
11161 simplified form of the call as a tree.
11163 The simplified form may be a constant or other expression which
11164 computes the same value, but in a more efficient manner (including
11165 calls to other builtin functions).
11167 The call may contain arguments which need to be evaluated, but
11168 which are not useful to determine the result of the call. In
11169 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11170 COMPOUND_EXPR will be an argument which must be evaluated.
11171 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11172 COMPOUND_EXPR in the chain will contain the tree for the simplified
11173 form of the builtin function call. */
11175 static tree
11176 fold_builtin_strcspn (tree s1, tree s2)
11178 if (!validate_arg (s1, POINTER_TYPE)
11179 || !validate_arg (s2, POINTER_TYPE))
11180 return NULL_TREE;
11181 else
11183 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
11185 /* If both arguments are constants, evaluate at compile-time. */
11186 if (p1 && p2)
11188 const size_t r = strcspn (p1, p2);
11189 return size_int (r);
11192 /* If the first argument is "", return NULL_TREE. */
11193 if (p1 && *p1 == '\0')
11195 /* Evaluate and ignore argument s2 in case it has
11196 side-effects. */
11197 return omit_one_operand (integer_type_node,
11198 integer_zero_node, s2);
11201 /* If the second argument is "", return __builtin_strlen(s1). */
11202 if (p2 && *p2 == '\0')
11204 tree fn = implicit_built_in_decls[BUILT_IN_STRLEN];
11206 /* If the replacement _DECL isn't initialized, don't do the
11207 transformation. */
11208 if (!fn)
11209 return NULL_TREE;
11211 return build_call_expr (fn, 1, s1);
11213 return NULL_TREE;
11217 /* Fold a call to the fputs builtin. ARG0 and ARG1 are the arguments
11218 to the call. IGNORE is true if the value returned
11219 by the builtin will be ignored. UNLOCKED is true is true if this
11220 actually a call to fputs_unlocked. If LEN in non-NULL, it represents
11221 the known length of the string. Return NULL_TREE if no simplification
11222 was possible. */
11224 tree
11225 fold_builtin_fputs (tree arg0, tree arg1, bool ignore, bool unlocked, tree len)
11227 /* If we're using an unlocked function, assume the other unlocked
11228 functions exist explicitly. */
11229 tree const fn_fputc = unlocked ? built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
11230 : implicit_built_in_decls[BUILT_IN_FPUTC];
11231 tree const fn_fwrite = unlocked ? built_in_decls[BUILT_IN_FWRITE_UNLOCKED]
11232 : implicit_built_in_decls[BUILT_IN_FWRITE];
11234 /* If the return value is used, don't do the transformation. */
11235 if (!ignore)
11236 return NULL_TREE;
11238 /* Verify the arguments in the original call. */
11239 if (!validate_arg (arg0, POINTER_TYPE)
11240 || !validate_arg (arg1, POINTER_TYPE))
11241 return NULL_TREE;
11243 if (! len)
11244 len = c_strlen (arg0, 0);
11246 /* Get the length of the string passed to fputs. If the length
11247 can't be determined, punt. */
11248 if (!len
11249 || TREE_CODE (len) != INTEGER_CST)
11250 return NULL_TREE;
11252 switch (compare_tree_int (len, 1))
11254 case -1: /* length is 0, delete the call entirely . */
11255 return omit_one_operand (integer_type_node, integer_zero_node, arg1);;
11257 case 0: /* length is 1, call fputc. */
11259 const char *p = c_getstr (arg0);
11261 if (p != NULL)
11263 if (fn_fputc)
11264 return build_call_expr (fn_fputc, 2,
11265 build_int_cst (NULL_TREE, p[0]), arg1);
11266 else
11267 return NULL_TREE;
11270 /* FALLTHROUGH */
11271 case 1: /* length is greater than 1, call fwrite. */
11273 /* If optimizing for size keep fputs. */
11274 if (optimize_size)
11275 return NULL_TREE;
11276 /* New argument list transforming fputs(string, stream) to
11277 fwrite(string, 1, len, stream). */
11278 if (fn_fwrite)
11279 return build_call_expr (fn_fwrite, 4, arg0, size_one_node, len, arg1);
11280 else
11281 return NULL_TREE;
11283 default:
11284 gcc_unreachable ();
11286 return NULL_TREE;
11289 /* Fold the next_arg or va_start call EXP. Returns true if there was an error
11290 produced. False otherwise. This is done so that we don't output the error
11291 or warning twice or three times. */
11292 bool
11293 fold_builtin_next_arg (tree exp, bool va_start_p)
11295 tree fntype = TREE_TYPE (current_function_decl);
11296 int nargs = call_expr_nargs (exp);
11297 tree arg;
11299 if (TYPE_ARG_TYPES (fntype) == 0
11300 || (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
11301 == void_type_node))
11303 error ("%<va_start%> used in function with fixed args");
11304 return true;
11307 if (va_start_p)
11309 if (va_start_p && (nargs != 2))
11311 error ("wrong number of arguments to function %<va_start%>");
11312 return true;
11314 arg = CALL_EXPR_ARG (exp, 1);
11316 /* We use __builtin_va_start (ap, 0, 0) or __builtin_next_arg (0, 0)
11317 when we checked the arguments and if needed issued a warning. */
11318 else
11320 if (nargs == 0)
11322 /* Evidently an out of date version of <stdarg.h>; can't validate
11323 va_start's second argument, but can still work as intended. */
11324 warning (0, "%<__builtin_next_arg%> called without an argument");
11325 return true;
11327 else if (nargs > 1)
11329 error ("wrong number of arguments to function %<__builtin_next_arg%>");
11330 return true;
11332 arg = CALL_EXPR_ARG (exp, 0);
11335 /* We destructively modify the call to be __builtin_va_start (ap, 0)
11336 or __builtin_next_arg (0) the first time we see it, after checking
11337 the arguments and if needed issuing a warning. */
11338 if (!integer_zerop (arg))
11340 tree last_parm = tree_last (DECL_ARGUMENTS (current_function_decl));
11342 /* Strip off all nops for the sake of the comparison. This
11343 is not quite the same as STRIP_NOPS. It does more.
11344 We must also strip off INDIRECT_EXPR for C++ reference
11345 parameters. */
11346 while (TREE_CODE (arg) == NOP_EXPR
11347 || TREE_CODE (arg) == CONVERT_EXPR
11348 || TREE_CODE (arg) == NON_LVALUE_EXPR
11349 || TREE_CODE (arg) == INDIRECT_REF)
11350 arg = TREE_OPERAND (arg, 0);
11351 if (arg != last_parm)
11353 /* FIXME: Sometimes with the tree optimizers we can get the
11354 not the last argument even though the user used the last
11355 argument. We just warn and set the arg to be the last
11356 argument so that we will get wrong-code because of
11357 it. */
11358 warning (0, "second parameter of %<va_start%> not last named argument");
11360 /* We want to verify the second parameter just once before the tree
11361 optimizers are run and then avoid keeping it in the tree,
11362 as otherwise we could warn even for correct code like:
11363 void foo (int i, ...)
11364 { va_list ap; i++; va_start (ap, i); va_end (ap); } */
11365 if (va_start_p)
11366 CALL_EXPR_ARG (exp, 1) = integer_zero_node;
11367 else
11368 CALL_EXPR_ARG (exp, 0) = integer_zero_node;
11370 return false;
11374 /* Simplify a call to the sprintf builtin with arguments DEST, FMT, and ORIG.
11375 ORIG may be null if this is a 2-argument call. We don't attempt to
11376 simplify calls with more than 3 arguments.
11378 Return NULL_TREE if no simplification was possible, otherwise return the
11379 simplified form of the call as a tree. If IGNORED is true, it means that
11380 the caller does not use the returned value of the function. */
11382 static tree
11383 fold_builtin_sprintf (tree dest, tree fmt, tree orig, int ignored)
11385 tree call, retval;
11386 const char *fmt_str = NULL;
11388 /* Verify the required arguments in the original call. We deal with two
11389 types of sprintf() calls: 'sprintf (str, fmt)' and
11390 'sprintf (dest, "%s", orig)'. */
11391 if (!validate_arg (dest, POINTER_TYPE)
11392 || !validate_arg (fmt, POINTER_TYPE))
11393 return NULL_TREE;
11394 if (orig && !validate_arg (orig, POINTER_TYPE))
11395 return NULL_TREE;
11397 /* Check whether the format is a literal string constant. */
11398 fmt_str = c_getstr (fmt);
11399 if (fmt_str == NULL)
11400 return NULL_TREE;
11402 call = NULL_TREE;
11403 retval = NULL_TREE;
11405 if (!init_target_chars ())
11406 return NULL_TREE;
11408 /* If the format doesn't contain % args or %%, use strcpy. */
11409 if (strchr (fmt_str, target_percent) == NULL)
11411 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
11413 if (!fn)
11414 return NULL_TREE;
11416 /* Don't optimize sprintf (buf, "abc", ptr++). */
11417 if (orig)
11418 return NULL_TREE;
11420 /* Convert sprintf (str, fmt) into strcpy (str, fmt) when
11421 'format' is known to contain no % formats. */
11422 call = build_call_expr (fn, 2, dest, fmt);
11423 if (!ignored)
11424 retval = build_int_cst (NULL_TREE, strlen (fmt_str));
11427 /* If the format is "%s", use strcpy if the result isn't used. */
11428 else if (fmt_str && strcmp (fmt_str, target_percent_s) == 0)
11430 tree fn;
11431 fn = implicit_built_in_decls[BUILT_IN_STRCPY];
11433 if (!fn)
11434 return NULL_TREE;
11436 /* Don't crash on sprintf (str1, "%s"). */
11437 if (!orig)
11438 return NULL_TREE;
11440 /* Convert sprintf (str1, "%s", str2) into strcpy (str1, str2). */
11441 if (!ignored)
11443 retval = c_strlen (orig, 1);
11444 if (!retval || TREE_CODE (retval) != INTEGER_CST)
11445 return NULL_TREE;
11447 call = build_call_expr (fn, 2, dest, orig);
11450 if (call && retval)
11452 retval = fold_convert
11453 (TREE_TYPE (TREE_TYPE (implicit_built_in_decls[BUILT_IN_SPRINTF])),
11454 retval);
11455 return build2 (COMPOUND_EXPR, TREE_TYPE (retval), call, retval);
11457 else
11458 return call;
11461 /* Expand a call EXP to __builtin_object_size. */
11464 expand_builtin_object_size (tree exp)
11466 tree ost;
11467 int object_size_type;
11468 tree fndecl = get_callee_fndecl (exp);
11469 location_t locus = EXPR_LOCATION (exp);
11471 if (!validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
11473 error ("%Hfirst argument of %D must be a pointer, second integer constant",
11474 &locus, fndecl);
11475 expand_builtin_trap ();
11476 return const0_rtx;
11479 ost = CALL_EXPR_ARG (exp, 1);
11480 STRIP_NOPS (ost);
11482 if (TREE_CODE (ost) != INTEGER_CST
11483 || tree_int_cst_sgn (ost) < 0
11484 || compare_tree_int (ost, 3) > 0)
11486 error ("%Hlast argument of %D is not integer constant between 0 and 3",
11487 &locus, fndecl);
11488 expand_builtin_trap ();
11489 return const0_rtx;
11492 object_size_type = tree_low_cst (ost, 0);
11494 return object_size_type < 2 ? constm1_rtx : const0_rtx;
11497 /* Expand EXP, a call to the __mem{cpy,pcpy,move,set}_chk builtin.
11498 FCODE is the BUILT_IN_* to use.
11499 Return NULL_RTX if we failed; the caller should emit a normal call,
11500 otherwise try to get the result in TARGET, if convenient (and in
11501 mode MODE if that's convenient). */
11503 static rtx
11504 expand_builtin_memory_chk (tree exp, rtx target, enum machine_mode mode,
11505 enum built_in_function fcode)
11507 tree dest, src, len, size;
11509 if (!validate_arglist (exp,
11510 POINTER_TYPE,
11511 fcode == BUILT_IN_MEMSET_CHK
11512 ? INTEGER_TYPE : POINTER_TYPE,
11513 INTEGER_TYPE, INTEGER_TYPE, VOID_TYPE))
11514 return NULL_RTX;
11516 dest = CALL_EXPR_ARG (exp, 0);
11517 src = CALL_EXPR_ARG (exp, 1);
11518 len = CALL_EXPR_ARG (exp, 2);
11519 size = CALL_EXPR_ARG (exp, 3);
11521 if (! host_integerp (size, 1))
11522 return NULL_RTX;
11524 if (host_integerp (len, 1) || integer_all_onesp (size))
11526 tree fn;
11528 if (! integer_all_onesp (size) && tree_int_cst_lt (size, len))
11530 location_t locus = EXPR_LOCATION (exp);
11531 warning (0, "%Hcall to %D will always overflow destination buffer",
11532 &locus, get_callee_fndecl (exp));
11533 return NULL_RTX;
11536 fn = NULL_TREE;
11537 /* If __builtin_mem{cpy,pcpy,move,set}_chk is used, assume
11538 mem{cpy,pcpy,move,set} is available. */
11539 switch (fcode)
11541 case BUILT_IN_MEMCPY_CHK:
11542 fn = built_in_decls[BUILT_IN_MEMCPY];
11543 break;
11544 case BUILT_IN_MEMPCPY_CHK:
11545 fn = built_in_decls[BUILT_IN_MEMPCPY];
11546 break;
11547 case BUILT_IN_MEMMOVE_CHK:
11548 fn = built_in_decls[BUILT_IN_MEMMOVE];
11549 break;
11550 case BUILT_IN_MEMSET_CHK:
11551 fn = built_in_decls[BUILT_IN_MEMSET];
11552 break;
11553 default:
11554 break;
11557 if (! fn)
11558 return NULL_RTX;
11560 fn = build_call_expr (fn, 3, dest, src, len);
11561 STRIP_TYPE_NOPS (fn);
11562 while (TREE_CODE (fn) == COMPOUND_EXPR)
11564 expand_expr (TREE_OPERAND (fn, 0), const0_rtx, VOIDmode,
11565 EXPAND_NORMAL);
11566 fn = TREE_OPERAND (fn, 1);
11568 if (TREE_CODE (fn) == CALL_EXPR)
11569 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
11570 return expand_expr (fn, target, mode, EXPAND_NORMAL);
11572 else if (fcode == BUILT_IN_MEMSET_CHK)
11573 return NULL_RTX;
11574 else
11576 unsigned int dest_align
11577 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
11579 /* If DEST is not a pointer type, call the normal function. */
11580 if (dest_align == 0)
11581 return NULL_RTX;
11583 /* If SRC and DEST are the same (and not volatile), do nothing. */
11584 if (operand_equal_p (src, dest, 0))
11586 tree expr;
11588 if (fcode != BUILT_IN_MEMPCPY_CHK)
11590 /* Evaluate and ignore LEN in case it has side-effects. */
11591 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
11592 return expand_expr (dest, target, mode, EXPAND_NORMAL);
11595 expr = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
11596 return expand_expr (expr, target, mode, EXPAND_NORMAL);
11599 /* __memmove_chk special case. */
11600 if (fcode == BUILT_IN_MEMMOVE_CHK)
11602 unsigned int src_align
11603 = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
11605 if (src_align == 0)
11606 return NULL_RTX;
11608 /* If src is categorized for a readonly section we can use
11609 normal __memcpy_chk. */
11610 if (readonly_data_expr (src))
11612 tree fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
11613 if (!fn)
11614 return NULL_RTX;
11615 fn = build_call_expr (fn, 4, dest, src, len, size);
11616 STRIP_TYPE_NOPS (fn);
11617 while (TREE_CODE (fn) == COMPOUND_EXPR)
11619 expand_expr (TREE_OPERAND (fn, 0), const0_rtx, VOIDmode,
11620 EXPAND_NORMAL);
11621 fn = TREE_OPERAND (fn, 1);
11623 if (TREE_CODE (fn) == CALL_EXPR)
11624 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
11625 return expand_expr (fn, target, mode, EXPAND_NORMAL);
11628 return NULL_RTX;
11632 /* Emit warning if a buffer overflow is detected at compile time. */
11634 static void
11635 maybe_emit_chk_warning (tree exp, enum built_in_function fcode)
11637 int is_strlen = 0;
11638 tree len, size;
11639 location_t locus;
11641 switch (fcode)
11643 case BUILT_IN_STRCPY_CHK:
11644 case BUILT_IN_STPCPY_CHK:
11645 /* For __strcat_chk the warning will be emitted only if overflowing
11646 by at least strlen (dest) + 1 bytes. */
11647 case BUILT_IN_STRCAT_CHK:
11648 len = CALL_EXPR_ARG (exp, 1);
11649 size = CALL_EXPR_ARG (exp, 2);
11650 is_strlen = 1;
11651 break;
11652 case BUILT_IN_STRNCAT_CHK:
11653 case BUILT_IN_STRNCPY_CHK:
11654 len = CALL_EXPR_ARG (exp, 2);
11655 size = CALL_EXPR_ARG (exp, 3);
11656 break;
11657 case BUILT_IN_SNPRINTF_CHK:
11658 case BUILT_IN_VSNPRINTF_CHK:
11659 len = CALL_EXPR_ARG (exp, 1);
11660 size = CALL_EXPR_ARG (exp, 3);
11661 break;
11662 default:
11663 gcc_unreachable ();
11666 if (!len || !size)
11667 return;
11669 if (! host_integerp (size, 1) || integer_all_onesp (size))
11670 return;
11672 if (is_strlen)
11674 len = c_strlen (len, 1);
11675 if (! len || ! host_integerp (len, 1) || tree_int_cst_lt (len, size))
11676 return;
11678 else if (fcode == BUILT_IN_STRNCAT_CHK)
11680 tree src = CALL_EXPR_ARG (exp, 1);
11681 if (! src || ! host_integerp (len, 1) || tree_int_cst_lt (len, size))
11682 return;
11683 src = c_strlen (src, 1);
11684 if (! src || ! host_integerp (src, 1))
11686 locus = EXPR_LOCATION (exp);
11687 warning (0, "%Hcall to %D might overflow destination buffer",
11688 &locus, get_callee_fndecl (exp));
11689 return;
11691 else if (tree_int_cst_lt (src, size))
11692 return;
11694 else if (! host_integerp (len, 1) || ! tree_int_cst_lt (size, len))
11695 return;
11697 locus = EXPR_LOCATION (exp);
11698 warning (0, "%Hcall to %D will always overflow destination buffer",
11699 &locus, get_callee_fndecl (exp));
11702 /* Emit warning if a buffer overflow is detected at compile time
11703 in __sprintf_chk/__vsprintf_chk calls. */
11705 static void
11706 maybe_emit_sprintf_chk_warning (tree exp, enum built_in_function fcode)
11708 tree dest, size, len, fmt, flag;
11709 const char *fmt_str;
11710 int nargs = call_expr_nargs (exp);
11712 /* Verify the required arguments in the original call. */
11714 if (nargs < 4)
11715 return;
11716 dest = CALL_EXPR_ARG (exp, 0);
11717 flag = CALL_EXPR_ARG (exp, 1);
11718 size = CALL_EXPR_ARG (exp, 2);
11719 fmt = CALL_EXPR_ARG (exp, 3);
11721 if (! host_integerp (size, 1) || integer_all_onesp (size))
11722 return;
11724 /* Check whether the format is a literal string constant. */
11725 fmt_str = c_getstr (fmt);
11726 if (fmt_str == NULL)
11727 return;
11729 if (!init_target_chars ())
11730 return;
11732 /* If the format doesn't contain % args or %%, we know its size. */
11733 if (strchr (fmt_str, target_percent) == 0)
11734 len = build_int_cstu (size_type_node, strlen (fmt_str));
11735 /* If the format is "%s" and first ... argument is a string literal,
11736 we know it too. */
11737 else if (fcode == BUILT_IN_SPRINTF_CHK
11738 && strcmp (fmt_str, target_percent_s) == 0)
11740 tree arg;
11742 if (nargs < 5)
11743 return;
11744 arg = CALL_EXPR_ARG (exp, 4);
11745 if (! POINTER_TYPE_P (TREE_TYPE (arg)))
11746 return;
11748 len = c_strlen (arg, 1);
11749 if (!len || ! host_integerp (len, 1))
11750 return;
11752 else
11753 return;
11755 if (! tree_int_cst_lt (len, size))
11757 location_t locus = EXPR_LOCATION (exp);
11758 warning (0, "%Hcall to %D will always overflow destination buffer",
11759 &locus, get_callee_fndecl (exp));
11763 /* Fold a call to __builtin_object_size with arguments PTR and OST,
11764 if possible. */
11766 tree
11767 fold_builtin_object_size (tree ptr, tree ost)
11769 tree ret = NULL_TREE;
11770 int object_size_type;
11772 if (!validate_arg (ptr, POINTER_TYPE)
11773 || !validate_arg (ost, INTEGER_TYPE))
11774 return NULL_TREE;
11776 STRIP_NOPS (ost);
11778 if (TREE_CODE (ost) != INTEGER_CST
11779 || tree_int_cst_sgn (ost) < 0
11780 || compare_tree_int (ost, 3) > 0)
11781 return NULL_TREE;
11783 object_size_type = tree_low_cst (ost, 0);
11785 /* __builtin_object_size doesn't evaluate side-effects in its arguments;
11786 if there are any side-effects, it returns (size_t) -1 for types 0 and 1
11787 and (size_t) 0 for types 2 and 3. */
11788 if (TREE_SIDE_EFFECTS (ptr))
11789 return build_int_cst_type (size_type_node, object_size_type < 2 ? -1 : 0);
11791 if (TREE_CODE (ptr) == ADDR_EXPR)
11792 ret = build_int_cstu (size_type_node,
11793 compute_builtin_object_size (ptr, object_size_type));
11795 else if (TREE_CODE (ptr) == SSA_NAME)
11797 unsigned HOST_WIDE_INT bytes;
11799 /* If object size is not known yet, delay folding until
11800 later. Maybe subsequent passes will help determining
11801 it. */
11802 bytes = compute_builtin_object_size (ptr, object_size_type);
11803 if (bytes != (unsigned HOST_WIDE_INT) (object_size_type < 2
11804 ? -1 : 0))
11805 ret = build_int_cstu (size_type_node, bytes);
11808 if (ret)
11810 unsigned HOST_WIDE_INT low = TREE_INT_CST_LOW (ret);
11811 HOST_WIDE_INT high = TREE_INT_CST_HIGH (ret);
11812 if (fit_double_type (low, high, &low, &high, TREE_TYPE (ret)))
11813 ret = NULL_TREE;
11816 return ret;
11819 /* Fold a call to the __mem{cpy,pcpy,move,set}_chk builtin.
11820 DEST, SRC, LEN, and SIZE are the arguments to the call.
11821 IGNORE is true, if return value can be ignored. FCODE is the BUILT_IN_*
11822 code of the builtin. If MAXLEN is not NULL, it is maximum length
11823 passed as third argument. */
11825 tree
11826 fold_builtin_memory_chk (tree fndecl,
11827 tree dest, tree src, tree len, tree size,
11828 tree maxlen, bool ignore,
11829 enum built_in_function fcode)
11831 tree fn;
11833 if (!validate_arg (dest, POINTER_TYPE)
11834 || !validate_arg (src,
11835 (fcode == BUILT_IN_MEMSET_CHK
11836 ? INTEGER_TYPE : POINTER_TYPE))
11837 || !validate_arg (len, INTEGER_TYPE)
11838 || !validate_arg (size, INTEGER_TYPE))
11839 return NULL_TREE;
11841 /* If SRC and DEST are the same (and not volatile), return DEST
11842 (resp. DEST+LEN for __mempcpy_chk). */
11843 if (fcode != BUILT_IN_MEMSET_CHK && operand_equal_p (src, dest, 0))
11845 if (fcode != BUILT_IN_MEMPCPY_CHK)
11846 return omit_one_operand (TREE_TYPE (TREE_TYPE (fndecl)), dest, len);
11847 else
11849 tree temp = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
11850 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), temp);
11854 if (! host_integerp (size, 1))
11855 return NULL_TREE;
11857 if (! integer_all_onesp (size))
11859 if (! host_integerp (len, 1))
11861 /* If LEN is not constant, try MAXLEN too.
11862 For MAXLEN only allow optimizing into non-_ocs function
11863 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
11864 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
11866 if (fcode == BUILT_IN_MEMPCPY_CHK && ignore)
11868 /* (void) __mempcpy_chk () can be optimized into
11869 (void) __memcpy_chk (). */
11870 fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
11871 if (!fn)
11872 return NULL_TREE;
11874 return build_call_expr (fn, 4, dest, src, len, size);
11876 return NULL_TREE;
11879 else
11880 maxlen = len;
11882 if (tree_int_cst_lt (size, maxlen))
11883 return NULL_TREE;
11886 fn = NULL_TREE;
11887 /* If __builtin_mem{cpy,pcpy,move,set}_chk is used, assume
11888 mem{cpy,pcpy,move,set} is available. */
11889 switch (fcode)
11891 case BUILT_IN_MEMCPY_CHK:
11892 fn = built_in_decls[BUILT_IN_MEMCPY];
11893 break;
11894 case BUILT_IN_MEMPCPY_CHK:
11895 fn = built_in_decls[BUILT_IN_MEMPCPY];
11896 break;
11897 case BUILT_IN_MEMMOVE_CHK:
11898 fn = built_in_decls[BUILT_IN_MEMMOVE];
11899 break;
11900 case BUILT_IN_MEMSET_CHK:
11901 fn = built_in_decls[BUILT_IN_MEMSET];
11902 break;
11903 default:
11904 break;
11907 if (!fn)
11908 return NULL_TREE;
11910 return build_call_expr (fn, 3, dest, src, len);
11913 /* Fold a call to the __st[rp]cpy_chk builtin.
11914 DEST, SRC, and SIZE are the arguments to the call.
11915 IGNORE is true if return value can be ignored. FCODE is the BUILT_IN_*
11916 code of the builtin. If MAXLEN is not NULL, it is maximum length of
11917 strings passed as second argument. */
11919 tree
11920 fold_builtin_stxcpy_chk (tree fndecl, tree dest, tree src, tree size,
11921 tree maxlen, bool ignore,
11922 enum built_in_function fcode)
11924 tree len, fn;
11926 if (!validate_arg (dest, POINTER_TYPE)
11927 || !validate_arg (src, POINTER_TYPE)
11928 || !validate_arg (size, INTEGER_TYPE))
11929 return NULL_TREE;
11931 /* If SRC and DEST are the same (and not volatile), return DEST. */
11932 if (fcode == BUILT_IN_STRCPY_CHK && operand_equal_p (src, dest, 0))
11933 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), dest);
11935 if (! host_integerp (size, 1))
11936 return NULL_TREE;
11938 if (! integer_all_onesp (size))
11940 len = c_strlen (src, 1);
11941 if (! len || ! host_integerp (len, 1))
11943 /* If LEN is not constant, try MAXLEN too.
11944 For MAXLEN only allow optimizing into non-_ocs function
11945 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
11946 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
11948 if (fcode == BUILT_IN_STPCPY_CHK)
11950 if (! ignore)
11951 return NULL_TREE;
11953 /* If return value of __stpcpy_chk is ignored,
11954 optimize into __strcpy_chk. */
11955 fn = built_in_decls[BUILT_IN_STRCPY_CHK];
11956 if (!fn)
11957 return NULL_TREE;
11959 return build_call_expr (fn, 3, dest, src, size);
11962 if (! len || TREE_SIDE_EFFECTS (len))
11963 return NULL_TREE;
11965 /* If c_strlen returned something, but not a constant,
11966 transform __strcpy_chk into __memcpy_chk. */
11967 fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
11968 if (!fn)
11969 return NULL_TREE;
11971 len = size_binop (PLUS_EXPR, len, ssize_int (1));
11972 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)),
11973 build_call_expr (fn, 4,
11974 dest, src, len, size));
11977 else
11978 maxlen = len;
11980 if (! tree_int_cst_lt (maxlen, size))
11981 return NULL_TREE;
11984 /* If __builtin_st{r,p}cpy_chk is used, assume st{r,p}cpy is available. */
11985 fn = built_in_decls[fcode == BUILT_IN_STPCPY_CHK
11986 ? BUILT_IN_STPCPY : BUILT_IN_STRCPY];
11987 if (!fn)
11988 return NULL_TREE;
11990 return build_call_expr (fn, 2, dest, src);
11993 /* Fold a call to the __strncpy_chk builtin. DEST, SRC, LEN, and SIZE
11994 are the arguments to the call. If MAXLEN is not NULL, it is maximum
11995 length passed as third argument. */
11997 tree
11998 fold_builtin_strncpy_chk (tree dest, tree src, tree len, tree size,
11999 tree maxlen)
12001 tree fn;
12003 if (!validate_arg (dest, POINTER_TYPE)
12004 || !validate_arg (src, POINTER_TYPE)
12005 || !validate_arg (len, INTEGER_TYPE)
12006 || !validate_arg (size, INTEGER_TYPE))
12007 return NULL_TREE;
12009 if (! host_integerp (size, 1))
12010 return NULL_TREE;
12012 if (! integer_all_onesp (size))
12014 if (! host_integerp (len, 1))
12016 /* If LEN is not constant, try MAXLEN too.
12017 For MAXLEN only allow optimizing into non-_ocs function
12018 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12019 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12020 return NULL_TREE;
12022 else
12023 maxlen = len;
12025 if (tree_int_cst_lt (size, maxlen))
12026 return NULL_TREE;
12029 /* If __builtin_strncpy_chk is used, assume strncpy is available. */
12030 fn = built_in_decls[BUILT_IN_STRNCPY];
12031 if (!fn)
12032 return NULL_TREE;
12034 return build_call_expr (fn, 3, dest, src, len);
12037 /* Fold a call to the __strcat_chk builtin FNDECL. DEST, SRC, and SIZE
12038 are the arguments to the call. */
12040 static tree
12041 fold_builtin_strcat_chk (tree fndecl, tree dest, tree src, tree size)
12043 tree fn;
12044 const char *p;
12046 if (!validate_arg (dest, POINTER_TYPE)
12047 || !validate_arg (src, POINTER_TYPE)
12048 || !validate_arg (size, INTEGER_TYPE))
12049 return NULL_TREE;
12051 p = c_getstr (src);
12052 /* If the SRC parameter is "", return DEST. */
12053 if (p && *p == '\0')
12054 return omit_one_operand (TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
12056 if (! host_integerp (size, 1) || ! integer_all_onesp (size))
12057 return NULL_TREE;
12059 /* If __builtin_strcat_chk is used, assume strcat is available. */
12060 fn = built_in_decls[BUILT_IN_STRCAT];
12061 if (!fn)
12062 return NULL_TREE;
12064 return build_call_expr (fn, 2, dest, src);
12067 /* Fold a call to the __strncat_chk builtin with arguments DEST, SRC,
12068 LEN, and SIZE. */
12070 static tree
12071 fold_builtin_strncat_chk (tree fndecl,
12072 tree dest, tree src, tree len, tree size)
12074 tree fn;
12075 const char *p;
12077 if (!validate_arg (dest, POINTER_TYPE)
12078 || !validate_arg (src, POINTER_TYPE)
12079 || !validate_arg (size, INTEGER_TYPE)
12080 || !validate_arg (size, INTEGER_TYPE))
12081 return NULL_TREE;
12083 p = c_getstr (src);
12084 /* If the SRC parameter is "" or if LEN is 0, return DEST. */
12085 if (p && *p == '\0')
12086 return omit_one_operand (TREE_TYPE (TREE_TYPE (fndecl)), dest, len);
12087 else if (integer_zerop (len))
12088 return omit_one_operand (TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
12090 if (! host_integerp (size, 1))
12091 return NULL_TREE;
12093 if (! integer_all_onesp (size))
12095 tree src_len = c_strlen (src, 1);
12096 if (src_len
12097 && host_integerp (src_len, 1)
12098 && host_integerp (len, 1)
12099 && ! tree_int_cst_lt (len, src_len))
12101 /* If LEN >= strlen (SRC), optimize into __strcat_chk. */
12102 fn = built_in_decls[BUILT_IN_STRCAT_CHK];
12103 if (!fn)
12104 return NULL_TREE;
12106 return build_call_expr (fn, 3, dest, src, size);
12108 return NULL_TREE;
12111 /* If __builtin_strncat_chk is used, assume strncat is available. */
12112 fn = built_in_decls[BUILT_IN_STRNCAT];
12113 if (!fn)
12114 return NULL_TREE;
12116 return build_call_expr (fn, 3, dest, src, len);
12119 /* Fold a call EXP to __{,v}sprintf_chk. Return NULL_TREE if
12120 a normal call should be emitted rather than expanding the function
12121 inline. FCODE is either BUILT_IN_SPRINTF_CHK or BUILT_IN_VSPRINTF_CHK. */
12123 static tree
12124 fold_builtin_sprintf_chk (tree exp, enum built_in_function fcode)
12126 tree dest, size, len, fn, fmt, flag;
12127 const char *fmt_str;
12128 int nargs = call_expr_nargs (exp);
12130 /* Verify the required arguments in the original call. */
12131 if (nargs < 4)
12132 return NULL_TREE;
12133 dest = CALL_EXPR_ARG (exp, 0);
12134 if (!validate_arg (dest, POINTER_TYPE))
12135 return NULL_TREE;
12136 flag = CALL_EXPR_ARG (exp, 1);
12137 if (!validate_arg (flag, INTEGER_TYPE))
12138 return NULL_TREE;
12139 size = CALL_EXPR_ARG (exp, 2);
12140 if (!validate_arg (size, INTEGER_TYPE))
12141 return NULL_TREE;
12142 fmt = CALL_EXPR_ARG (exp, 3);
12143 if (!validate_arg (fmt, POINTER_TYPE))
12144 return NULL_TREE;
12146 if (! host_integerp (size, 1))
12147 return NULL_TREE;
12149 len = NULL_TREE;
12151 if (!init_target_chars ())
12152 return NULL_TREE;
12154 /* Check whether the format is a literal string constant. */
12155 fmt_str = c_getstr (fmt);
12156 if (fmt_str != NULL)
12158 /* If the format doesn't contain % args or %%, we know the size. */
12159 if (strchr (fmt_str, target_percent) == 0)
12161 if (fcode != BUILT_IN_SPRINTF_CHK || nargs == 4)
12162 len = build_int_cstu (size_type_node, strlen (fmt_str));
12164 /* If the format is "%s" and first ... argument is a string literal,
12165 we know the size too. */
12166 else if (fcode == BUILT_IN_SPRINTF_CHK
12167 && strcmp (fmt_str, target_percent_s) == 0)
12169 tree arg;
12171 if (nargs == 5)
12173 arg = CALL_EXPR_ARG (exp, 4);
12174 if (validate_arg (arg, POINTER_TYPE))
12176 len = c_strlen (arg, 1);
12177 if (! len || ! host_integerp (len, 1))
12178 len = NULL_TREE;
12184 if (! integer_all_onesp (size))
12186 if (! len || ! tree_int_cst_lt (len, size))
12187 return NULL_TREE;
12190 /* Only convert __{,v}sprintf_chk to {,v}sprintf if flag is 0
12191 or if format doesn't contain % chars or is "%s". */
12192 if (! integer_zerop (flag))
12194 if (fmt_str == NULL)
12195 return NULL_TREE;
12196 if (strchr (fmt_str, target_percent) != NULL
12197 && strcmp (fmt_str, target_percent_s))
12198 return NULL_TREE;
12201 /* If __builtin_{,v}sprintf_chk is used, assume {,v}sprintf is available. */
12202 fn = built_in_decls[fcode == BUILT_IN_VSPRINTF_CHK
12203 ? BUILT_IN_VSPRINTF : BUILT_IN_SPRINTF];
12204 if (!fn)
12205 return NULL_TREE;
12207 return rewrite_call_expr (exp, 4, fn, 2, dest, fmt);
12210 /* Fold a call EXP to {,v}snprintf. Return NULL_TREE if
12211 a normal call should be emitted rather than expanding the function
12212 inline. FCODE is either BUILT_IN_SNPRINTF_CHK or
12213 BUILT_IN_VSNPRINTF_CHK. If MAXLEN is not NULL, it is maximum length
12214 passed as second argument. */
12216 tree
12217 fold_builtin_snprintf_chk (tree exp, tree maxlen,
12218 enum built_in_function fcode)
12220 tree dest, size, len, fn, fmt, flag;
12221 const char *fmt_str;
12223 /* Verify the required arguments in the original call. */
12224 if (call_expr_nargs (exp) < 5)
12225 return NULL_TREE;
12226 dest = CALL_EXPR_ARG (exp, 0);
12227 if (!validate_arg (dest, POINTER_TYPE))
12228 return NULL_TREE;
12229 len = CALL_EXPR_ARG (exp, 1);
12230 if (!validate_arg (len, INTEGER_TYPE))
12231 return NULL_TREE;
12232 flag = CALL_EXPR_ARG (exp, 2);
12233 if (!validate_arg (flag, INTEGER_TYPE))
12234 return NULL_TREE;
12235 size = CALL_EXPR_ARG (exp, 3);
12236 if (!validate_arg (size, INTEGER_TYPE))
12237 return NULL_TREE;
12238 fmt = CALL_EXPR_ARG (exp, 4);
12239 if (!validate_arg (fmt, POINTER_TYPE))
12240 return NULL_TREE;
12242 if (! host_integerp (size, 1))
12243 return NULL_TREE;
12245 if (! integer_all_onesp (size))
12247 if (! host_integerp (len, 1))
12249 /* If LEN is not constant, try MAXLEN too.
12250 For MAXLEN only allow optimizing into non-_ocs function
12251 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12252 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12253 return NULL_TREE;
12255 else
12256 maxlen = len;
12258 if (tree_int_cst_lt (size, maxlen))
12259 return NULL_TREE;
12262 if (!init_target_chars ())
12263 return NULL_TREE;
12265 /* Only convert __{,v}snprintf_chk to {,v}snprintf if flag is 0
12266 or if format doesn't contain % chars or is "%s". */
12267 if (! integer_zerop (flag))
12269 fmt_str = c_getstr (fmt);
12270 if (fmt_str == NULL)
12271 return NULL_TREE;
12272 if (strchr (fmt_str, target_percent) != NULL
12273 && strcmp (fmt_str, target_percent_s))
12274 return NULL_TREE;
12277 /* If __builtin_{,v}snprintf_chk is used, assume {,v}snprintf is
12278 available. */
12279 fn = built_in_decls[fcode == BUILT_IN_VSNPRINTF_CHK
12280 ? BUILT_IN_VSNPRINTF : BUILT_IN_SNPRINTF];
12281 if (!fn)
12282 return NULL_TREE;
12284 return rewrite_call_expr (exp, 5, fn, 3, dest, len, fmt);
12287 /* Fold a call to the {,v}printf{,_unlocked} and __{,v}printf_chk builtins.
12288 FMT and ARG are the arguments to the call; we don't fold cases with
12289 more than 2 arguments, and ARG may be null if this is a 1-argument case.
12291 Return NULL_TREE if no simplification was possible, otherwise return the
12292 simplified form of the call as a tree. FCODE is the BUILT_IN_*
12293 code of the function to be simplified. */
12295 static tree
12296 fold_builtin_printf (tree fndecl, tree fmt, tree arg, bool ignore,
12297 enum built_in_function fcode)
12299 tree fn_putchar, fn_puts, newarg, call = NULL_TREE;
12300 const char *fmt_str = NULL;
12302 /* If the return value is used, don't do the transformation. */
12303 if (! ignore)
12304 return NULL_TREE;
12306 /* Verify the required arguments in the original call. */
12307 if (!validate_arg (fmt, POINTER_TYPE))
12308 return NULL_TREE;
12310 /* Check whether the format is a literal string constant. */
12311 fmt_str = c_getstr (fmt);
12312 if (fmt_str == NULL)
12313 return NULL_TREE;
12315 if (fcode == BUILT_IN_PRINTF_UNLOCKED)
12317 /* If we're using an unlocked function, assume the other
12318 unlocked functions exist explicitly. */
12319 fn_putchar = built_in_decls[BUILT_IN_PUTCHAR_UNLOCKED];
12320 fn_puts = built_in_decls[BUILT_IN_PUTS_UNLOCKED];
12322 else
12324 fn_putchar = implicit_built_in_decls[BUILT_IN_PUTCHAR];
12325 fn_puts = implicit_built_in_decls[BUILT_IN_PUTS];
12328 if (!init_target_chars ())
12329 return NULL_TREE;
12331 if (strcmp (fmt_str, target_percent_s) == 0
12332 || strchr (fmt_str, target_percent) == NULL)
12334 const char *str;
12336 if (strcmp (fmt_str, target_percent_s) == 0)
12338 if (fcode == BUILT_IN_VPRINTF || fcode == BUILT_IN_VPRINTF_CHK)
12339 return NULL_TREE;
12341 if (!arg || !validate_arg (arg, POINTER_TYPE))
12342 return NULL_TREE;
12344 str = c_getstr (arg);
12345 if (str == NULL)
12346 return NULL_TREE;
12348 else
12350 /* The format specifier doesn't contain any '%' characters. */
12351 if (fcode != BUILT_IN_VPRINTF && fcode != BUILT_IN_VPRINTF_CHK
12352 && arg)
12353 return NULL_TREE;
12354 str = fmt_str;
12357 /* If the string was "", printf does nothing. */
12358 if (str[0] == '\0')
12359 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), 0);
12361 /* If the string has length of 1, call putchar. */
12362 if (str[1] == '\0')
12364 /* Given printf("c"), (where c is any one character,)
12365 convert "c"[0] to an int and pass that to the replacement
12366 function. */
12367 newarg = build_int_cst (NULL_TREE, str[0]);
12368 if (fn_putchar)
12369 call = build_call_expr (fn_putchar, 1, newarg);
12371 else
12373 /* If the string was "string\n", call puts("string"). */
12374 size_t len = strlen (str);
12375 if ((unsigned char)str[len - 1] == target_newline)
12377 /* Create a NUL-terminated string that's one char shorter
12378 than the original, stripping off the trailing '\n'. */
12379 char *newstr = alloca (len);
12380 memcpy (newstr, str, len - 1);
12381 newstr[len - 1] = 0;
12383 newarg = build_string_literal (len, newstr);
12384 if (fn_puts)
12385 call = build_call_expr (fn_puts, 1, newarg);
12387 else
12388 /* We'd like to arrange to call fputs(string,stdout) here,
12389 but we need stdout and don't have a way to get it yet. */
12390 return NULL_TREE;
12394 /* The other optimizations can be done only on the non-va_list variants. */
12395 else if (fcode == BUILT_IN_VPRINTF || fcode == BUILT_IN_VPRINTF_CHK)
12396 return NULL_TREE;
12398 /* If the format specifier was "%s\n", call __builtin_puts(arg). */
12399 else if (strcmp (fmt_str, target_percent_s_newline) == 0)
12401 if (!arg || !validate_arg (arg, POINTER_TYPE))
12402 return NULL_TREE;
12403 if (fn_puts)
12404 call = build_call_expr (fn_puts, 1, arg);
12407 /* If the format specifier was "%c", call __builtin_putchar(arg). */
12408 else if (strcmp (fmt_str, target_percent_c) == 0)
12410 if (!arg || !validate_arg (arg, INTEGER_TYPE))
12411 return NULL_TREE;
12412 if (fn_putchar)
12413 call = build_call_expr (fn_putchar, 1, arg);
12416 if (!call)
12417 return NULL_TREE;
12419 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), call);
12422 /* Fold a call to the {,v}fprintf{,_unlocked} and __{,v}printf_chk builtins.
12423 FP, FMT, and ARG are the arguments to the call. We don't fold calls with
12424 more than 3 arguments, and ARG may be null in the 2-argument case.
12426 Return NULL_TREE if no simplification was possible, otherwise return the
12427 simplified form of the call as a tree. FCODE is the BUILT_IN_*
12428 code of the function to be simplified. */
12430 static tree
12431 fold_builtin_fprintf (tree fndecl, tree fp, tree fmt, tree arg, bool ignore,
12432 enum built_in_function fcode)
12434 tree fn_fputc, fn_fputs, call = NULL_TREE;
12435 const char *fmt_str = NULL;
12437 /* If the return value is used, don't do the transformation. */
12438 if (! ignore)
12439 return NULL_TREE;
12441 /* Verify the required arguments in the original call. */
12442 if (!validate_arg (fp, POINTER_TYPE))
12443 return NULL_TREE;
12444 if (!validate_arg (fmt, POINTER_TYPE))
12445 return NULL_TREE;
12447 /* Check whether the format is a literal string constant. */
12448 fmt_str = c_getstr (fmt);
12449 if (fmt_str == NULL)
12450 return NULL_TREE;
12452 if (fcode == BUILT_IN_FPRINTF_UNLOCKED)
12454 /* If we're using an unlocked function, assume the other
12455 unlocked functions exist explicitly. */
12456 fn_fputc = built_in_decls[BUILT_IN_FPUTC_UNLOCKED];
12457 fn_fputs = built_in_decls[BUILT_IN_FPUTS_UNLOCKED];
12459 else
12461 fn_fputc = implicit_built_in_decls[BUILT_IN_FPUTC];
12462 fn_fputs = implicit_built_in_decls[BUILT_IN_FPUTS];
12465 if (!init_target_chars ())
12466 return NULL_TREE;
12468 /* If the format doesn't contain % args or %%, use strcpy. */
12469 if (strchr (fmt_str, target_percent) == NULL)
12471 if (fcode != BUILT_IN_VFPRINTF && fcode != BUILT_IN_VFPRINTF_CHK
12472 && arg)
12473 return NULL_TREE;
12475 /* If the format specifier was "", fprintf does nothing. */
12476 if (fmt_str[0] == '\0')
12478 /* If FP has side-effects, just wait until gimplification is
12479 done. */
12480 if (TREE_SIDE_EFFECTS (fp))
12481 return NULL_TREE;
12483 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), 0);
12486 /* When "string" doesn't contain %, replace all cases of
12487 fprintf (fp, string) with fputs (string, fp). The fputs
12488 builtin will take care of special cases like length == 1. */
12489 if (fn_fputs)
12490 call = build_call_expr (fn_fputs, 2, fmt, fp);
12493 /* The other optimizations can be done only on the non-va_list variants. */
12494 else if (fcode == BUILT_IN_VFPRINTF || fcode == BUILT_IN_VFPRINTF_CHK)
12495 return NULL_TREE;
12497 /* If the format specifier was "%s", call __builtin_fputs (arg, fp). */
12498 else if (strcmp (fmt_str, target_percent_s) == 0)
12500 if (!arg || !validate_arg (arg, POINTER_TYPE))
12501 return NULL_TREE;
12502 if (fn_fputs)
12503 call = build_call_expr (fn_fputs, 2, arg, fp);
12506 /* If the format specifier was "%c", call __builtin_fputc (arg, fp). */
12507 else if (strcmp (fmt_str, target_percent_c) == 0)
12509 if (!arg || !validate_arg (arg, INTEGER_TYPE))
12510 return NULL_TREE;
12511 if (fn_fputc)
12512 call = build_call_expr (fn_fputc, 2, arg, fp);
12515 if (!call)
12516 return NULL_TREE;
12517 return fold_convert (TREE_TYPE (TREE_TYPE (fndecl)), call);
12520 /* Initialize format string characters in the target charset. */
12522 static bool
12523 init_target_chars (void)
12525 static bool init;
12526 if (!init)
12528 target_newline = lang_hooks.to_target_charset ('\n');
12529 target_percent = lang_hooks.to_target_charset ('%');
12530 target_c = lang_hooks.to_target_charset ('c');
12531 target_s = lang_hooks.to_target_charset ('s');
12532 if (target_newline == 0 || target_percent == 0 || target_c == 0
12533 || target_s == 0)
12534 return false;
12536 target_percent_c[0] = target_percent;
12537 target_percent_c[1] = target_c;
12538 target_percent_c[2] = '\0';
12540 target_percent_s[0] = target_percent;
12541 target_percent_s[1] = target_s;
12542 target_percent_s[2] = '\0';
12544 target_percent_s_newline[0] = target_percent;
12545 target_percent_s_newline[1] = target_s;
12546 target_percent_s_newline[2] = target_newline;
12547 target_percent_s_newline[3] = '\0';
12549 init = true;
12551 return true;
12554 /* Helper function for do_mpfr_arg*(). Ensure M is a normal number
12555 and no overflow/underflow occurred. INEXACT is true if M was not
12556 exactly calculated. TYPE is the tree type for the result. This
12557 function assumes that you cleared the MPFR flags and then
12558 calculated M to see if anything subsequently set a flag prior to
12559 entering this function. Return NULL_TREE if any checks fail. */
12561 static tree
12562 do_mpfr_ckconv (mpfr_srcptr m, tree type, int inexact)
12564 /* Proceed iff we get a normal number, i.e. not NaN or Inf and no
12565 overflow/underflow occurred. If -frounding-math, proceed iff the
12566 result of calling FUNC was exact. */
12567 if (mpfr_number_p (m) && !mpfr_overflow_p () && !mpfr_underflow_p ()
12568 && (!flag_rounding_math || !inexact))
12570 REAL_VALUE_TYPE rr;
12572 real_from_mpfr (&rr, m, type, GMP_RNDN);
12573 /* Proceed iff GCC's REAL_VALUE_TYPE can hold the MPFR value,
12574 check for overflow/underflow. If the REAL_VALUE_TYPE is zero
12575 but the mpft_t is not, then we underflowed in the
12576 conversion. */
12577 if (real_isfinite (&rr)
12578 && (rr.cl == rvc_zero) == (mpfr_zero_p (m) != 0))
12580 REAL_VALUE_TYPE rmode;
12582 real_convert (&rmode, TYPE_MODE (type), &rr);
12583 /* Proceed iff the specified mode can hold the value. */
12584 if (real_identical (&rmode, &rr))
12585 return build_real (type, rmode);
12588 return NULL_TREE;
12591 /* If argument ARG is a REAL_CST, call the one-argument mpfr function
12592 FUNC on it and return the resulting value as a tree with type TYPE.
12593 If MIN and/or MAX are not NULL, then the supplied ARG must be
12594 within those bounds. If INCLUSIVE is true, then MIN/MAX are
12595 acceptable values, otherwise they are not. The mpfr precision is
12596 set to the precision of TYPE. We assume that function FUNC returns
12597 zero if the result could be calculated exactly within the requested
12598 precision. */
12600 static tree
12601 do_mpfr_arg1 (tree arg, tree type, int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t),
12602 const REAL_VALUE_TYPE *min, const REAL_VALUE_TYPE *max,
12603 bool inclusive)
12605 tree result = NULL_TREE;
12607 STRIP_NOPS (arg);
12609 /* To proceed, MPFR must exactly represent the target floating point
12610 format, which only happens when the target base equals two. */
12611 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12612 && TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
12614 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg);
12616 if (real_isfinite (ra)
12617 && (!min || real_compare (inclusive ? GE_EXPR: GT_EXPR , ra, min))
12618 && (!max || real_compare (inclusive ? LE_EXPR: LT_EXPR , ra, max)))
12620 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12621 int inexact;
12622 mpfr_t m;
12624 mpfr_init2 (m, prec);
12625 mpfr_from_real (m, ra, GMP_RNDN);
12626 mpfr_clear_flags ();
12627 inexact = func (m, m, GMP_RNDN);
12628 result = do_mpfr_ckconv (m, type, inexact);
12629 mpfr_clear (m);
12633 return result;
12636 /* If argument ARG is a REAL_CST, call the two-argument mpfr function
12637 FUNC on it and return the resulting value as a tree with type TYPE.
12638 The mpfr precision is set to the precision of TYPE. We assume that
12639 function FUNC returns zero if the result could be calculated
12640 exactly within the requested precision. */
12642 static tree
12643 do_mpfr_arg2 (tree arg1, tree arg2, tree type,
12644 int (*func)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t))
12646 tree result = NULL_TREE;
12648 STRIP_NOPS (arg1);
12649 STRIP_NOPS (arg2);
12651 /* To proceed, MPFR must exactly represent the target floating point
12652 format, which only happens when the target base equals two. */
12653 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12654 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1)
12655 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2))
12657 const REAL_VALUE_TYPE *const ra1 = &TREE_REAL_CST (arg1);
12658 const REAL_VALUE_TYPE *const ra2 = &TREE_REAL_CST (arg2);
12660 if (real_isfinite (ra1) && real_isfinite (ra2))
12662 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12663 int inexact;
12664 mpfr_t m1, m2;
12666 mpfr_inits2 (prec, m1, m2, NULL);
12667 mpfr_from_real (m1, ra1, GMP_RNDN);
12668 mpfr_from_real (m2, ra2, GMP_RNDN);
12669 mpfr_clear_flags ();
12670 inexact = func (m1, m1, m2, GMP_RNDN);
12671 result = do_mpfr_ckconv (m1, type, inexact);
12672 mpfr_clears (m1, m2, NULL);
12676 return result;
12679 /* If argument ARG is a REAL_CST, call the three-argument mpfr function
12680 FUNC on it and return the resulting value as a tree with type TYPE.
12681 The mpfr precision is set to the precision of TYPE. We assume that
12682 function FUNC returns zero if the result could be calculated
12683 exactly within the requested precision. */
12685 static tree
12686 do_mpfr_arg3 (tree arg1, tree arg2, tree arg3, tree type,
12687 int (*func)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t))
12689 tree result = NULL_TREE;
12691 STRIP_NOPS (arg1);
12692 STRIP_NOPS (arg2);
12693 STRIP_NOPS (arg3);
12695 /* To proceed, MPFR must exactly represent the target floating point
12696 format, which only happens when the target base equals two. */
12697 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12698 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1)
12699 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2)
12700 && TREE_CODE (arg3) == REAL_CST && !TREE_OVERFLOW (arg3))
12702 const REAL_VALUE_TYPE *const ra1 = &TREE_REAL_CST (arg1);
12703 const REAL_VALUE_TYPE *const ra2 = &TREE_REAL_CST (arg2);
12704 const REAL_VALUE_TYPE *const ra3 = &TREE_REAL_CST (arg3);
12706 if (real_isfinite (ra1) && real_isfinite (ra2) && real_isfinite (ra3))
12708 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12709 int inexact;
12710 mpfr_t m1, m2, m3;
12712 mpfr_inits2 (prec, m1, m2, m3, NULL);
12713 mpfr_from_real (m1, ra1, GMP_RNDN);
12714 mpfr_from_real (m2, ra2, GMP_RNDN);
12715 mpfr_from_real (m3, ra3, GMP_RNDN);
12716 mpfr_clear_flags ();
12717 inexact = func (m1, m1, m2, m3, GMP_RNDN);
12718 result = do_mpfr_ckconv (m1, type, inexact);
12719 mpfr_clears (m1, m2, m3, NULL);
12723 return result;
12726 /* If argument ARG is a REAL_CST, call mpfr_sin_cos() on it and set
12727 the pointers *(ARG_SINP) and *(ARG_COSP) to the resulting values.
12728 If ARG_SINP and ARG_COSP are NULL then the result is returned
12729 as a complex value.
12730 The type is taken from the type of ARG and is used for setting the
12731 precision of the calculation and results. */
12733 static tree
12734 do_mpfr_sincos (tree arg, tree arg_sinp, tree arg_cosp)
12736 tree const type = TREE_TYPE (arg);
12737 tree result = NULL_TREE;
12739 STRIP_NOPS (arg);
12741 /* To proceed, MPFR must exactly represent the target floating point
12742 format, which only happens when the target base equals two. */
12743 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12744 && TREE_CODE (arg) == REAL_CST
12745 && !TREE_OVERFLOW (arg))
12747 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg);
12749 if (real_isfinite (ra))
12751 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12752 tree result_s, result_c;
12753 int inexact;
12754 mpfr_t m, ms, mc;
12756 mpfr_inits2 (prec, m, ms, mc, NULL);
12757 mpfr_from_real (m, ra, GMP_RNDN);
12758 mpfr_clear_flags ();
12759 inexact = mpfr_sin_cos (ms, mc, m, GMP_RNDN);
12760 result_s = do_mpfr_ckconv (ms, type, inexact);
12761 result_c = do_mpfr_ckconv (mc, type, inexact);
12762 mpfr_clears (m, ms, mc, NULL);
12763 if (result_s && result_c)
12765 /* If we are to return in a complex value do so. */
12766 if (!arg_sinp && !arg_cosp)
12767 return build_complex (build_complex_type (type),
12768 result_c, result_s);
12770 /* Dereference the sin/cos pointer arguments. */
12771 arg_sinp = build_fold_indirect_ref (arg_sinp);
12772 arg_cosp = build_fold_indirect_ref (arg_cosp);
12773 /* Proceed if valid pointer type were passed in. */
12774 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg_sinp)) == TYPE_MAIN_VARIANT (type)
12775 && TYPE_MAIN_VARIANT (TREE_TYPE (arg_cosp)) == TYPE_MAIN_VARIANT (type))
12777 /* Set the values. */
12778 result_s = fold_build2 (MODIFY_EXPR, type, arg_sinp,
12779 result_s);
12780 TREE_SIDE_EFFECTS (result_s) = 1;
12781 result_c = fold_build2 (MODIFY_EXPR, type, arg_cosp,
12782 result_c);
12783 TREE_SIDE_EFFECTS (result_c) = 1;
12784 /* Combine the assignments into a compound expr. */
12785 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
12786 result_s, result_c));
12791 return result;
12794 #if MPFR_VERSION >= MPFR_VERSION_NUM(2,3,0)
12795 /* If argument ARG1 is an INTEGER_CST and ARG2 is a REAL_CST, call the
12796 two-argument mpfr order N Bessel function FUNC on them and return
12797 the resulting value as a tree with type TYPE. The mpfr precision
12798 is set to the precision of TYPE. We assume that function FUNC
12799 returns zero if the result could be calculated exactly within the
12800 requested precision. */
12801 static tree
12802 do_mpfr_bessel_n (tree arg1, tree arg2, tree type,
12803 int (*func)(mpfr_ptr, long, mpfr_srcptr, mp_rnd_t),
12804 const REAL_VALUE_TYPE *min, bool inclusive)
12806 tree result = NULL_TREE;
12808 STRIP_NOPS (arg1);
12809 STRIP_NOPS (arg2);
12811 /* To proceed, MPFR must exactly represent the target floating point
12812 format, which only happens when the target base equals two. */
12813 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12814 && host_integerp (arg1, 0)
12815 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2))
12817 const HOST_WIDE_INT n = tree_low_cst(arg1, 0);
12818 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg2);
12820 if (n == (long)n
12821 && real_isfinite (ra)
12822 && (!min || real_compare (inclusive ? GE_EXPR: GT_EXPR , ra, min)))
12824 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12825 int inexact;
12826 mpfr_t m;
12828 mpfr_init2 (m, prec);
12829 mpfr_from_real (m, ra, GMP_RNDN);
12830 mpfr_clear_flags ();
12831 inexact = func (m, n, m, GMP_RNDN);
12832 result = do_mpfr_ckconv (m, type, inexact);
12833 mpfr_clear (m);
12837 return result;
12840 /* If arguments ARG0 and ARG1 are REAL_CSTs, call mpfr_remquo() to set
12841 the pointer *(ARG_QUO) and return the result. The type is taken
12842 from the type of ARG0 and is used for setting the precision of the
12843 calculation and results. */
12845 static tree
12846 do_mpfr_remquo (tree arg0, tree arg1, tree arg_quo)
12848 tree const type = TREE_TYPE (arg0);
12849 tree result = NULL_TREE;
12851 STRIP_NOPS (arg0);
12852 STRIP_NOPS (arg1);
12854 /* To proceed, MPFR must exactly represent the target floating point
12855 format, which only happens when the target base equals two. */
12856 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12857 && TREE_CODE (arg0) == REAL_CST && !TREE_OVERFLOW (arg0)
12858 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1))
12860 const REAL_VALUE_TYPE *const ra0 = TREE_REAL_CST_PTR (arg0);
12861 const REAL_VALUE_TYPE *const ra1 = TREE_REAL_CST_PTR (arg1);
12863 if (real_isfinite (ra0) && real_isfinite (ra1))
12865 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12866 tree result_rem;
12867 long integer_quo;
12868 mpfr_t m0, m1;
12870 mpfr_inits2 (prec, m0, m1, NULL);
12871 mpfr_from_real (m0, ra0, GMP_RNDN);
12872 mpfr_from_real (m1, ra1, GMP_RNDN);
12873 mpfr_clear_flags ();
12874 mpfr_remquo (m0, &integer_quo, m0, m1, GMP_RNDN);
12875 /* Remquo is independent of the rounding mode, so pass
12876 inexact=0 to do_mpfr_ckconv(). */
12877 result_rem = do_mpfr_ckconv (m0, type, /*inexact=*/ 0);
12878 mpfr_clears (m0, m1, NULL);
12879 if (result_rem)
12881 /* MPFR calculates quo in the host's long so it may
12882 return more bits in quo than the target int can hold
12883 if sizeof(host long) > sizeof(target int). This can
12884 happen even for native compilers in LP64 mode. In
12885 these cases, modulo the quo value with the largest
12886 number that the target int can hold while leaving one
12887 bit for the sign. */
12888 if (sizeof (integer_quo) * CHAR_BIT > INT_TYPE_SIZE)
12889 integer_quo %= (long)(1UL << (INT_TYPE_SIZE - 1));
12891 /* Dereference the quo pointer argument. */
12892 arg_quo = build_fold_indirect_ref (arg_quo);
12893 /* Proceed iff a valid pointer type was passed in. */
12894 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg_quo)) == integer_type_node)
12896 /* Set the value. */
12897 tree result_quo = fold_build2 (MODIFY_EXPR,
12898 TREE_TYPE (arg_quo), arg_quo,
12899 build_int_cst (NULL, integer_quo));
12900 TREE_SIDE_EFFECTS (result_quo) = 1;
12901 /* Combine the quo assignment with the rem. */
12902 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
12903 result_quo, result_rem));
12908 return result;
12911 /* If ARG is a REAL_CST, call mpfr_lgamma() on it and return the
12912 resulting value as a tree with type TYPE. The mpfr precision is
12913 set to the precision of TYPE. We assume that this mpfr function
12914 returns zero if the result could be calculated exactly within the
12915 requested precision. In addition, the integer pointer represented
12916 by ARG_SG will be dereferenced and set to the appropriate signgam
12917 (-1,1) value. */
12919 static tree
12920 do_mpfr_lgamma_r (tree arg, tree arg_sg, tree type)
12922 tree result = NULL_TREE;
12924 STRIP_NOPS (arg);
12926 /* To proceed, MPFR must exactly represent the target floating point
12927 format, which only happens when the target base equals two. Also
12928 verify ARG is a constant and that ARG_SG is an int pointer. */
12929 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12930 && TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg)
12931 && TREE_CODE (TREE_TYPE (arg_sg)) == POINTER_TYPE
12932 && TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (arg_sg))) == integer_type_node)
12934 const REAL_VALUE_TYPE *const ra = TREE_REAL_CST_PTR (arg);
12936 /* In addition to NaN and Inf, the argument cannot be zero or a
12937 negative integer. */
12938 if (real_isfinite (ra)
12939 && ra->cl != rvc_zero
12940 && !(real_isneg(ra) && real_isinteger(ra, TYPE_MODE (type))))
12942 const int prec = REAL_MODE_FORMAT (TYPE_MODE (type))->p;
12943 int inexact, sg;
12944 mpfr_t m;
12945 tree result_lg;
12947 mpfr_init2 (m, prec);
12948 mpfr_from_real (m, ra, GMP_RNDN);
12949 mpfr_clear_flags ();
12950 inexact = mpfr_lgamma (m, &sg, m, GMP_RNDN);
12951 result_lg = do_mpfr_ckconv (m, type, inexact);
12952 mpfr_clear (m);
12953 if (result_lg)
12955 tree result_sg;
12957 /* Dereference the arg_sg pointer argument. */
12958 arg_sg = build_fold_indirect_ref (arg_sg);
12959 /* Assign the signgam value into *arg_sg. */
12960 result_sg = fold_build2 (MODIFY_EXPR,
12961 TREE_TYPE (arg_sg), arg_sg,
12962 build_int_cst (NULL, sg));
12963 TREE_SIDE_EFFECTS (result_sg) = 1;
12964 /* Combine the signgam assignment with the lgamma result. */
12965 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
12966 result_sg, result_lg));
12971 return result;
12973 #endif