5f4b7176155485cd53604361eee28baa924543fa
[gcc.git] / gcc / builtins.c
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, 2008, 2009, 2010
4 Free Software Foundation, Inc.
5
6 This file is part of GCC.
7
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.
12
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.
17
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/>. */
21
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 "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"
53
54 #ifndef SLOW_UNALIGNED_ACCESS
55 #define SLOW_UNALIGNED_ACCESS(MODE, ALIGN) STRICT_ALIGNMENT
56 #endif
57
58 #ifndef PAD_VARARGS_DOWN
59 #define PAD_VARARGS_DOWN BYTES_BIG_ENDIAN
60 #endif
61 static tree do_mpc_arg1 (tree, tree, int (*)(mpc_ptr, mpc_srcptr, mpc_rnd_t));
62
63 /* Define the names of the builtin function types and codes. */
64 const char *const built_in_class_names[4]
65 = {"NOT_BUILT_IN", "BUILT_IN_FRONTEND", "BUILT_IN_MD", "BUILT_IN_NORMAL"};
66
67 #define DEF_BUILTIN(X, N, C, T, LT, B, F, NA, AT, IM, COND) #X,
68 const char * built_in_names[(int) END_BUILTINS] =
69 {
70 #include "builtins.def"
71 };
72 #undef DEF_BUILTIN
73
74 /* Setup an array of _DECL trees, make sure each element is
75 initialized to NULL_TREE. */
76 tree built_in_decls[(int) END_BUILTINS];
77 /* Declarations used when constructing the builtin implicitly in the compiler.
78 It may be NULL_TREE when this is invalid (for instance runtime is not
79 required to implement the function call in all cases). */
80 tree implicit_built_in_decls[(int) END_BUILTINS];
81
82 static const char *c_getstr (tree);
83 static rtx c_readstr (const char *, enum machine_mode);
84 static int target_char_cast (tree, char *);
85 static rtx get_memory_rtx (tree, tree);
86 static int apply_args_size (void);
87 static int apply_result_size (void);
88 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
89 static rtx result_vector (int, rtx);
90 #endif
91 static void expand_builtin_update_setjmp_buf (rtx);
92 static void expand_builtin_prefetch (tree);
93 static rtx expand_builtin_apply_args (void);
94 static rtx expand_builtin_apply_args_1 (void);
95 static rtx expand_builtin_apply (rtx, rtx, rtx);
96 static void expand_builtin_return (rtx);
97 static enum type_class type_to_class (tree);
98 static rtx expand_builtin_classify_type (tree);
99 static void expand_errno_check (tree, rtx);
100 static rtx expand_builtin_mathfn (tree, rtx, rtx);
101 static rtx expand_builtin_mathfn_2 (tree, rtx, rtx);
102 static rtx expand_builtin_mathfn_3 (tree, rtx, rtx);
103 static rtx expand_builtin_interclass_mathfn (tree, rtx, rtx);
104 static rtx expand_builtin_sincos (tree);
105 static rtx expand_builtin_cexpi (tree, rtx, rtx);
106 static rtx expand_builtin_int_roundingfn (tree, rtx);
107 static rtx expand_builtin_int_roundingfn_2 (tree, rtx);
108 static rtx expand_builtin_args_info (tree);
109 static rtx expand_builtin_next_arg (void);
110 static rtx expand_builtin_va_start (tree);
111 static rtx expand_builtin_va_end (tree);
112 static rtx expand_builtin_va_copy (tree);
113 static rtx expand_builtin_memcmp (tree, rtx, enum machine_mode);
114 static rtx expand_builtin_strcmp (tree, rtx);
115 static rtx expand_builtin_strncmp (tree, rtx, enum machine_mode);
116 static rtx builtin_memcpy_read_str (void *, HOST_WIDE_INT, enum machine_mode);
117 static rtx expand_builtin_memcpy (tree, rtx);
118 static rtx expand_builtin_mempcpy (tree, rtx, enum machine_mode);
119 static rtx expand_builtin_mempcpy_args (tree, tree, tree, rtx,
120 enum machine_mode, int);
121 static rtx expand_builtin_strcpy (tree, rtx);
122 static rtx expand_builtin_strcpy_args (tree, tree, rtx);
123 static rtx expand_builtin_stpcpy (tree, rtx, enum machine_mode);
124 static rtx expand_builtin_strncpy (tree, rtx);
125 static rtx builtin_memset_gen_str (void *, HOST_WIDE_INT, enum machine_mode);
126 static rtx expand_builtin_memset (tree, rtx, enum machine_mode);
127 static rtx expand_builtin_memset_args (tree, tree, tree, rtx, enum machine_mode, tree);
128 static rtx expand_builtin_bzero (tree);
129 static rtx expand_builtin_strlen (tree, rtx, enum machine_mode);
130 static rtx expand_builtin_alloca (tree, rtx);
131 static rtx expand_builtin_unop (enum machine_mode, tree, rtx, rtx, optab);
132 static rtx expand_builtin_frame_address (tree, tree);
133 static tree stabilize_va_list_loc (location_t, tree, int);
134 static rtx expand_builtin_expect (tree, rtx);
135 static tree fold_builtin_constant_p (tree);
136 static tree fold_builtin_expect (location_t, tree, tree);
137 static tree fold_builtin_classify_type (tree);
138 static tree fold_builtin_strlen (location_t, tree, tree);
139 static tree fold_builtin_inf (location_t, tree, int);
140 static tree fold_builtin_nan (tree, tree, int);
141 static tree rewrite_call_expr (location_t, tree, int, tree, int, ...);
142 static bool validate_arg (const_tree, enum tree_code code);
143 static bool integer_valued_real_p (tree);
144 static tree fold_trunc_transparent_mathfn (location_t, tree, tree);
145 static bool readonly_data_expr (tree);
146 static rtx expand_builtin_fabs (tree, rtx, rtx);
147 static rtx expand_builtin_signbit (tree, rtx);
148 static tree fold_builtin_sqrt (location_t, tree, tree);
149 static tree fold_builtin_cbrt (location_t, tree, tree);
150 static tree fold_builtin_pow (location_t, tree, tree, tree, tree);
151 static tree fold_builtin_powi (location_t, tree, tree, tree, tree);
152 static tree fold_builtin_cos (location_t, tree, tree, tree);
153 static tree fold_builtin_cosh (location_t, tree, tree, tree);
154 static tree fold_builtin_tan (tree, tree);
155 static tree fold_builtin_trunc (location_t, tree, tree);
156 static tree fold_builtin_floor (location_t, tree, tree);
157 static tree fold_builtin_ceil (location_t, tree, tree);
158 static tree fold_builtin_round (location_t, tree, tree);
159 static tree fold_builtin_int_roundingfn (location_t, tree, tree);
160 static tree fold_builtin_bitop (tree, tree);
161 static tree fold_builtin_memory_op (location_t, tree, tree, tree, tree, bool, int);
162 static tree fold_builtin_strchr (location_t, tree, tree, tree);
163 static tree fold_builtin_memchr (location_t, tree, tree, tree, tree);
164 static tree fold_builtin_memcmp (location_t, tree, tree, tree);
165 static tree fold_builtin_strcmp (location_t, tree, tree);
166 static tree fold_builtin_strncmp (location_t, tree, tree, tree);
167 static tree fold_builtin_signbit (location_t, tree, tree);
168 static tree fold_builtin_copysign (location_t, tree, tree, tree, tree);
169 static tree fold_builtin_isascii (location_t, tree);
170 static tree fold_builtin_toascii (location_t, tree);
171 static tree fold_builtin_isdigit (location_t, tree);
172 static tree fold_builtin_fabs (location_t, tree, tree);
173 static tree fold_builtin_abs (location_t, tree, tree);
174 static tree fold_builtin_unordered_cmp (location_t, tree, tree, tree, enum tree_code,
175 enum tree_code);
176 static tree fold_builtin_n (location_t, tree, tree *, int, bool);
177 static tree fold_builtin_0 (location_t, tree, bool);
178 static tree fold_builtin_1 (location_t, tree, tree, bool);
179 static tree fold_builtin_2 (location_t, tree, tree, tree, bool);
180 static tree fold_builtin_3 (location_t, tree, tree, tree, tree, bool);
181 static tree fold_builtin_4 (location_t, tree, tree, tree, tree, tree, bool);
182 static tree fold_builtin_varargs (location_t, tree, tree, bool);
183
184 static tree fold_builtin_strpbrk (location_t, tree, tree, tree);
185 static tree fold_builtin_strstr (location_t, tree, tree, tree);
186 static tree fold_builtin_strrchr (location_t, tree, tree, tree);
187 static tree fold_builtin_strcat (location_t, tree, tree);
188 static tree fold_builtin_strncat (location_t, tree, tree, tree);
189 static tree fold_builtin_strspn (location_t, tree, tree);
190 static tree fold_builtin_strcspn (location_t, tree, tree);
191 static tree fold_builtin_sprintf (location_t, tree, tree, tree, int);
192
193 static rtx expand_builtin_object_size (tree);
194 static rtx expand_builtin_memory_chk (tree, rtx, enum machine_mode,
195 enum built_in_function);
196 static void maybe_emit_chk_warning (tree, enum built_in_function);
197 static void maybe_emit_sprintf_chk_warning (tree, enum built_in_function);
198 static void maybe_emit_free_warning (tree);
199 static tree fold_builtin_object_size (tree, tree);
200 static tree fold_builtin_strcat_chk (location_t, tree, tree, tree, tree);
201 static tree fold_builtin_strncat_chk (location_t, tree, tree, tree, tree, tree);
202 static tree fold_builtin_sprintf_chk (location_t, tree, enum built_in_function);
203 static tree fold_builtin_printf (location_t, tree, tree, tree, bool, enum built_in_function);
204 static tree fold_builtin_fprintf (location_t, tree, tree, tree, tree, bool,
205 enum built_in_function);
206 static bool init_target_chars (void);
207
208 static unsigned HOST_WIDE_INT target_newline;
209 static unsigned HOST_WIDE_INT target_percent;
210 static unsigned HOST_WIDE_INT target_c;
211 static unsigned HOST_WIDE_INT target_s;
212 static char target_percent_c[3];
213 static char target_percent_s[3];
214 static char target_percent_s_newline[4];
215 static tree do_mpfr_arg1 (tree, tree, int (*)(mpfr_ptr, mpfr_srcptr, mp_rnd_t),
216 const REAL_VALUE_TYPE *, const REAL_VALUE_TYPE *, bool);
217 static tree do_mpfr_arg2 (tree, tree, tree,
218 int (*)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t));
219 static tree do_mpfr_arg3 (tree, tree, tree, tree,
220 int (*)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t));
221 static tree do_mpfr_sincos (tree, tree, tree);
222 static tree do_mpfr_bessel_n (tree, tree, tree,
223 int (*)(mpfr_ptr, long, mpfr_srcptr, mp_rnd_t),
224 const REAL_VALUE_TYPE *, bool);
225 static tree do_mpfr_remquo (tree, tree, tree);
226 static tree do_mpfr_lgamma_r (tree, tree, tree);
227
228 /* Return true if NAME starts with __builtin_ or __sync_. */
229
230 bool
231 is_builtin_name (const char *name)
232 {
233 if (strncmp (name, "__builtin_", 10) == 0)
234 return true;
235 if (strncmp (name, "__sync_", 7) == 0)
236 return true;
237 return false;
238 }
239
240
241 /* Return true if DECL is a function symbol representing a built-in. */
242
243 bool
244 is_builtin_fn (tree decl)
245 {
246 return TREE_CODE (decl) == FUNCTION_DECL && DECL_BUILT_IN (decl);
247 }
248
249
250 /* Return true if NODE should be considered for inline expansion regardless
251 of the optimization level. This means whenever a function is invoked with
252 its "internal" name, which normally contains the prefix "__builtin". */
253
254 static bool
255 called_as_built_in (tree node)
256 {
257 /* Note that we must use DECL_NAME, not DECL_ASSEMBLER_NAME_SET_P since
258 we want the name used to call the function, not the name it
259 will have. */
260 const char *name = IDENTIFIER_POINTER (DECL_NAME (node));
261 return is_builtin_name (name);
262 }
263
264 /* Return the alignment in bits of EXP, an object.
265 Don't return more than MAX_ALIGN no matter what, ALIGN is the inital
266 guessed alignment e.g. from type alignment. */
267
268 int
269 get_object_alignment (tree exp, unsigned int align, unsigned int max_align)
270 {
271 unsigned int inner;
272
273 inner = max_align;
274 if (handled_component_p (exp))
275 {
276 HOST_WIDE_INT bitsize, bitpos;
277 tree offset;
278 enum machine_mode mode;
279 int unsignedp, volatilep;
280
281 exp = get_inner_reference (exp, &bitsize, &bitpos, &offset,
282 &mode, &unsignedp, &volatilep, true);
283 if (bitpos)
284 inner = MIN (inner, (unsigned) (bitpos & -bitpos));
285 while (offset)
286 {
287 tree next_offset;
288
289 if (TREE_CODE (offset) == PLUS_EXPR)
290 {
291 next_offset = TREE_OPERAND (offset, 0);
292 offset = TREE_OPERAND (offset, 1);
293 }
294 else
295 next_offset = NULL;
296 if (host_integerp (offset, 1))
297 {
298 /* Any overflow in calculating offset_bits won't change
299 the alignment. */
300 unsigned offset_bits
301 = ((unsigned) tree_low_cst (offset, 1) * BITS_PER_UNIT);
302
303 if (offset_bits)
304 inner = MIN (inner, (offset_bits & -offset_bits));
305 }
306 else if (TREE_CODE (offset) == MULT_EXPR
307 && host_integerp (TREE_OPERAND (offset, 1), 1))
308 {
309 /* Any overflow in calculating offset_factor won't change
310 the alignment. */
311 unsigned offset_factor
312 = ((unsigned) tree_low_cst (TREE_OPERAND (offset, 1), 1)
313 * BITS_PER_UNIT);
314
315 if (offset_factor)
316 inner = MIN (inner, (offset_factor & -offset_factor));
317 }
318 else
319 {
320 inner = MIN (inner, BITS_PER_UNIT);
321 break;
322 }
323 offset = next_offset;
324 }
325 }
326 if (TREE_CODE (exp) == CONST_DECL)
327 exp = DECL_INITIAL (exp);
328 if (DECL_P (exp)
329 && TREE_CODE (exp) != LABEL_DECL)
330 align = MIN (inner, DECL_ALIGN (exp));
331 #ifdef CONSTANT_ALIGNMENT
332 else if (CONSTANT_CLASS_P (exp))
333 align = MIN (inner, (unsigned)CONSTANT_ALIGNMENT (exp, align));
334 #endif
335 else if (TREE_CODE (exp) == VIEW_CONVERT_EXPR
336 || TREE_CODE (exp) == INDIRECT_REF)
337 align = MIN (TYPE_ALIGN (TREE_TYPE (exp)), inner);
338 else
339 align = MIN (align, inner);
340 return MIN (align, max_align);
341 }
342
343 /* Returns true iff we can trust that alignment information has been
344 calculated properly. */
345
346 bool
347 can_trust_pointer_alignment (void)
348 {
349 /* We rely on TER to compute accurate alignment information. */
350 return (optimize && flag_tree_ter);
351 }
352
353 /* Return the alignment in bits of EXP, a pointer valued expression.
354 But don't return more than MAX_ALIGN no matter what.
355 The alignment returned is, by default, the alignment of the thing that
356 EXP points to. If it is not a POINTER_TYPE, 0 is returned.
357
358 Otherwise, look at the expression to see if we can do better, i.e., if the
359 expression is actually pointing at an object whose alignment is tighter. */
360
361 int
362 get_pointer_alignment (tree exp, unsigned int max_align)
363 {
364 unsigned int align, inner;
365
366 if (!can_trust_pointer_alignment ())
367 return 0;
368
369 if (!POINTER_TYPE_P (TREE_TYPE (exp)))
370 return 0;
371
372 align = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
373 align = MIN (align, max_align);
374
375 while (1)
376 {
377 switch (TREE_CODE (exp))
378 {
379 CASE_CONVERT:
380 exp = TREE_OPERAND (exp, 0);
381 if (! POINTER_TYPE_P (TREE_TYPE (exp)))
382 return align;
383
384 inner = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
385 align = MIN (inner, max_align);
386 break;
387
388 case POINTER_PLUS_EXPR:
389 /* If sum of pointer + int, restrict our maximum alignment to that
390 imposed by the integer. If not, we can't do any better than
391 ALIGN. */
392 if (! host_integerp (TREE_OPERAND (exp, 1), 1))
393 return align;
394
395 while (((tree_low_cst (TREE_OPERAND (exp, 1), 1))
396 & (max_align / BITS_PER_UNIT - 1))
397 != 0)
398 max_align >>= 1;
399
400 exp = TREE_OPERAND (exp, 0);
401 break;
402
403 case ADDR_EXPR:
404 /* See what we are pointing at and look at its alignment. */
405 return get_object_alignment (TREE_OPERAND (exp, 0), align, max_align);
406
407 default:
408 return align;
409 }
410 }
411 }
412
413 /* Compute the length of a C string. TREE_STRING_LENGTH is not the right
414 way, because it could contain a zero byte in the middle.
415 TREE_STRING_LENGTH is the size of the character array, not the string.
416
417 ONLY_VALUE should be nonzero if the result is not going to be emitted
418 into the instruction stream and zero if it is going to be expanded.
419 E.g. with i++ ? "foo" : "bar", if ONLY_VALUE is nonzero, constant 3
420 is returned, otherwise NULL, since
421 len = c_strlen (src, 1); if (len) expand_expr (len, ...); would not
422 evaluate the side-effects.
423
424 The value returned is of type `ssizetype'.
425
426 Unfortunately, string_constant can't access the values of const char
427 arrays with initializers, so neither can we do so here. */
428
429 tree
430 c_strlen (tree src, int only_value)
431 {
432 tree offset_node;
433 HOST_WIDE_INT offset;
434 int max;
435 const char *ptr;
436 location_t loc;
437
438 STRIP_NOPS (src);
439 if (TREE_CODE (src) == COND_EXPR
440 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
441 {
442 tree len1, len2;
443
444 len1 = c_strlen (TREE_OPERAND (src, 1), only_value);
445 len2 = c_strlen (TREE_OPERAND (src, 2), only_value);
446 if (tree_int_cst_equal (len1, len2))
447 return len1;
448 }
449
450 if (TREE_CODE (src) == COMPOUND_EXPR
451 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
452 return c_strlen (TREE_OPERAND (src, 1), only_value);
453
454 if (EXPR_HAS_LOCATION (src))
455 loc = EXPR_LOCATION (src);
456 else
457 loc = input_location;
458
459 src = string_constant (src, &offset_node);
460 if (src == 0)
461 return NULL_TREE;
462
463 max = TREE_STRING_LENGTH (src) - 1;
464 ptr = TREE_STRING_POINTER (src);
465
466 if (offset_node && TREE_CODE (offset_node) != INTEGER_CST)
467 {
468 /* If the string has an internal zero byte (e.g., "foo\0bar"), we can't
469 compute the offset to the following null if we don't know where to
470 start searching for it. */
471 int i;
472
473 for (i = 0; i < max; i++)
474 if (ptr[i] == 0)
475 return NULL_TREE;
476
477 /* We don't know the starting offset, but we do know that the string
478 has no internal zero bytes. We can assume that the offset falls
479 within the bounds of the string; otherwise, the programmer deserves
480 what he gets. Subtract the offset from the length of the string,
481 and return that. This would perhaps not be valid if we were dealing
482 with named arrays in addition to literal string constants. */
483
484 return size_diffop_loc (loc, size_int (max), offset_node);
485 }
486
487 /* We have a known offset into the string. Start searching there for
488 a null character if we can represent it as a single HOST_WIDE_INT. */
489 if (offset_node == 0)
490 offset = 0;
491 else if (! host_integerp (offset_node, 0))
492 offset = -1;
493 else
494 offset = tree_low_cst (offset_node, 0);
495
496 /* If the offset is known to be out of bounds, warn, and call strlen at
497 runtime. */
498 if (offset < 0 || offset > max)
499 {
500 /* Suppress multiple warnings for propagated constant strings. */
501 if (! TREE_NO_WARNING (src))
502 {
503 warning_at (loc, 0, "offset outside bounds of constant string");
504 TREE_NO_WARNING (src) = 1;
505 }
506 return NULL_TREE;
507 }
508
509 /* Use strlen to search for the first zero byte. Since any strings
510 constructed with build_string will have nulls appended, we win even
511 if we get handed something like (char[4])"abcd".
512
513 Since OFFSET is our starting index into the string, no further
514 calculation is needed. */
515 return ssize_int (strlen (ptr + offset));
516 }
517
518 /* Return a char pointer for a C string if it is a string constant
519 or sum of string constant and integer constant. */
520
521 static const char *
522 c_getstr (tree src)
523 {
524 tree offset_node;
525
526 src = string_constant (src, &offset_node);
527 if (src == 0)
528 return 0;
529
530 if (offset_node == 0)
531 return TREE_STRING_POINTER (src);
532 else if (!host_integerp (offset_node, 1)
533 || compare_tree_int (offset_node, TREE_STRING_LENGTH (src) - 1) > 0)
534 return 0;
535
536 return TREE_STRING_POINTER (src) + tree_low_cst (offset_node, 1);
537 }
538
539 /* Return a CONST_INT or CONST_DOUBLE corresponding to target reading
540 GET_MODE_BITSIZE (MODE) bits from string constant STR. */
541
542 static rtx
543 c_readstr (const char *str, enum machine_mode mode)
544 {
545 HOST_WIDE_INT c[2];
546 HOST_WIDE_INT ch;
547 unsigned int i, j;
548
549 gcc_assert (GET_MODE_CLASS (mode) == MODE_INT);
550
551 c[0] = 0;
552 c[1] = 0;
553 ch = 1;
554 for (i = 0; i < GET_MODE_SIZE (mode); i++)
555 {
556 j = i;
557 if (WORDS_BIG_ENDIAN)
558 j = GET_MODE_SIZE (mode) - i - 1;
559 if (BYTES_BIG_ENDIAN != WORDS_BIG_ENDIAN
560 && GET_MODE_SIZE (mode) > UNITS_PER_WORD)
561 j = j + UNITS_PER_WORD - 2 * (j % UNITS_PER_WORD) - 1;
562 j *= BITS_PER_UNIT;
563 gcc_assert (j < 2 * HOST_BITS_PER_WIDE_INT);
564
565 if (ch)
566 ch = (unsigned char) str[i];
567 c[j / HOST_BITS_PER_WIDE_INT] |= ch << (j % HOST_BITS_PER_WIDE_INT);
568 }
569 return immed_double_const (c[0], c[1], mode);
570 }
571
572 /* Cast a target constant CST to target CHAR and if that value fits into
573 host char type, return zero and put that value into variable pointed to by
574 P. */
575
576 static int
577 target_char_cast (tree cst, char *p)
578 {
579 unsigned HOST_WIDE_INT val, hostval;
580
581 if (!host_integerp (cst, 1)
582 || CHAR_TYPE_SIZE > HOST_BITS_PER_WIDE_INT)
583 return 1;
584
585 val = tree_low_cst (cst, 1);
586 if (CHAR_TYPE_SIZE < HOST_BITS_PER_WIDE_INT)
587 val &= (((unsigned HOST_WIDE_INT) 1) << CHAR_TYPE_SIZE) - 1;
588
589 hostval = val;
590 if (HOST_BITS_PER_CHAR < HOST_BITS_PER_WIDE_INT)
591 hostval &= (((unsigned HOST_WIDE_INT) 1) << HOST_BITS_PER_CHAR) - 1;
592
593 if (val != hostval)
594 return 1;
595
596 *p = hostval;
597 return 0;
598 }
599
600 /* Similar to save_expr, but assumes that arbitrary code is not executed
601 in between the multiple evaluations. In particular, we assume that a
602 non-addressable local variable will not be modified. */
603
604 static tree
605 builtin_save_expr (tree exp)
606 {
607 if (TREE_ADDRESSABLE (exp) == 0
608 && (TREE_CODE (exp) == PARM_DECL
609 || (TREE_CODE (exp) == VAR_DECL && !TREE_STATIC (exp))))
610 return exp;
611
612 return save_expr (exp);
613 }
614
615 /* Given TEM, a pointer to a stack frame, follow the dynamic chain COUNT
616 times to get the address of either a higher stack frame, or a return
617 address located within it (depending on FNDECL_CODE). */
618
619 static rtx
620 expand_builtin_return_addr (enum built_in_function fndecl_code, int count)
621 {
622 int i;
623
624 #ifdef INITIAL_FRAME_ADDRESS_RTX
625 rtx tem = INITIAL_FRAME_ADDRESS_RTX;
626 #else
627 rtx tem;
628
629 /* For a zero count with __builtin_return_address, we don't care what
630 frame address we return, because target-specific definitions will
631 override us. Therefore frame pointer elimination is OK, and using
632 the soft frame pointer is OK.
633
634 For a nonzero count, or a zero count with __builtin_frame_address,
635 we require a stable offset from the current frame pointer to the
636 previous one, so we must use the hard frame pointer, and
637 we must disable frame pointer elimination. */
638 if (count == 0 && fndecl_code == BUILT_IN_RETURN_ADDRESS)
639 tem = frame_pointer_rtx;
640 else
641 {
642 tem = hard_frame_pointer_rtx;
643
644 /* Tell reload not to eliminate the frame pointer. */
645 crtl->accesses_prior_frames = 1;
646 }
647 #endif
648
649 /* Some machines need special handling before we can access
650 arbitrary frames. For example, on the SPARC, we must first flush
651 all register windows to the stack. */
652 #ifdef SETUP_FRAME_ADDRESSES
653 if (count > 0)
654 SETUP_FRAME_ADDRESSES ();
655 #endif
656
657 /* On the SPARC, the return address is not in the frame, it is in a
658 register. There is no way to access it off of the current frame
659 pointer, but it can be accessed off the previous frame pointer by
660 reading the value from the register window save area. */
661 #ifdef RETURN_ADDR_IN_PREVIOUS_FRAME
662 if (fndecl_code == BUILT_IN_RETURN_ADDRESS)
663 count--;
664 #endif
665
666 /* Scan back COUNT frames to the specified frame. */
667 for (i = 0; i < count; i++)
668 {
669 /* Assume the dynamic chain pointer is in the word that the
670 frame address points to, unless otherwise specified. */
671 #ifdef DYNAMIC_CHAIN_ADDRESS
672 tem = DYNAMIC_CHAIN_ADDRESS (tem);
673 #endif
674 tem = memory_address (Pmode, tem);
675 tem = gen_frame_mem (Pmode, tem);
676 tem = copy_to_reg (tem);
677 }
678
679 /* For __builtin_frame_address, return what we've got. But, on
680 the SPARC for example, we may have to add a bias. */
681 if (fndecl_code == BUILT_IN_FRAME_ADDRESS)
682 #ifdef FRAME_ADDR_RTX
683 return FRAME_ADDR_RTX (tem);
684 #else
685 return tem;
686 #endif
687
688 /* For __builtin_return_address, get the return address from that frame. */
689 #ifdef RETURN_ADDR_RTX
690 tem = RETURN_ADDR_RTX (count, tem);
691 #else
692 tem = memory_address (Pmode,
693 plus_constant (tem, GET_MODE_SIZE (Pmode)));
694 tem = gen_frame_mem (Pmode, tem);
695 #endif
696 return tem;
697 }
698
699 /* Alias set used for setjmp buffer. */
700 static alias_set_type setjmp_alias_set = -1;
701
702 /* Construct the leading half of a __builtin_setjmp call. Control will
703 return to RECEIVER_LABEL. This is also called directly by the SJLJ
704 exception handling code. */
705
706 void
707 expand_builtin_setjmp_setup (rtx buf_addr, rtx receiver_label)
708 {
709 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
710 rtx stack_save;
711 rtx mem;
712
713 if (setjmp_alias_set == -1)
714 setjmp_alias_set = new_alias_set ();
715
716 buf_addr = convert_memory_address (Pmode, buf_addr);
717
718 buf_addr = force_reg (Pmode, force_operand (buf_addr, NULL_RTX));
719
720 /* We store the frame pointer and the address of receiver_label in
721 the buffer and use the rest of it for the stack save area, which
722 is machine-dependent. */
723
724 mem = gen_rtx_MEM (Pmode, buf_addr);
725 set_mem_alias_set (mem, setjmp_alias_set);
726 emit_move_insn (mem, targetm.builtin_setjmp_frame_value ());
727
728 mem = gen_rtx_MEM (Pmode, plus_constant (buf_addr, GET_MODE_SIZE (Pmode))),
729 set_mem_alias_set (mem, setjmp_alias_set);
730
731 emit_move_insn (validize_mem (mem),
732 force_reg (Pmode, gen_rtx_LABEL_REF (Pmode, receiver_label)));
733
734 stack_save = gen_rtx_MEM (sa_mode,
735 plus_constant (buf_addr,
736 2 * GET_MODE_SIZE (Pmode)));
737 set_mem_alias_set (stack_save, setjmp_alias_set);
738 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
739
740 /* If there is further processing to do, do it. */
741 #ifdef HAVE_builtin_setjmp_setup
742 if (HAVE_builtin_setjmp_setup)
743 emit_insn (gen_builtin_setjmp_setup (buf_addr));
744 #endif
745
746 /* Tell optimize_save_area_alloca that extra work is going to
747 need to go on during alloca. */
748 cfun->calls_setjmp = 1;
749
750 /* We have a nonlocal label. */
751 cfun->has_nonlocal_label = 1;
752 }
753
754 /* Construct the trailing part of a __builtin_setjmp call. This is
755 also called directly by the SJLJ exception handling code. */
756
757 void
758 expand_builtin_setjmp_receiver (rtx receiver_label ATTRIBUTE_UNUSED)
759 {
760 rtx chain;
761
762 /* Clobber the FP when we get here, so we have to make sure it's
763 marked as used by this function. */
764 emit_use (hard_frame_pointer_rtx);
765
766 /* Mark the static chain as clobbered here so life information
767 doesn't get messed up for it. */
768 chain = targetm.calls.static_chain (current_function_decl, true);
769 if (chain && REG_P (chain))
770 emit_clobber (chain);
771
772 /* Now put in the code to restore the frame pointer, and argument
773 pointer, if needed. */
774 #ifdef HAVE_nonlocal_goto
775 if (! HAVE_nonlocal_goto)
776 #endif
777 {
778 emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
779 /* This might change the hard frame pointer in ways that aren't
780 apparent to early optimization passes, so force a clobber. */
781 emit_clobber (hard_frame_pointer_rtx);
782 }
783
784 #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM
785 if (fixed_regs[ARG_POINTER_REGNUM])
786 {
787 #ifdef ELIMINABLE_REGS
788 size_t i;
789 static const struct elims {const int from, to;} elim_regs[] = ELIMINABLE_REGS;
790
791 for (i = 0; i < ARRAY_SIZE (elim_regs); i++)
792 if (elim_regs[i].from == ARG_POINTER_REGNUM
793 && elim_regs[i].to == HARD_FRAME_POINTER_REGNUM)
794 break;
795
796 if (i == ARRAY_SIZE (elim_regs))
797 #endif
798 {
799 /* Now restore our arg pointer from the address at which it
800 was saved in our stack frame. */
801 emit_move_insn (crtl->args.internal_arg_pointer,
802 copy_to_reg (get_arg_pointer_save_area ()));
803 }
804 }
805 #endif
806
807 #ifdef HAVE_builtin_setjmp_receiver
808 if (HAVE_builtin_setjmp_receiver)
809 emit_insn (gen_builtin_setjmp_receiver (receiver_label));
810 else
811 #endif
812 #ifdef HAVE_nonlocal_goto_receiver
813 if (HAVE_nonlocal_goto_receiver)
814 emit_insn (gen_nonlocal_goto_receiver ());
815 else
816 #endif
817 { /* Nothing */ }
818
819 /* We must not allow the code we just generated to be reordered by
820 scheduling. Specifically, the update of the frame pointer must
821 happen immediately, not later. */
822 emit_insn (gen_blockage ());
823 }
824
825 /* __builtin_longjmp is passed a pointer to an array of five words (not
826 all will be used on all machines). It operates similarly to the C
827 library function of the same name, but is more efficient. Much of
828 the code below is copied from the handling of non-local gotos. */
829
830 static void
831 expand_builtin_longjmp (rtx buf_addr, rtx value)
832 {
833 rtx fp, lab, stack, insn, last;
834 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
835
836 /* DRAP is needed for stack realign if longjmp is expanded to current
837 function */
838 if (SUPPORTS_STACK_ALIGNMENT)
839 crtl->need_drap = true;
840
841 if (setjmp_alias_set == -1)
842 setjmp_alias_set = new_alias_set ();
843
844 buf_addr = convert_memory_address (Pmode, buf_addr);
845
846 buf_addr = force_reg (Pmode, buf_addr);
847
848 /* We require that the user must pass a second argument of 1, because
849 that is what builtin_setjmp will return. */
850 gcc_assert (value == const1_rtx);
851
852 last = get_last_insn ();
853 #ifdef HAVE_builtin_longjmp
854 if (HAVE_builtin_longjmp)
855 emit_insn (gen_builtin_longjmp (buf_addr));
856 else
857 #endif
858 {
859 fp = gen_rtx_MEM (Pmode, buf_addr);
860 lab = gen_rtx_MEM (Pmode, plus_constant (buf_addr,
861 GET_MODE_SIZE (Pmode)));
862
863 stack = gen_rtx_MEM (sa_mode, plus_constant (buf_addr,
864 2 * GET_MODE_SIZE (Pmode)));
865 set_mem_alias_set (fp, setjmp_alias_set);
866 set_mem_alias_set (lab, setjmp_alias_set);
867 set_mem_alias_set (stack, setjmp_alias_set);
868
869 /* Pick up FP, label, and SP from the block and jump. This code is
870 from expand_goto in stmt.c; see there for detailed comments. */
871 #ifdef HAVE_nonlocal_goto
872 if (HAVE_nonlocal_goto)
873 /* We have to pass a value to the nonlocal_goto pattern that will
874 get copied into the static_chain pointer, but it does not matter
875 what that value is, because builtin_setjmp does not use it. */
876 emit_insn (gen_nonlocal_goto (value, lab, stack, fp));
877 else
878 #endif
879 {
880 lab = copy_to_reg (lab);
881
882 emit_clobber (gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode)));
883 emit_clobber (gen_rtx_MEM (BLKmode, hard_frame_pointer_rtx));
884
885 emit_move_insn (hard_frame_pointer_rtx, fp);
886 emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
887
888 emit_use (hard_frame_pointer_rtx);
889 emit_use (stack_pointer_rtx);
890 emit_indirect_jump (lab);
891 }
892 }
893
894 /* Search backwards and mark the jump insn as a non-local goto.
895 Note that this precludes the use of __builtin_longjmp to a
896 __builtin_setjmp target in the same function. However, we've
897 already cautioned the user that these functions are for
898 internal exception handling use only. */
899 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
900 {
901 gcc_assert (insn != last);
902
903 if (JUMP_P (insn))
904 {
905 add_reg_note (insn, REG_NON_LOCAL_GOTO, const0_rtx);
906 break;
907 }
908 else if (CALL_P (insn))
909 break;
910 }
911 }
912
913 /* Expand a call to __builtin_nonlocal_goto. We're passed the target label
914 and the address of the save area. */
915
916 static rtx
917 expand_builtin_nonlocal_goto (tree exp)
918 {
919 tree t_label, t_save_area;
920 rtx r_label, r_save_area, r_fp, r_sp, insn;
921
922 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
923 return NULL_RTX;
924
925 t_label = CALL_EXPR_ARG (exp, 0);
926 t_save_area = CALL_EXPR_ARG (exp, 1);
927
928 r_label = expand_normal (t_label);
929 r_label = convert_memory_address (Pmode, r_label);
930 r_save_area = expand_normal (t_save_area);
931 r_save_area = convert_memory_address (Pmode, r_save_area);
932 /* Copy the address of the save location to a register just in case it was based
933 on the frame pointer. */
934 r_save_area = copy_to_reg (r_save_area);
935 r_fp = gen_rtx_MEM (Pmode, r_save_area);
936 r_sp = gen_rtx_MEM (STACK_SAVEAREA_MODE (SAVE_NONLOCAL),
937 plus_constant (r_save_area, GET_MODE_SIZE (Pmode)));
938
939 crtl->has_nonlocal_goto = 1;
940
941 #ifdef HAVE_nonlocal_goto
942 /* ??? We no longer need to pass the static chain value, afaik. */
943 if (HAVE_nonlocal_goto)
944 emit_insn (gen_nonlocal_goto (const0_rtx, r_label, r_sp, r_fp));
945 else
946 #endif
947 {
948 r_label = copy_to_reg (r_label);
949
950 emit_clobber (gen_rtx_MEM (BLKmode, gen_rtx_SCRATCH (VOIDmode)));
951 emit_clobber (gen_rtx_MEM (BLKmode, hard_frame_pointer_rtx));
952
953 /* Restore frame pointer for containing function.
954 This sets the actual hard register used for the frame pointer
955 to the location of the function's incoming static chain info.
956 The non-local goto handler will then adjust it to contain the
957 proper value and reload the argument pointer, if needed. */
958 emit_move_insn (hard_frame_pointer_rtx, r_fp);
959 emit_stack_restore (SAVE_NONLOCAL, r_sp, NULL_RTX);
960
961 /* USE of hard_frame_pointer_rtx added for consistency;
962 not clear if really needed. */
963 emit_use (hard_frame_pointer_rtx);
964 emit_use (stack_pointer_rtx);
965
966 /* If the architecture is using a GP register, we must
967 conservatively assume that the target function makes use of it.
968 The prologue of functions with nonlocal gotos must therefore
969 initialize the GP register to the appropriate value, and we
970 must then make sure that this value is live at the point
971 of the jump. (Note that this doesn't necessarily apply
972 to targets with a nonlocal_goto pattern; they are free
973 to implement it in their own way. Note also that this is
974 a no-op if the GP register is a global invariant.) */
975 if ((unsigned) PIC_OFFSET_TABLE_REGNUM != INVALID_REGNUM
976 && fixed_regs[PIC_OFFSET_TABLE_REGNUM])
977 emit_use (pic_offset_table_rtx);
978
979 emit_indirect_jump (r_label);
980 }
981
982 /* Search backwards to the jump insn and mark it as a
983 non-local goto. */
984 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
985 {
986 if (JUMP_P (insn))
987 {
988 add_reg_note (insn, REG_NON_LOCAL_GOTO, const0_rtx);
989 break;
990 }
991 else if (CALL_P (insn))
992 break;
993 }
994
995 return const0_rtx;
996 }
997
998 /* __builtin_update_setjmp_buf is passed a pointer to an array of five words
999 (not all will be used on all machines) that was passed to __builtin_setjmp.
1000 It updates the stack pointer in that block to correspond to the current
1001 stack pointer. */
1002
1003 static void
1004 expand_builtin_update_setjmp_buf (rtx buf_addr)
1005 {
1006 enum machine_mode sa_mode = Pmode;
1007 rtx stack_save;
1008
1009
1010 #ifdef HAVE_save_stack_nonlocal
1011 if (HAVE_save_stack_nonlocal)
1012 sa_mode = insn_data[(int) CODE_FOR_save_stack_nonlocal].operand[0].mode;
1013 #endif
1014 #ifdef STACK_SAVEAREA_MODE
1015 sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
1016 #endif
1017
1018 stack_save
1019 = gen_rtx_MEM (sa_mode,
1020 memory_address
1021 (sa_mode,
1022 plus_constant (buf_addr, 2 * GET_MODE_SIZE (Pmode))));
1023
1024 #ifdef HAVE_setjmp
1025 if (HAVE_setjmp)
1026 emit_insn (gen_setjmp ());
1027 #endif
1028
1029 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
1030 }
1031
1032 /* Expand a call to __builtin_prefetch. For a target that does not support
1033 data prefetch, evaluate the memory address argument in case it has side
1034 effects. */
1035
1036 static void
1037 expand_builtin_prefetch (tree exp)
1038 {
1039 tree arg0, arg1, arg2;
1040 int nargs;
1041 rtx op0, op1, op2;
1042
1043 if (!validate_arglist (exp, POINTER_TYPE, 0))
1044 return;
1045
1046 arg0 = CALL_EXPR_ARG (exp, 0);
1047
1048 /* Arguments 1 and 2 are optional; argument 1 (read/write) defaults to
1049 zero (read) and argument 2 (locality) defaults to 3 (high degree of
1050 locality). */
1051 nargs = call_expr_nargs (exp);
1052 if (nargs > 1)
1053 arg1 = CALL_EXPR_ARG (exp, 1);
1054 else
1055 arg1 = integer_zero_node;
1056 if (nargs > 2)
1057 arg2 = CALL_EXPR_ARG (exp, 2);
1058 else
1059 arg2 = build_int_cst (NULL_TREE, 3);
1060
1061 /* Argument 0 is an address. */
1062 op0 = expand_expr (arg0, NULL_RTX, Pmode, EXPAND_NORMAL);
1063
1064 /* Argument 1 (read/write flag) must be a compile-time constant int. */
1065 if (TREE_CODE (arg1) != INTEGER_CST)
1066 {
1067 error ("second argument to %<__builtin_prefetch%> must be a constant");
1068 arg1 = integer_zero_node;
1069 }
1070 op1 = expand_normal (arg1);
1071 /* Argument 1 must be either zero or one. */
1072 if (INTVAL (op1) != 0 && INTVAL (op1) != 1)
1073 {
1074 warning (0, "invalid second argument to %<__builtin_prefetch%>;"
1075 " using zero");
1076 op1 = const0_rtx;
1077 }
1078
1079 /* Argument 2 (locality) must be a compile-time constant int. */
1080 if (TREE_CODE (arg2) != INTEGER_CST)
1081 {
1082 error ("third argument to %<__builtin_prefetch%> must be a constant");
1083 arg2 = integer_zero_node;
1084 }
1085 op2 = expand_normal (arg2);
1086 /* Argument 2 must be 0, 1, 2, or 3. */
1087 if (INTVAL (op2) < 0 || INTVAL (op2) > 3)
1088 {
1089 warning (0, "invalid third argument to %<__builtin_prefetch%>; using zero");
1090 op2 = const0_rtx;
1091 }
1092
1093 #ifdef HAVE_prefetch
1094 if (HAVE_prefetch)
1095 {
1096 if ((! (*insn_data[(int) CODE_FOR_prefetch].operand[0].predicate)
1097 (op0,
1098 insn_data[(int) CODE_FOR_prefetch].operand[0].mode))
1099 || (GET_MODE (op0) != Pmode))
1100 {
1101 op0 = convert_memory_address (Pmode, op0);
1102 op0 = force_reg (Pmode, op0);
1103 }
1104 emit_insn (gen_prefetch (op0, op1, op2));
1105 }
1106 #endif
1107
1108 /* Don't do anything with direct references to volatile memory, but
1109 generate code to handle other side effects. */
1110 if (!MEM_P (op0) && side_effects_p (op0))
1111 emit_insn (op0);
1112 }
1113
1114 /* Get a MEM rtx for expression EXP which is the address of an operand
1115 to be used in a string instruction (cmpstrsi, movmemsi, ..). LEN is
1116 the maximum length of the block of memory that might be accessed or
1117 NULL if unknown. */
1118
1119 static rtx
1120 get_memory_rtx (tree exp, tree len)
1121 {
1122 tree orig_exp = exp;
1123 rtx addr, mem;
1124 HOST_WIDE_INT off;
1125
1126 /* When EXP is not resolved SAVE_EXPR, MEM_ATTRS can be still derived
1127 from its expression, for expr->a.b only <variable>.a.b is recorded. */
1128 if (TREE_CODE (exp) == SAVE_EXPR && !SAVE_EXPR_RESOLVED_P (exp))
1129 exp = TREE_OPERAND (exp, 0);
1130
1131 addr = expand_expr (orig_exp, NULL_RTX, ptr_mode, EXPAND_NORMAL);
1132 mem = gen_rtx_MEM (BLKmode, memory_address (BLKmode, addr));
1133
1134 /* Get an expression we can use to find the attributes to assign to MEM.
1135 If it is an ADDR_EXPR, use the operand. Otherwise, dereference it if
1136 we can. First remove any nops. */
1137 while (CONVERT_EXPR_P (exp)
1138 && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (exp, 0))))
1139 exp = TREE_OPERAND (exp, 0);
1140
1141 off = 0;
1142 if (TREE_CODE (exp) == POINTER_PLUS_EXPR
1143 && TREE_CODE (TREE_OPERAND (exp, 0)) == ADDR_EXPR
1144 && host_integerp (TREE_OPERAND (exp, 1), 0)
1145 && (off = tree_low_cst (TREE_OPERAND (exp, 1), 0)) > 0)
1146 exp = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
1147 else if (TREE_CODE (exp) == ADDR_EXPR)
1148 exp = TREE_OPERAND (exp, 0);
1149 else if (POINTER_TYPE_P (TREE_TYPE (exp)))
1150 exp = build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (exp)), exp);
1151 else
1152 exp = NULL;
1153
1154 /* Honor attributes derived from exp, except for the alias set
1155 (as builtin stringops may alias with anything) and the size
1156 (as stringops may access multiple array elements). */
1157 if (exp)
1158 {
1159 set_mem_attributes (mem, exp, 0);
1160
1161 if (off)
1162 mem = adjust_automodify_address_nv (mem, BLKmode, NULL, off);
1163
1164 /* Allow the string and memory builtins to overflow from one
1165 field into another, see http://gcc.gnu.org/PR23561.
1166 Thus avoid COMPONENT_REFs in MEM_EXPR unless we know the whole
1167 memory accessed by the string or memory builtin will fit
1168 within the field. */
1169 if (MEM_EXPR (mem) && TREE_CODE (MEM_EXPR (mem)) == COMPONENT_REF)
1170 {
1171 tree mem_expr = MEM_EXPR (mem);
1172 HOST_WIDE_INT offset = -1, length = -1;
1173 tree inner = exp;
1174
1175 while (TREE_CODE (inner) == ARRAY_REF
1176 || CONVERT_EXPR_P (inner)
1177 || TREE_CODE (inner) == VIEW_CONVERT_EXPR
1178 || TREE_CODE (inner) == SAVE_EXPR)
1179 inner = TREE_OPERAND (inner, 0);
1180
1181 gcc_assert (TREE_CODE (inner) == COMPONENT_REF);
1182
1183 if (MEM_OFFSET (mem)
1184 && CONST_INT_P (MEM_OFFSET (mem)))
1185 offset = INTVAL (MEM_OFFSET (mem));
1186
1187 if (offset >= 0 && len && host_integerp (len, 0))
1188 length = tree_low_cst (len, 0);
1189
1190 while (TREE_CODE (inner) == COMPONENT_REF)
1191 {
1192 tree field = TREE_OPERAND (inner, 1);
1193 gcc_assert (TREE_CODE (mem_expr) == COMPONENT_REF);
1194 gcc_assert (field == TREE_OPERAND (mem_expr, 1));
1195
1196 /* Bitfields are generally not byte-addressable. */
1197 gcc_assert (!DECL_BIT_FIELD (field)
1198 || ((tree_low_cst (DECL_FIELD_BIT_OFFSET (field), 1)
1199 % BITS_PER_UNIT) == 0
1200 && host_integerp (DECL_SIZE (field), 0)
1201 && (TREE_INT_CST_LOW (DECL_SIZE (field))
1202 % BITS_PER_UNIT) == 0));
1203
1204 /* If we can prove that the memory starting at XEXP (mem, 0) and
1205 ending at XEXP (mem, 0) + LENGTH will fit into this field, we
1206 can keep the COMPONENT_REF in MEM_EXPR. But be careful with
1207 fields without DECL_SIZE_UNIT like flexible array members. */
1208 if (length >= 0
1209 && DECL_SIZE_UNIT (field)
1210 && host_integerp (DECL_SIZE_UNIT (field), 0))
1211 {
1212 HOST_WIDE_INT size
1213 = TREE_INT_CST_LOW (DECL_SIZE_UNIT (field));
1214 if (offset <= size
1215 && length <= size
1216 && offset + length <= size)
1217 break;
1218 }
1219
1220 if (offset >= 0
1221 && host_integerp (DECL_FIELD_OFFSET (field), 0))
1222 offset += TREE_INT_CST_LOW (DECL_FIELD_OFFSET (field))
1223 + tree_low_cst (DECL_FIELD_BIT_OFFSET (field), 1)
1224 / BITS_PER_UNIT;
1225 else
1226 {
1227 offset = -1;
1228 length = -1;
1229 }
1230
1231 mem_expr = TREE_OPERAND (mem_expr, 0);
1232 inner = TREE_OPERAND (inner, 0);
1233 }
1234
1235 if (mem_expr == NULL)
1236 offset = -1;
1237 if (mem_expr != MEM_EXPR (mem))
1238 {
1239 set_mem_expr (mem, mem_expr);
1240 set_mem_offset (mem, offset >= 0 ? GEN_INT (offset) : NULL_RTX);
1241 }
1242 }
1243 set_mem_alias_set (mem, 0);
1244 set_mem_size (mem, NULL_RTX);
1245 }
1246
1247 return mem;
1248 }
1249 \f
1250 /* Built-in functions to perform an untyped call and return. */
1251
1252 /* For each register that may be used for calling a function, this
1253 gives a mode used to copy the register's value. VOIDmode indicates
1254 the register is not used for calling a function. If the machine
1255 has register windows, this gives only the outbound registers.
1256 INCOMING_REGNO gives the corresponding inbound register. */
1257 static enum machine_mode apply_args_mode[FIRST_PSEUDO_REGISTER];
1258
1259 /* For each register that may be used for returning values, this gives
1260 a mode used to copy the register's value. VOIDmode indicates the
1261 register is not used for returning values. If the machine has
1262 register windows, this gives only the outbound registers.
1263 INCOMING_REGNO gives the corresponding inbound register. */
1264 static enum machine_mode apply_result_mode[FIRST_PSEUDO_REGISTER];
1265
1266 /* Return the size required for the block returned by __builtin_apply_args,
1267 and initialize apply_args_mode. */
1268
1269 static int
1270 apply_args_size (void)
1271 {
1272 static int size = -1;
1273 int align;
1274 unsigned int regno;
1275 enum machine_mode mode;
1276
1277 /* The values computed by this function never change. */
1278 if (size < 0)
1279 {
1280 /* The first value is the incoming arg-pointer. */
1281 size = GET_MODE_SIZE (Pmode);
1282
1283 /* The second value is the structure value address unless this is
1284 passed as an "invisible" first argument. */
1285 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1286 size += GET_MODE_SIZE (Pmode);
1287
1288 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1289 if (FUNCTION_ARG_REGNO_P (regno))
1290 {
1291 mode = reg_raw_mode[regno];
1292
1293 gcc_assert (mode != VOIDmode);
1294
1295 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1296 if (size % align != 0)
1297 size = CEIL (size, align) * align;
1298 size += GET_MODE_SIZE (mode);
1299 apply_args_mode[regno] = mode;
1300 }
1301 else
1302 {
1303 apply_args_mode[regno] = VOIDmode;
1304 }
1305 }
1306 return size;
1307 }
1308
1309 /* Return the size required for the block returned by __builtin_apply,
1310 and initialize apply_result_mode. */
1311
1312 static int
1313 apply_result_size (void)
1314 {
1315 static int size = -1;
1316 int align, regno;
1317 enum machine_mode mode;
1318
1319 /* The values computed by this function never change. */
1320 if (size < 0)
1321 {
1322 size = 0;
1323
1324 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1325 if (targetm.calls.function_value_regno_p (regno))
1326 {
1327 mode = reg_raw_mode[regno];
1328
1329 gcc_assert (mode != VOIDmode);
1330
1331 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1332 if (size % align != 0)
1333 size = CEIL (size, align) * align;
1334 size += GET_MODE_SIZE (mode);
1335 apply_result_mode[regno] = mode;
1336 }
1337 else
1338 apply_result_mode[regno] = VOIDmode;
1339
1340 /* Allow targets that use untyped_call and untyped_return to override
1341 the size so that machine-specific information can be stored here. */
1342 #ifdef APPLY_RESULT_SIZE
1343 size = APPLY_RESULT_SIZE;
1344 #endif
1345 }
1346 return size;
1347 }
1348
1349 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
1350 /* Create a vector describing the result block RESULT. If SAVEP is true,
1351 the result block is used to save the values; otherwise it is used to
1352 restore the values. */
1353
1354 static rtx
1355 result_vector (int savep, rtx result)
1356 {
1357 int regno, size, align, nelts;
1358 enum machine_mode mode;
1359 rtx reg, mem;
1360 rtx *savevec = XALLOCAVEC (rtx, FIRST_PSEUDO_REGISTER);
1361
1362 size = nelts = 0;
1363 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1364 if ((mode = apply_result_mode[regno]) != VOIDmode)
1365 {
1366 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1367 if (size % align != 0)
1368 size = CEIL (size, align) * align;
1369 reg = gen_rtx_REG (mode, savep ? regno : INCOMING_REGNO (regno));
1370 mem = adjust_address (result, mode, size);
1371 savevec[nelts++] = (savep
1372 ? gen_rtx_SET (VOIDmode, mem, reg)
1373 : gen_rtx_SET (VOIDmode, reg, mem));
1374 size += GET_MODE_SIZE (mode);
1375 }
1376 return gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (nelts, savevec));
1377 }
1378 #endif /* HAVE_untyped_call or HAVE_untyped_return */
1379
1380 /* Save the state required to perform an untyped call with the same
1381 arguments as were passed to the current function. */
1382
1383 static rtx
1384 expand_builtin_apply_args_1 (void)
1385 {
1386 rtx registers, tem;
1387 int size, align, regno;
1388 enum machine_mode mode;
1389 rtx struct_incoming_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 1);
1390
1391 /* Create a block where the arg-pointer, structure value address,
1392 and argument registers can be saved. */
1393 registers = assign_stack_local (BLKmode, apply_args_size (), -1);
1394
1395 /* Walk past the arg-pointer and structure value address. */
1396 size = GET_MODE_SIZE (Pmode);
1397 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1398 size += GET_MODE_SIZE (Pmode);
1399
1400 /* Save each register used in calling a function to the block. */
1401 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1402 if ((mode = apply_args_mode[regno]) != VOIDmode)
1403 {
1404 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1405 if (size % align != 0)
1406 size = CEIL (size, align) * align;
1407
1408 tem = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1409
1410 emit_move_insn (adjust_address (registers, mode, size), tem);
1411 size += GET_MODE_SIZE (mode);
1412 }
1413
1414 /* Save the arg pointer to the block. */
1415 tem = copy_to_reg (crtl->args.internal_arg_pointer);
1416 #ifdef STACK_GROWS_DOWNWARD
1417 /* We need the pointer as the caller actually passed them to us, not
1418 as we might have pretended they were passed. Make sure it's a valid
1419 operand, as emit_move_insn isn't expected to handle a PLUS. */
1420 tem
1421 = force_operand (plus_constant (tem, crtl->args.pretend_args_size),
1422 NULL_RTX);
1423 #endif
1424 emit_move_insn (adjust_address (registers, Pmode, 0), tem);
1425
1426 size = GET_MODE_SIZE (Pmode);
1427
1428 /* Save the structure value address unless this is passed as an
1429 "invisible" first argument. */
1430 if (struct_incoming_value)
1431 {
1432 emit_move_insn (adjust_address (registers, Pmode, size),
1433 copy_to_reg (struct_incoming_value));
1434 size += GET_MODE_SIZE (Pmode);
1435 }
1436
1437 /* Return the address of the block. */
1438 return copy_addr_to_reg (XEXP (registers, 0));
1439 }
1440
1441 /* __builtin_apply_args returns block of memory allocated on
1442 the stack into which is stored the arg pointer, structure
1443 value address, static chain, and all the registers that might
1444 possibly be used in performing a function call. The code is
1445 moved to the start of the function so the incoming values are
1446 saved. */
1447
1448 static rtx
1449 expand_builtin_apply_args (void)
1450 {
1451 /* Don't do __builtin_apply_args more than once in a function.
1452 Save the result of the first call and reuse it. */
1453 if (apply_args_value != 0)
1454 return apply_args_value;
1455 {
1456 /* When this function is called, it means that registers must be
1457 saved on entry to this function. So we migrate the
1458 call to the first insn of this function. */
1459 rtx temp;
1460 rtx seq;
1461
1462 start_sequence ();
1463 temp = expand_builtin_apply_args_1 ();
1464 seq = get_insns ();
1465 end_sequence ();
1466
1467 apply_args_value = temp;
1468
1469 /* Put the insns after the NOTE that starts the function.
1470 If this is inside a start_sequence, make the outer-level insn
1471 chain current, so the code is placed at the start of the
1472 function. If internal_arg_pointer is a non-virtual pseudo,
1473 it needs to be placed after the function that initializes
1474 that pseudo. */
1475 push_topmost_sequence ();
1476 if (REG_P (crtl->args.internal_arg_pointer)
1477 && REGNO (crtl->args.internal_arg_pointer) > LAST_VIRTUAL_REGISTER)
1478 emit_insn_before (seq, parm_birth_insn);
1479 else
1480 emit_insn_before (seq, NEXT_INSN (entry_of_function ()));
1481 pop_topmost_sequence ();
1482 return temp;
1483 }
1484 }
1485
1486 /* Perform an untyped call and save the state required to perform an
1487 untyped return of whatever value was returned by the given function. */
1488
1489 static rtx
1490 expand_builtin_apply (rtx function, rtx arguments, rtx argsize)
1491 {
1492 int size, align, regno;
1493 enum machine_mode mode;
1494 rtx incoming_args, result, reg, dest, src, call_insn;
1495 rtx old_stack_level = 0;
1496 rtx call_fusage = 0;
1497 rtx struct_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0);
1498
1499 arguments = convert_memory_address (Pmode, arguments);
1500
1501 /* Create a block where the return registers can be saved. */
1502 result = assign_stack_local (BLKmode, apply_result_size (), -1);
1503
1504 /* Fetch the arg pointer from the ARGUMENTS block. */
1505 incoming_args = gen_reg_rtx (Pmode);
1506 emit_move_insn (incoming_args, gen_rtx_MEM (Pmode, arguments));
1507 #ifndef STACK_GROWS_DOWNWARD
1508 incoming_args = expand_simple_binop (Pmode, MINUS, incoming_args, argsize,
1509 incoming_args, 0, OPTAB_LIB_WIDEN);
1510 #endif
1511
1512 /* Push a new argument block and copy the arguments. Do not allow
1513 the (potential) memcpy call below to interfere with our stack
1514 manipulations. */
1515 do_pending_stack_adjust ();
1516 NO_DEFER_POP;
1517
1518 /* Save the stack with nonlocal if available. */
1519 #ifdef HAVE_save_stack_nonlocal
1520 if (HAVE_save_stack_nonlocal)
1521 emit_stack_save (SAVE_NONLOCAL, &old_stack_level, NULL_RTX);
1522 else
1523 #endif
1524 emit_stack_save (SAVE_BLOCK, &old_stack_level, NULL_RTX);
1525
1526 /* Allocate a block of memory onto the stack and copy the memory
1527 arguments to the outgoing arguments address. */
1528 allocate_dynamic_stack_space (argsize, 0, BITS_PER_UNIT);
1529
1530 /* Set DRAP flag to true, even though allocate_dynamic_stack_space
1531 may have already set current_function_calls_alloca to true.
1532 current_function_calls_alloca won't be set if argsize is zero,
1533 so we have to guarantee need_drap is true here. */
1534 if (SUPPORTS_STACK_ALIGNMENT)
1535 crtl->need_drap = true;
1536
1537 dest = virtual_outgoing_args_rtx;
1538 #ifndef STACK_GROWS_DOWNWARD
1539 if (CONST_INT_P (argsize))
1540 dest = plus_constant (dest, -INTVAL (argsize));
1541 else
1542 dest = gen_rtx_PLUS (Pmode, dest, negate_rtx (Pmode, argsize));
1543 #endif
1544 dest = gen_rtx_MEM (BLKmode, dest);
1545 set_mem_align (dest, PARM_BOUNDARY);
1546 src = gen_rtx_MEM (BLKmode, incoming_args);
1547 set_mem_align (src, PARM_BOUNDARY);
1548 emit_block_move (dest, src, argsize, BLOCK_OP_NORMAL);
1549
1550 /* Refer to the argument block. */
1551 apply_args_size ();
1552 arguments = gen_rtx_MEM (BLKmode, arguments);
1553 set_mem_align (arguments, PARM_BOUNDARY);
1554
1555 /* Walk past the arg-pointer and structure value address. */
1556 size = GET_MODE_SIZE (Pmode);
1557 if (struct_value)
1558 size += GET_MODE_SIZE (Pmode);
1559
1560 /* Restore each of the registers previously saved. Make USE insns
1561 for each of these registers for use in making the call. */
1562 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1563 if ((mode = apply_args_mode[regno]) != VOIDmode)
1564 {
1565 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1566 if (size % align != 0)
1567 size = CEIL (size, align) * align;
1568 reg = gen_rtx_REG (mode, regno);
1569 emit_move_insn (reg, adjust_address (arguments, mode, size));
1570 use_reg (&call_fusage, reg);
1571 size += GET_MODE_SIZE (mode);
1572 }
1573
1574 /* Restore the structure value address unless this is passed as an
1575 "invisible" first argument. */
1576 size = GET_MODE_SIZE (Pmode);
1577 if (struct_value)
1578 {
1579 rtx value = gen_reg_rtx (Pmode);
1580 emit_move_insn (value, adjust_address (arguments, Pmode, size));
1581 emit_move_insn (struct_value, value);
1582 if (REG_P (struct_value))
1583 use_reg (&call_fusage, struct_value);
1584 size += GET_MODE_SIZE (Pmode);
1585 }
1586
1587 /* All arguments and registers used for the call are set up by now! */
1588 function = prepare_call_address (NULL, function, NULL, &call_fusage, 0, 0);
1589
1590 /* Ensure address is valid. SYMBOL_REF is already valid, so no need,
1591 and we don't want to load it into a register as an optimization,
1592 because prepare_call_address already did it if it should be done. */
1593 if (GET_CODE (function) != SYMBOL_REF)
1594 function = memory_address (FUNCTION_MODE, function);
1595
1596 /* Generate the actual call instruction and save the return value. */
1597 #ifdef HAVE_untyped_call
1598 if (HAVE_untyped_call)
1599 emit_call_insn (gen_untyped_call (gen_rtx_MEM (FUNCTION_MODE, function),
1600 result, result_vector (1, result)));
1601 else
1602 #endif
1603 #ifdef HAVE_call_value
1604 if (HAVE_call_value)
1605 {
1606 rtx valreg = 0;
1607
1608 /* Locate the unique return register. It is not possible to
1609 express a call that sets more than one return register using
1610 call_value; use untyped_call for that. In fact, untyped_call
1611 only needs to save the return registers in the given block. */
1612 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1613 if ((mode = apply_result_mode[regno]) != VOIDmode)
1614 {
1615 gcc_assert (!valreg); /* HAVE_untyped_call required. */
1616
1617 valreg = gen_rtx_REG (mode, regno);
1618 }
1619
1620 emit_call_insn (GEN_CALL_VALUE (valreg,
1621 gen_rtx_MEM (FUNCTION_MODE, function),
1622 const0_rtx, NULL_RTX, const0_rtx));
1623
1624 emit_move_insn (adjust_address (result, GET_MODE (valreg), 0), valreg);
1625 }
1626 else
1627 #endif
1628 gcc_unreachable ();
1629
1630 /* Find the CALL insn we just emitted, and attach the register usage
1631 information. */
1632 call_insn = last_call_insn ();
1633 add_function_usage_to (call_insn, call_fusage);
1634
1635 /* Restore the stack. */
1636 #ifdef HAVE_save_stack_nonlocal
1637 if (HAVE_save_stack_nonlocal)
1638 emit_stack_restore (SAVE_NONLOCAL, old_stack_level, NULL_RTX);
1639 else
1640 #endif
1641 emit_stack_restore (SAVE_BLOCK, old_stack_level, NULL_RTX);
1642
1643 OK_DEFER_POP;
1644
1645 /* Return the address of the result block. */
1646 result = copy_addr_to_reg (XEXP (result, 0));
1647 return convert_memory_address (ptr_mode, result);
1648 }
1649
1650 /* Perform an untyped return. */
1651
1652 static void
1653 expand_builtin_return (rtx result)
1654 {
1655 int size, align, regno;
1656 enum machine_mode mode;
1657 rtx reg;
1658 rtx call_fusage = 0;
1659
1660 result = convert_memory_address (Pmode, result);
1661
1662 apply_result_size ();
1663 result = gen_rtx_MEM (BLKmode, result);
1664
1665 #ifdef HAVE_untyped_return
1666 if (HAVE_untyped_return)
1667 {
1668 emit_jump_insn (gen_untyped_return (result, result_vector (0, result)));
1669 emit_barrier ();
1670 return;
1671 }
1672 #endif
1673
1674 /* Restore the return value and note that each value is used. */
1675 size = 0;
1676 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1677 if ((mode = apply_result_mode[regno]) != VOIDmode)
1678 {
1679 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1680 if (size % align != 0)
1681 size = CEIL (size, align) * align;
1682 reg = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1683 emit_move_insn (reg, adjust_address (result, mode, size));
1684
1685 push_to_sequence (call_fusage);
1686 emit_use (reg);
1687 call_fusage = get_insns ();
1688 end_sequence ();
1689 size += GET_MODE_SIZE (mode);
1690 }
1691
1692 /* Put the USE insns before the return. */
1693 emit_insn (call_fusage);
1694
1695 /* Return whatever values was restored by jumping directly to the end
1696 of the function. */
1697 expand_naked_return ();
1698 }
1699
1700 /* Used by expand_builtin_classify_type and fold_builtin_classify_type. */
1701
1702 static enum type_class
1703 type_to_class (tree type)
1704 {
1705 switch (TREE_CODE (type))
1706 {
1707 case VOID_TYPE: return void_type_class;
1708 case INTEGER_TYPE: return integer_type_class;
1709 case ENUMERAL_TYPE: return enumeral_type_class;
1710 case BOOLEAN_TYPE: return boolean_type_class;
1711 case POINTER_TYPE: return pointer_type_class;
1712 case REFERENCE_TYPE: return reference_type_class;
1713 case OFFSET_TYPE: return offset_type_class;
1714 case REAL_TYPE: return real_type_class;
1715 case COMPLEX_TYPE: return complex_type_class;
1716 case FUNCTION_TYPE: return function_type_class;
1717 case METHOD_TYPE: return method_type_class;
1718 case RECORD_TYPE: return record_type_class;
1719 case UNION_TYPE:
1720 case QUAL_UNION_TYPE: return union_type_class;
1721 case ARRAY_TYPE: return (TYPE_STRING_FLAG (type)
1722 ? string_type_class : array_type_class);
1723 case LANG_TYPE: return lang_type_class;
1724 default: return no_type_class;
1725 }
1726 }
1727
1728 /* Expand a call EXP to __builtin_classify_type. */
1729
1730 static rtx
1731 expand_builtin_classify_type (tree exp)
1732 {
1733 if (call_expr_nargs (exp))
1734 return GEN_INT (type_to_class (TREE_TYPE (CALL_EXPR_ARG (exp, 0))));
1735 return GEN_INT (no_type_class);
1736 }
1737
1738 /* This helper macro, meant to be used in mathfn_built_in below,
1739 determines which among a set of three builtin math functions is
1740 appropriate for a given type mode. The `F' and `L' cases are
1741 automatically generated from the `double' case. */
1742 #define CASE_MATHFN(BUILT_IN_MATHFN) \
1743 case BUILT_IN_MATHFN: case BUILT_IN_MATHFN##F: case BUILT_IN_MATHFN##L: \
1744 fcode = BUILT_IN_MATHFN; fcodef = BUILT_IN_MATHFN##F ; \
1745 fcodel = BUILT_IN_MATHFN##L ; break;
1746 /* Similar to above, but appends _R after any F/L suffix. */
1747 #define CASE_MATHFN_REENT(BUILT_IN_MATHFN) \
1748 case BUILT_IN_MATHFN##_R: case BUILT_IN_MATHFN##F_R: case BUILT_IN_MATHFN##L_R: \
1749 fcode = BUILT_IN_MATHFN##_R; fcodef = BUILT_IN_MATHFN##F_R ; \
1750 fcodel = BUILT_IN_MATHFN##L_R ; break;
1751
1752 /* Return mathematic function equivalent to FN but operating directly
1753 on TYPE, if available. If IMPLICIT is true find the function in
1754 implicit_built_in_decls[], otherwise use built_in_decls[]. If we
1755 can't do the conversion, return zero. */
1756
1757 static tree
1758 mathfn_built_in_1 (tree type, enum built_in_function fn, bool implicit)
1759 {
1760 tree const *const fn_arr
1761 = implicit ? implicit_built_in_decls : built_in_decls;
1762 enum built_in_function fcode, fcodef, fcodel;
1763
1764 switch (fn)
1765 {
1766 CASE_MATHFN (BUILT_IN_ACOS)
1767 CASE_MATHFN (BUILT_IN_ACOSH)
1768 CASE_MATHFN (BUILT_IN_ASIN)
1769 CASE_MATHFN (BUILT_IN_ASINH)
1770 CASE_MATHFN (BUILT_IN_ATAN)
1771 CASE_MATHFN (BUILT_IN_ATAN2)
1772 CASE_MATHFN (BUILT_IN_ATANH)
1773 CASE_MATHFN (BUILT_IN_CBRT)
1774 CASE_MATHFN (BUILT_IN_CEIL)
1775 CASE_MATHFN (BUILT_IN_CEXPI)
1776 CASE_MATHFN (BUILT_IN_COPYSIGN)
1777 CASE_MATHFN (BUILT_IN_COS)
1778 CASE_MATHFN (BUILT_IN_COSH)
1779 CASE_MATHFN (BUILT_IN_DREM)
1780 CASE_MATHFN (BUILT_IN_ERF)
1781 CASE_MATHFN (BUILT_IN_ERFC)
1782 CASE_MATHFN (BUILT_IN_EXP)
1783 CASE_MATHFN (BUILT_IN_EXP10)
1784 CASE_MATHFN (BUILT_IN_EXP2)
1785 CASE_MATHFN (BUILT_IN_EXPM1)
1786 CASE_MATHFN (BUILT_IN_FABS)
1787 CASE_MATHFN (BUILT_IN_FDIM)
1788 CASE_MATHFN (BUILT_IN_FLOOR)
1789 CASE_MATHFN (BUILT_IN_FMA)
1790 CASE_MATHFN (BUILT_IN_FMAX)
1791 CASE_MATHFN (BUILT_IN_FMIN)
1792 CASE_MATHFN (BUILT_IN_FMOD)
1793 CASE_MATHFN (BUILT_IN_FREXP)
1794 CASE_MATHFN (BUILT_IN_GAMMA)
1795 CASE_MATHFN_REENT (BUILT_IN_GAMMA) /* GAMMA_R */
1796 CASE_MATHFN (BUILT_IN_HUGE_VAL)
1797 CASE_MATHFN (BUILT_IN_HYPOT)
1798 CASE_MATHFN (BUILT_IN_ILOGB)
1799 CASE_MATHFN (BUILT_IN_INF)
1800 CASE_MATHFN (BUILT_IN_ISINF)
1801 CASE_MATHFN (BUILT_IN_J0)
1802 CASE_MATHFN (BUILT_IN_J1)
1803 CASE_MATHFN (BUILT_IN_JN)
1804 CASE_MATHFN (BUILT_IN_LCEIL)
1805 CASE_MATHFN (BUILT_IN_LDEXP)
1806 CASE_MATHFN (BUILT_IN_LFLOOR)
1807 CASE_MATHFN (BUILT_IN_LGAMMA)
1808 CASE_MATHFN_REENT (BUILT_IN_LGAMMA) /* LGAMMA_R */
1809 CASE_MATHFN (BUILT_IN_LLCEIL)
1810 CASE_MATHFN (BUILT_IN_LLFLOOR)
1811 CASE_MATHFN (BUILT_IN_LLRINT)
1812 CASE_MATHFN (BUILT_IN_LLROUND)
1813 CASE_MATHFN (BUILT_IN_LOG)
1814 CASE_MATHFN (BUILT_IN_LOG10)
1815 CASE_MATHFN (BUILT_IN_LOG1P)
1816 CASE_MATHFN (BUILT_IN_LOG2)
1817 CASE_MATHFN (BUILT_IN_LOGB)
1818 CASE_MATHFN (BUILT_IN_LRINT)
1819 CASE_MATHFN (BUILT_IN_LROUND)
1820 CASE_MATHFN (BUILT_IN_MODF)
1821 CASE_MATHFN (BUILT_IN_NAN)
1822 CASE_MATHFN (BUILT_IN_NANS)
1823 CASE_MATHFN (BUILT_IN_NEARBYINT)
1824 CASE_MATHFN (BUILT_IN_NEXTAFTER)
1825 CASE_MATHFN (BUILT_IN_NEXTTOWARD)
1826 CASE_MATHFN (BUILT_IN_POW)
1827 CASE_MATHFN (BUILT_IN_POWI)
1828 CASE_MATHFN (BUILT_IN_POW10)
1829 CASE_MATHFN (BUILT_IN_REMAINDER)
1830 CASE_MATHFN (BUILT_IN_REMQUO)
1831 CASE_MATHFN (BUILT_IN_RINT)
1832 CASE_MATHFN (BUILT_IN_ROUND)
1833 CASE_MATHFN (BUILT_IN_SCALB)
1834 CASE_MATHFN (BUILT_IN_SCALBLN)
1835 CASE_MATHFN (BUILT_IN_SCALBN)
1836 CASE_MATHFN (BUILT_IN_SIGNBIT)
1837 CASE_MATHFN (BUILT_IN_SIGNIFICAND)
1838 CASE_MATHFN (BUILT_IN_SIN)
1839 CASE_MATHFN (BUILT_IN_SINCOS)
1840 CASE_MATHFN (BUILT_IN_SINH)
1841 CASE_MATHFN (BUILT_IN_SQRT)
1842 CASE_MATHFN (BUILT_IN_TAN)
1843 CASE_MATHFN (BUILT_IN_TANH)
1844 CASE_MATHFN (BUILT_IN_TGAMMA)
1845 CASE_MATHFN (BUILT_IN_TRUNC)
1846 CASE_MATHFN (BUILT_IN_Y0)
1847 CASE_MATHFN (BUILT_IN_Y1)
1848 CASE_MATHFN (BUILT_IN_YN)
1849
1850 default:
1851 return NULL_TREE;
1852 }
1853
1854 if (TYPE_MAIN_VARIANT (type) == double_type_node)
1855 return fn_arr[fcode];
1856 else if (TYPE_MAIN_VARIANT (type) == float_type_node)
1857 return fn_arr[fcodef];
1858 else if (TYPE_MAIN_VARIANT (type) == long_double_type_node)
1859 return fn_arr[fcodel];
1860 else
1861 return NULL_TREE;
1862 }
1863
1864 /* Like mathfn_built_in_1(), but always use the implicit array. */
1865
1866 tree
1867 mathfn_built_in (tree type, enum built_in_function fn)
1868 {
1869 return mathfn_built_in_1 (type, fn, /*implicit=*/ 1);
1870 }
1871
1872 /* If errno must be maintained, expand the RTL to check if the result,
1873 TARGET, of a built-in function call, EXP, is NaN, and if so set
1874 errno to EDOM. */
1875
1876 static void
1877 expand_errno_check (tree exp, rtx target)
1878 {
1879 rtx lab = gen_label_rtx ();
1880
1881 /* Test the result; if it is NaN, set errno=EDOM because
1882 the argument was not in the domain. */
1883 do_compare_rtx_and_jump (target, target, EQ, 0, GET_MODE (target),
1884 NULL_RTX, NULL_RTX, lab,
1885 /* The jump is very likely. */
1886 REG_BR_PROB_BASE - (REG_BR_PROB_BASE / 2000 - 1));
1887
1888 #ifdef TARGET_EDOM
1889 /* If this built-in doesn't throw an exception, set errno directly. */
1890 if (TREE_NOTHROW (TREE_OPERAND (CALL_EXPR_FN (exp), 0)))
1891 {
1892 #ifdef GEN_ERRNO_RTX
1893 rtx errno_rtx = GEN_ERRNO_RTX;
1894 #else
1895 rtx errno_rtx
1896 = gen_rtx_MEM (word_mode, gen_rtx_SYMBOL_REF (Pmode, "errno"));
1897 #endif
1898 emit_move_insn (errno_rtx, GEN_INT (TARGET_EDOM));
1899 emit_label (lab);
1900 return;
1901 }
1902 #endif
1903
1904 /* Make sure the library call isn't expanded as a tail call. */
1905 CALL_EXPR_TAILCALL (exp) = 0;
1906
1907 /* We can't set errno=EDOM directly; let the library call do it.
1908 Pop the arguments right away in case the call gets deleted. */
1909 NO_DEFER_POP;
1910 expand_call (exp, target, 0);
1911 OK_DEFER_POP;
1912 emit_label (lab);
1913 }
1914
1915 /* Expand a call to one of the builtin math functions (sqrt, exp, or log).
1916 Return NULL_RTX if a normal call should be emitted rather than expanding
1917 the function in-line. EXP is the expression that is a call to the builtin
1918 function; if convenient, the result should be placed in TARGET.
1919 SUBTARGET may be used as the target for computing one of EXP's operands. */
1920
1921 static rtx
1922 expand_builtin_mathfn (tree exp, rtx target, rtx subtarget)
1923 {
1924 optab builtin_optab;
1925 rtx op0, insns;
1926 tree fndecl = get_callee_fndecl (exp);
1927 enum machine_mode mode;
1928 bool errno_set = false;
1929 tree arg;
1930
1931 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
1932 return NULL_RTX;
1933
1934 arg = CALL_EXPR_ARG (exp, 0);
1935
1936 switch (DECL_FUNCTION_CODE (fndecl))
1937 {
1938 CASE_FLT_FN (BUILT_IN_SQRT):
1939 errno_set = ! tree_expr_nonnegative_p (arg);
1940 builtin_optab = sqrt_optab;
1941 break;
1942 CASE_FLT_FN (BUILT_IN_EXP):
1943 errno_set = true; builtin_optab = exp_optab; break;
1944 CASE_FLT_FN (BUILT_IN_EXP10):
1945 CASE_FLT_FN (BUILT_IN_POW10):
1946 errno_set = true; builtin_optab = exp10_optab; break;
1947 CASE_FLT_FN (BUILT_IN_EXP2):
1948 errno_set = true; builtin_optab = exp2_optab; break;
1949 CASE_FLT_FN (BUILT_IN_EXPM1):
1950 errno_set = true; builtin_optab = expm1_optab; break;
1951 CASE_FLT_FN (BUILT_IN_LOGB):
1952 errno_set = true; builtin_optab = logb_optab; break;
1953 CASE_FLT_FN (BUILT_IN_LOG):
1954 errno_set = true; builtin_optab = log_optab; break;
1955 CASE_FLT_FN (BUILT_IN_LOG10):
1956 errno_set = true; builtin_optab = log10_optab; break;
1957 CASE_FLT_FN (BUILT_IN_LOG2):
1958 errno_set = true; builtin_optab = log2_optab; break;
1959 CASE_FLT_FN (BUILT_IN_LOG1P):
1960 errno_set = true; builtin_optab = log1p_optab; break;
1961 CASE_FLT_FN (BUILT_IN_ASIN):
1962 builtin_optab = asin_optab; break;
1963 CASE_FLT_FN (BUILT_IN_ACOS):
1964 builtin_optab = acos_optab; break;
1965 CASE_FLT_FN (BUILT_IN_TAN):
1966 builtin_optab = tan_optab; break;
1967 CASE_FLT_FN (BUILT_IN_ATAN):
1968 builtin_optab = atan_optab; break;
1969 CASE_FLT_FN (BUILT_IN_FLOOR):
1970 builtin_optab = floor_optab; break;
1971 CASE_FLT_FN (BUILT_IN_CEIL):
1972 builtin_optab = ceil_optab; break;
1973 CASE_FLT_FN (BUILT_IN_TRUNC):
1974 builtin_optab = btrunc_optab; break;
1975 CASE_FLT_FN (BUILT_IN_ROUND):
1976 builtin_optab = round_optab; break;
1977 CASE_FLT_FN (BUILT_IN_NEARBYINT):
1978 builtin_optab = nearbyint_optab;
1979 if (flag_trapping_math)
1980 break;
1981 /* Else fallthrough and expand as rint. */
1982 CASE_FLT_FN (BUILT_IN_RINT):
1983 builtin_optab = rint_optab; break;
1984 CASE_FLT_FN (BUILT_IN_SIGNIFICAND):
1985 builtin_optab = significand_optab; break;
1986 default:
1987 gcc_unreachable ();
1988 }
1989
1990 /* Make a suitable register to place result in. */
1991 mode = TYPE_MODE (TREE_TYPE (exp));
1992
1993 if (! flag_errno_math || ! HONOR_NANS (mode))
1994 errno_set = false;
1995
1996 /* Before working hard, check whether the instruction is available. */
1997 if (optab_handler (builtin_optab, mode)->insn_code != CODE_FOR_nothing)
1998 {
1999 target = gen_reg_rtx (mode);
2000
2001 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2002 need to expand the argument again. This way, we will not perform
2003 side-effects more the once. */
2004 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2005
2006 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2007
2008 start_sequence ();
2009
2010 /* Compute into TARGET.
2011 Set TARGET to wherever the result comes back. */
2012 target = expand_unop (mode, builtin_optab, op0, target, 0);
2013
2014 if (target != 0)
2015 {
2016 if (errno_set)
2017 expand_errno_check (exp, target);
2018
2019 /* Output the entire sequence. */
2020 insns = get_insns ();
2021 end_sequence ();
2022 emit_insn (insns);
2023 return target;
2024 }
2025
2026 /* If we were unable to expand via the builtin, stop the sequence
2027 (without outputting the insns) and call to the library function
2028 with the stabilized argument list. */
2029 end_sequence ();
2030 }
2031
2032 return expand_call (exp, target, target == const0_rtx);
2033 }
2034
2035 /* Expand a call to the builtin binary math functions (pow and atan2).
2036 Return NULL_RTX if a normal call should be emitted rather than expanding the
2037 function in-line. EXP is the expression that is a call to the builtin
2038 function; if convenient, the result should be placed in TARGET.
2039 SUBTARGET may be used as the target for computing one of EXP's
2040 operands. */
2041
2042 static rtx
2043 expand_builtin_mathfn_2 (tree exp, rtx target, rtx subtarget)
2044 {
2045 optab builtin_optab;
2046 rtx op0, op1, insns;
2047 int op1_type = REAL_TYPE;
2048 tree fndecl = get_callee_fndecl (exp);
2049 tree arg0, arg1;
2050 enum machine_mode mode;
2051 bool errno_set = true;
2052
2053 switch (DECL_FUNCTION_CODE (fndecl))
2054 {
2055 CASE_FLT_FN (BUILT_IN_SCALBN):
2056 CASE_FLT_FN (BUILT_IN_SCALBLN):
2057 CASE_FLT_FN (BUILT_IN_LDEXP):
2058 op1_type = INTEGER_TYPE;
2059 default:
2060 break;
2061 }
2062
2063 if (!validate_arglist (exp, REAL_TYPE, op1_type, VOID_TYPE))
2064 return NULL_RTX;
2065
2066 arg0 = CALL_EXPR_ARG (exp, 0);
2067 arg1 = CALL_EXPR_ARG (exp, 1);
2068
2069 switch (DECL_FUNCTION_CODE (fndecl))
2070 {
2071 CASE_FLT_FN (BUILT_IN_POW):
2072 builtin_optab = pow_optab; break;
2073 CASE_FLT_FN (BUILT_IN_ATAN2):
2074 builtin_optab = atan2_optab; break;
2075 CASE_FLT_FN (BUILT_IN_SCALB):
2076 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (exp)))->b != 2)
2077 return 0;
2078 builtin_optab = scalb_optab; break;
2079 CASE_FLT_FN (BUILT_IN_SCALBN):
2080 CASE_FLT_FN (BUILT_IN_SCALBLN):
2081 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (exp)))->b != 2)
2082 return 0;
2083 /* Fall through... */
2084 CASE_FLT_FN (BUILT_IN_LDEXP):
2085 builtin_optab = ldexp_optab; break;
2086 CASE_FLT_FN (BUILT_IN_FMOD):
2087 builtin_optab = fmod_optab; break;
2088 CASE_FLT_FN (BUILT_IN_REMAINDER):
2089 CASE_FLT_FN (BUILT_IN_DREM):
2090 builtin_optab = remainder_optab; break;
2091 default:
2092 gcc_unreachable ();
2093 }
2094
2095 /* Make a suitable register to place result in. */
2096 mode = TYPE_MODE (TREE_TYPE (exp));
2097
2098 /* Before working hard, check whether the instruction is available. */
2099 if (optab_handler (builtin_optab, mode)->insn_code == CODE_FOR_nothing)
2100 return NULL_RTX;
2101
2102 target = gen_reg_rtx (mode);
2103
2104 if (! flag_errno_math || ! HONOR_NANS (mode))
2105 errno_set = false;
2106
2107 /* Always stabilize the argument list. */
2108 CALL_EXPR_ARG (exp, 0) = arg0 = builtin_save_expr (arg0);
2109 CALL_EXPR_ARG (exp, 1) = arg1 = builtin_save_expr (arg1);
2110
2111 op0 = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
2112 op1 = expand_normal (arg1);
2113
2114 start_sequence ();
2115
2116 /* Compute into TARGET.
2117 Set TARGET to wherever the result comes back. */
2118 target = expand_binop (mode, builtin_optab, op0, op1,
2119 target, 0, OPTAB_DIRECT);
2120
2121 /* If we were unable to expand via the builtin, stop the sequence
2122 (without outputting the insns) and call to the library function
2123 with the stabilized argument list. */
2124 if (target == 0)
2125 {
2126 end_sequence ();
2127 return expand_call (exp, target, target == const0_rtx);
2128 }
2129
2130 if (errno_set)
2131 expand_errno_check (exp, target);
2132
2133 /* Output the entire sequence. */
2134 insns = get_insns ();
2135 end_sequence ();
2136 emit_insn (insns);
2137
2138 return target;
2139 }
2140
2141 /* Expand a call to the builtin sin and cos math functions.
2142 Return NULL_RTX if a normal call should be emitted rather than expanding the
2143 function in-line. EXP is the expression that is a call to the builtin
2144 function; if convenient, the result should be placed in TARGET.
2145 SUBTARGET may be used as the target for computing one of EXP's
2146 operands. */
2147
2148 static rtx
2149 expand_builtin_mathfn_3 (tree exp, rtx target, rtx subtarget)
2150 {
2151 optab builtin_optab;
2152 rtx op0, insns;
2153 tree fndecl = get_callee_fndecl (exp);
2154 enum machine_mode mode;
2155 tree arg;
2156
2157 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2158 return NULL_RTX;
2159
2160 arg = CALL_EXPR_ARG (exp, 0);
2161
2162 switch (DECL_FUNCTION_CODE (fndecl))
2163 {
2164 CASE_FLT_FN (BUILT_IN_SIN):
2165 CASE_FLT_FN (BUILT_IN_COS):
2166 builtin_optab = sincos_optab; break;
2167 default:
2168 gcc_unreachable ();
2169 }
2170
2171 /* Make a suitable register to place result in. */
2172 mode = TYPE_MODE (TREE_TYPE (exp));
2173
2174 /* Check if sincos insn is available, otherwise fallback
2175 to sin or cos insn. */
2176 if (optab_handler (builtin_optab, mode)->insn_code == CODE_FOR_nothing)
2177 switch (DECL_FUNCTION_CODE (fndecl))
2178 {
2179 CASE_FLT_FN (BUILT_IN_SIN):
2180 builtin_optab = sin_optab; break;
2181 CASE_FLT_FN (BUILT_IN_COS):
2182 builtin_optab = cos_optab; break;
2183 default:
2184 gcc_unreachable ();
2185 }
2186
2187 /* Before working hard, check whether the instruction is available. */
2188 if (optab_handler (builtin_optab, mode)->insn_code != CODE_FOR_nothing)
2189 {
2190 target = gen_reg_rtx (mode);
2191
2192 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2193 need to expand the argument again. This way, we will not perform
2194 side-effects more the once. */
2195 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2196
2197 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2198
2199 start_sequence ();
2200
2201 /* Compute into TARGET.
2202 Set TARGET to wherever the result comes back. */
2203 if (builtin_optab == sincos_optab)
2204 {
2205 int result;
2206
2207 switch (DECL_FUNCTION_CODE (fndecl))
2208 {
2209 CASE_FLT_FN (BUILT_IN_SIN):
2210 result = expand_twoval_unop (builtin_optab, op0, 0, target, 0);
2211 break;
2212 CASE_FLT_FN (BUILT_IN_COS):
2213 result = expand_twoval_unop (builtin_optab, op0, target, 0, 0);
2214 break;
2215 default:
2216 gcc_unreachable ();
2217 }
2218 gcc_assert (result);
2219 }
2220 else
2221 {
2222 target = expand_unop (mode, builtin_optab, op0, target, 0);
2223 }
2224
2225 if (target != 0)
2226 {
2227 /* Output the entire sequence. */
2228 insns = get_insns ();
2229 end_sequence ();
2230 emit_insn (insns);
2231 return target;
2232 }
2233
2234 /* If we were unable to expand via the builtin, stop the sequence
2235 (without outputting the insns) and call to the library function
2236 with the stabilized argument list. */
2237 end_sequence ();
2238 }
2239
2240 target = expand_call (exp, target, target == const0_rtx);
2241
2242 return target;
2243 }
2244
2245 /* Given an interclass math builtin decl FNDECL and it's argument ARG
2246 return an RTL instruction code that implements the functionality.
2247 If that isn't possible or available return CODE_FOR_nothing. */
2248
2249 static enum insn_code
2250 interclass_mathfn_icode (tree arg, tree fndecl)
2251 {
2252 bool errno_set = false;
2253 optab builtin_optab = 0;
2254 enum machine_mode mode;
2255
2256 switch (DECL_FUNCTION_CODE (fndecl))
2257 {
2258 CASE_FLT_FN (BUILT_IN_ILOGB):
2259 errno_set = true; builtin_optab = ilogb_optab; break;
2260 CASE_FLT_FN (BUILT_IN_ISINF):
2261 builtin_optab = isinf_optab; break;
2262 case BUILT_IN_ISNORMAL:
2263 case BUILT_IN_ISFINITE:
2264 CASE_FLT_FN (BUILT_IN_FINITE):
2265 case BUILT_IN_FINITED32:
2266 case BUILT_IN_FINITED64:
2267 case BUILT_IN_FINITED128:
2268 case BUILT_IN_ISINFD32:
2269 case BUILT_IN_ISINFD64:
2270 case BUILT_IN_ISINFD128:
2271 /* These builtins have no optabs (yet). */
2272 break;
2273 default:
2274 gcc_unreachable ();
2275 }
2276
2277 /* There's no easy way to detect the case we need to set EDOM. */
2278 if (flag_errno_math && errno_set)
2279 return CODE_FOR_nothing;
2280
2281 /* Optab mode depends on the mode of the input argument. */
2282 mode = TYPE_MODE (TREE_TYPE (arg));
2283
2284 if (builtin_optab)
2285 return optab_handler (builtin_optab, mode)->insn_code;
2286 return CODE_FOR_nothing;
2287 }
2288
2289 /* Expand a call to one of the builtin math functions that operate on
2290 floating point argument and output an integer result (ilogb, isinf,
2291 isnan, etc).
2292 Return 0 if a normal call should be emitted rather than expanding the
2293 function in-line. EXP is the expression that is a call to the builtin
2294 function; if convenient, the result should be placed in TARGET.
2295 SUBTARGET may be used as the target for computing one of EXP's operands. */
2296
2297 static rtx
2298 expand_builtin_interclass_mathfn (tree exp, rtx target, rtx subtarget)
2299 {
2300 enum insn_code icode = CODE_FOR_nothing;
2301 rtx op0;
2302 tree fndecl = get_callee_fndecl (exp);
2303 enum machine_mode mode;
2304 tree arg;
2305
2306 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2307 return NULL_RTX;
2308
2309 arg = CALL_EXPR_ARG (exp, 0);
2310 icode = interclass_mathfn_icode (arg, fndecl);
2311 mode = TYPE_MODE (TREE_TYPE (arg));
2312
2313 if (icode != CODE_FOR_nothing)
2314 {
2315 rtx last = get_last_insn ();
2316 tree orig_arg = arg;
2317 /* Make a suitable register to place result in. */
2318 if (!target
2319 || GET_MODE (target) != TYPE_MODE (TREE_TYPE (exp))
2320 || !insn_data[icode].operand[0].predicate (target, GET_MODE (target)))
2321 target = gen_reg_rtx (TYPE_MODE (TREE_TYPE (exp)));
2322
2323 gcc_assert (insn_data[icode].operand[0].predicate
2324 (target, GET_MODE (target)));
2325
2326 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2327 need to expand the argument again. This way, we will not perform
2328 side-effects more the once. */
2329 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2330
2331 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2332
2333 if (mode != GET_MODE (op0))
2334 op0 = convert_to_mode (mode, op0, 0);
2335
2336 /* Compute into TARGET.
2337 Set TARGET to wherever the result comes back. */
2338 if (maybe_emit_unop_insn (icode, target, op0, UNKNOWN))
2339 return target;
2340 delete_insns_since (last);
2341 CALL_EXPR_ARG (exp, 0) = orig_arg;
2342 }
2343
2344 return NULL_RTX;
2345 }
2346
2347 /* Expand a call to the builtin sincos math function.
2348 Return NULL_RTX if a normal call should be emitted rather than expanding the
2349 function in-line. EXP is the expression that is a call to the builtin
2350 function. */
2351
2352 static rtx
2353 expand_builtin_sincos (tree exp)
2354 {
2355 rtx op0, op1, op2, target1, target2;
2356 enum machine_mode mode;
2357 tree arg, sinp, cosp;
2358 int result;
2359 location_t loc = EXPR_LOCATION (exp);
2360
2361 if (!validate_arglist (exp, REAL_TYPE,
2362 POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
2363 return NULL_RTX;
2364
2365 arg = CALL_EXPR_ARG (exp, 0);
2366 sinp = CALL_EXPR_ARG (exp, 1);
2367 cosp = CALL_EXPR_ARG (exp, 2);
2368
2369 /* Make a suitable register to place result in. */
2370 mode = TYPE_MODE (TREE_TYPE (arg));
2371
2372 /* Check if sincos insn is available, otherwise emit the call. */
2373 if (optab_handler (sincos_optab, mode)->insn_code == CODE_FOR_nothing)
2374 return NULL_RTX;
2375
2376 target1 = gen_reg_rtx (mode);
2377 target2 = gen_reg_rtx (mode);
2378
2379 op0 = expand_normal (arg);
2380 op1 = expand_normal (build_fold_indirect_ref_loc (loc, sinp));
2381 op2 = expand_normal (build_fold_indirect_ref_loc (loc, cosp));
2382
2383 /* Compute into target1 and target2.
2384 Set TARGET to wherever the result comes back. */
2385 result = expand_twoval_unop (sincos_optab, op0, target2, target1, 0);
2386 gcc_assert (result);
2387
2388 /* Move target1 and target2 to the memory locations indicated
2389 by op1 and op2. */
2390 emit_move_insn (op1, target1);
2391 emit_move_insn (op2, target2);
2392
2393 return const0_rtx;
2394 }
2395
2396 /* Expand a call to the internal cexpi builtin to the sincos math function.
2397 EXP is the expression that is a call to the builtin function; if convenient,
2398 the result should be placed in TARGET. SUBTARGET may be used as the target
2399 for computing one of EXP's operands. */
2400
2401 static rtx
2402 expand_builtin_cexpi (tree exp, rtx target, rtx subtarget)
2403 {
2404 tree fndecl = get_callee_fndecl (exp);
2405 tree arg, type;
2406 enum machine_mode mode;
2407 rtx op0, op1, op2;
2408 location_t loc = EXPR_LOCATION (exp);
2409
2410 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2411 return NULL_RTX;
2412
2413 arg = CALL_EXPR_ARG (exp, 0);
2414 type = TREE_TYPE (arg);
2415 mode = TYPE_MODE (TREE_TYPE (arg));
2416
2417 /* Try expanding via a sincos optab, fall back to emitting a libcall
2418 to sincos or cexp. We are sure we have sincos or cexp because cexpi
2419 is only generated from sincos, cexp or if we have either of them. */
2420 if (optab_handler (sincos_optab, mode)->insn_code != CODE_FOR_nothing)
2421 {
2422 op1 = gen_reg_rtx (mode);
2423 op2 = gen_reg_rtx (mode);
2424
2425 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
2426
2427 /* Compute into op1 and op2. */
2428 expand_twoval_unop (sincos_optab, op0, op2, op1, 0);
2429 }
2430 else if (TARGET_HAS_SINCOS)
2431 {
2432 tree call, fn = NULL_TREE;
2433 tree top1, top2;
2434 rtx op1a, op2a;
2435
2436 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2437 fn = built_in_decls[BUILT_IN_SINCOSF];
2438 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2439 fn = built_in_decls[BUILT_IN_SINCOS];
2440 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2441 fn = built_in_decls[BUILT_IN_SINCOSL];
2442 else
2443 gcc_unreachable ();
2444
2445 op1 = assign_temp (TREE_TYPE (arg), 0, 1, 1);
2446 op2 = assign_temp (TREE_TYPE (arg), 0, 1, 1);
2447 op1a = copy_to_mode_reg (Pmode, XEXP (op1, 0));
2448 op2a = copy_to_mode_reg (Pmode, XEXP (op2, 0));
2449 top1 = make_tree (build_pointer_type (TREE_TYPE (arg)), op1a);
2450 top2 = make_tree (build_pointer_type (TREE_TYPE (arg)), op2a);
2451
2452 /* Make sure not to fold the sincos call again. */
2453 call = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
2454 expand_normal (build_call_nary (TREE_TYPE (TREE_TYPE (fn)),
2455 call, 3, arg, top1, top2));
2456 }
2457 else
2458 {
2459 tree call, fn = NULL_TREE, narg;
2460 tree ctype = build_complex_type (type);
2461
2462 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2463 fn = built_in_decls[BUILT_IN_CEXPF];
2464 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2465 fn = built_in_decls[BUILT_IN_CEXP];
2466 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2467 fn = built_in_decls[BUILT_IN_CEXPL];
2468 else
2469 gcc_unreachable ();
2470
2471 /* If we don't have a decl for cexp create one. This is the
2472 friendliest fallback if the user calls __builtin_cexpi
2473 without full target C99 function support. */
2474 if (fn == NULL_TREE)
2475 {
2476 tree fntype;
2477 const char *name = NULL;
2478
2479 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIF)
2480 name = "cexpf";
2481 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPI)
2482 name = "cexp";
2483 else if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_CEXPIL)
2484 name = "cexpl";
2485
2486 fntype = build_function_type_list (ctype, ctype, NULL_TREE);
2487 fn = build_fn_decl (name, fntype);
2488 }
2489
2490 narg = fold_build2_loc (loc, COMPLEX_EXPR, ctype,
2491 build_real (type, dconst0), arg);
2492
2493 /* Make sure not to fold the cexp call again. */
2494 call = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
2495 return expand_expr (build_call_nary (ctype, call, 1, narg),
2496 target, VOIDmode, EXPAND_NORMAL);
2497 }
2498
2499 /* Now build the proper return type. */
2500 return expand_expr (build2 (COMPLEX_EXPR, build_complex_type (type),
2501 make_tree (TREE_TYPE (arg), op2),
2502 make_tree (TREE_TYPE (arg), op1)),
2503 target, VOIDmode, EXPAND_NORMAL);
2504 }
2505
2506 /* Conveniently construct a function call expression. FNDECL names the
2507 function to be called, N is the number of arguments, and the "..."
2508 parameters are the argument expressions. Unlike build_call_exr
2509 this doesn't fold the call, hence it will always return a CALL_EXPR. */
2510
2511 static tree
2512 build_call_nofold_loc (location_t loc, tree fndecl, int n, ...)
2513 {
2514 va_list ap;
2515 tree fntype = TREE_TYPE (fndecl);
2516 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
2517
2518 va_start (ap, n);
2519 fn = build_call_valist (TREE_TYPE (fntype), fn, n, ap);
2520 va_end (ap);
2521 SET_EXPR_LOCATION (fn, loc);
2522 return fn;
2523 }
2524 #define build_call_nofold(...) \
2525 build_call_nofold_loc (UNKNOWN_LOCATION, __VA_ARGS__)
2526
2527 /* Expand a call to one of the builtin rounding functions gcc defines
2528 as an extension (lfloor and lceil). As these are gcc extensions we
2529 do not need to worry about setting errno to EDOM.
2530 If expanding via optab fails, lower expression to (int)(floor(x)).
2531 EXP is the expression that is a call to the builtin function;
2532 if convenient, the result should be placed in TARGET. */
2533
2534 static rtx
2535 expand_builtin_int_roundingfn (tree exp, rtx target)
2536 {
2537 convert_optab builtin_optab;
2538 rtx op0, insns, tmp;
2539 tree fndecl = get_callee_fndecl (exp);
2540 enum built_in_function fallback_fn;
2541 tree fallback_fndecl;
2542 enum machine_mode mode;
2543 tree arg;
2544
2545 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2546 gcc_unreachable ();
2547
2548 arg = CALL_EXPR_ARG (exp, 0);
2549
2550 switch (DECL_FUNCTION_CODE (fndecl))
2551 {
2552 CASE_FLT_FN (BUILT_IN_LCEIL):
2553 CASE_FLT_FN (BUILT_IN_LLCEIL):
2554 builtin_optab = lceil_optab;
2555 fallback_fn = BUILT_IN_CEIL;
2556 break;
2557
2558 CASE_FLT_FN (BUILT_IN_LFLOOR):
2559 CASE_FLT_FN (BUILT_IN_LLFLOOR):
2560 builtin_optab = lfloor_optab;
2561 fallback_fn = BUILT_IN_FLOOR;
2562 break;
2563
2564 default:
2565 gcc_unreachable ();
2566 }
2567
2568 /* Make a suitable register to place result in. */
2569 mode = TYPE_MODE (TREE_TYPE (exp));
2570
2571 target = gen_reg_rtx (mode);
2572
2573 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2574 need to expand the argument again. This way, we will not perform
2575 side-effects more the once. */
2576 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2577
2578 op0 = expand_expr (arg, NULL, VOIDmode, EXPAND_NORMAL);
2579
2580 start_sequence ();
2581
2582 /* Compute into TARGET. */
2583 if (expand_sfix_optab (target, op0, builtin_optab))
2584 {
2585 /* Output the entire sequence. */
2586 insns = get_insns ();
2587 end_sequence ();
2588 emit_insn (insns);
2589 return target;
2590 }
2591
2592 /* If we were unable to expand via the builtin, stop the sequence
2593 (without outputting the insns). */
2594 end_sequence ();
2595
2596 /* Fall back to floating point rounding optab. */
2597 fallback_fndecl = mathfn_built_in (TREE_TYPE (arg), fallback_fn);
2598
2599 /* For non-C99 targets we may end up without a fallback fndecl here
2600 if the user called __builtin_lfloor directly. In this case emit
2601 a call to the floor/ceil variants nevertheless. This should result
2602 in the best user experience for not full C99 targets. */
2603 if (fallback_fndecl == NULL_TREE)
2604 {
2605 tree fntype;
2606 const char *name = NULL;
2607
2608 switch (DECL_FUNCTION_CODE (fndecl))
2609 {
2610 case BUILT_IN_LCEIL:
2611 case BUILT_IN_LLCEIL:
2612 name = "ceil";
2613 break;
2614 case BUILT_IN_LCEILF:
2615 case BUILT_IN_LLCEILF:
2616 name = "ceilf";
2617 break;
2618 case BUILT_IN_LCEILL:
2619 case BUILT_IN_LLCEILL:
2620 name = "ceill";
2621 break;
2622 case BUILT_IN_LFLOOR:
2623 case BUILT_IN_LLFLOOR:
2624 name = "floor";
2625 break;
2626 case BUILT_IN_LFLOORF:
2627 case BUILT_IN_LLFLOORF:
2628 name = "floorf";
2629 break;
2630 case BUILT_IN_LFLOORL:
2631 case BUILT_IN_LLFLOORL:
2632 name = "floorl";
2633 break;
2634 default:
2635 gcc_unreachable ();
2636 }
2637
2638 fntype = build_function_type_list (TREE_TYPE (arg),
2639 TREE_TYPE (arg), NULL_TREE);
2640 fallback_fndecl = build_fn_decl (name, fntype);
2641 }
2642
2643 exp = build_call_nofold (fallback_fndecl, 1, arg);
2644
2645 tmp = expand_normal (exp);
2646
2647 /* Truncate the result of floating point optab to integer
2648 via expand_fix (). */
2649 target = gen_reg_rtx (mode);
2650 expand_fix (target, tmp, 0);
2651
2652 return target;
2653 }
2654
2655 /* Expand a call to one of the builtin math functions doing integer
2656 conversion (lrint).
2657 Return 0 if a normal call should be emitted rather than expanding the
2658 function in-line. EXP is the expression that is a call to the builtin
2659 function; if convenient, the result should be placed in TARGET. */
2660
2661 static rtx
2662 expand_builtin_int_roundingfn_2 (tree exp, rtx target)
2663 {
2664 convert_optab builtin_optab;
2665 rtx op0, insns;
2666 tree fndecl = get_callee_fndecl (exp);
2667 tree arg;
2668 enum machine_mode mode;
2669
2670 /* There's no easy way to detect the case we need to set EDOM. */
2671 if (flag_errno_math)
2672 return NULL_RTX;
2673
2674 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
2675 gcc_unreachable ();
2676
2677 arg = CALL_EXPR_ARG (exp, 0);
2678
2679 switch (DECL_FUNCTION_CODE (fndecl))
2680 {
2681 CASE_FLT_FN (BUILT_IN_LRINT):
2682 CASE_FLT_FN (BUILT_IN_LLRINT):
2683 builtin_optab = lrint_optab; break;
2684 CASE_FLT_FN (BUILT_IN_LROUND):
2685 CASE_FLT_FN (BUILT_IN_LLROUND):
2686 builtin_optab = lround_optab; break;
2687 default:
2688 gcc_unreachable ();
2689 }
2690
2691 /* Make a suitable register to place result in. */
2692 mode = TYPE_MODE (TREE_TYPE (exp));
2693
2694 target = gen_reg_rtx (mode);
2695
2696 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2697 need to expand the argument again. This way, we will not perform
2698 side-effects more the once. */
2699 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
2700
2701 op0 = expand_expr (arg, NULL, VOIDmode, EXPAND_NORMAL);
2702
2703 start_sequence ();
2704
2705 if (expand_sfix_optab (target, op0, builtin_optab))
2706 {
2707 /* Output the entire sequence. */
2708 insns = get_insns ();
2709 end_sequence ();
2710 emit_insn (insns);
2711 return target;
2712 }
2713
2714 /* If we were unable to expand via the builtin, stop the sequence
2715 (without outputting the insns) and call to the library function
2716 with the stabilized argument list. */
2717 end_sequence ();
2718
2719 target = expand_call (exp, target, target == const0_rtx);
2720
2721 return target;
2722 }
2723
2724 /* To evaluate powi(x,n), the floating point value x raised to the
2725 constant integer exponent n, we use a hybrid algorithm that
2726 combines the "window method" with look-up tables. For an
2727 introduction to exponentiation algorithms and "addition chains",
2728 see section 4.6.3, "Evaluation of Powers" of Donald E. Knuth,
2729 "Seminumerical Algorithms", Vol. 2, "The Art of Computer Programming",
2730 3rd Edition, 1998, and Daniel M. Gordon, "A Survey of Fast Exponentiation
2731 Methods", Journal of Algorithms, Vol. 27, pp. 129-146, 1998. */
2732
2733 /* Provide a default value for POWI_MAX_MULTS, the maximum number of
2734 multiplications to inline before calling the system library's pow
2735 function. powi(x,n) requires at worst 2*bits(n)-2 multiplications,
2736 so this default never requires calling pow, powf or powl. */
2737
2738 #ifndef POWI_MAX_MULTS
2739 #define POWI_MAX_MULTS (2*HOST_BITS_PER_WIDE_INT-2)
2740 #endif
2741
2742 /* The size of the "optimal power tree" lookup table. All
2743 exponents less than this value are simply looked up in the
2744 powi_table below. This threshold is also used to size the
2745 cache of pseudo registers that hold intermediate results. */
2746 #define POWI_TABLE_SIZE 256
2747
2748 /* The size, in bits of the window, used in the "window method"
2749 exponentiation algorithm. This is equivalent to a radix of
2750 (1<<POWI_WINDOW_SIZE) in the corresponding "m-ary method". */
2751 #define POWI_WINDOW_SIZE 3
2752
2753 /* The following table is an efficient representation of an
2754 "optimal power tree". For each value, i, the corresponding
2755 value, j, in the table states than an optimal evaluation
2756 sequence for calculating pow(x,i) can be found by evaluating
2757 pow(x,j)*pow(x,i-j). An optimal power tree for the first
2758 100 integers is given in Knuth's "Seminumerical algorithms". */
2759
2760 static const unsigned char powi_table[POWI_TABLE_SIZE] =
2761 {
2762 0, 1, 1, 2, 2, 3, 3, 4, /* 0 - 7 */
2763 4, 6, 5, 6, 6, 10, 7, 9, /* 8 - 15 */
2764 8, 16, 9, 16, 10, 12, 11, 13, /* 16 - 23 */
2765 12, 17, 13, 18, 14, 24, 15, 26, /* 24 - 31 */
2766 16, 17, 17, 19, 18, 33, 19, 26, /* 32 - 39 */
2767 20, 25, 21, 40, 22, 27, 23, 44, /* 40 - 47 */
2768 24, 32, 25, 34, 26, 29, 27, 44, /* 48 - 55 */
2769 28, 31, 29, 34, 30, 60, 31, 36, /* 56 - 63 */
2770 32, 64, 33, 34, 34, 46, 35, 37, /* 64 - 71 */
2771 36, 65, 37, 50, 38, 48, 39, 69, /* 72 - 79 */
2772 40, 49, 41, 43, 42, 51, 43, 58, /* 80 - 87 */
2773 44, 64, 45, 47, 46, 59, 47, 76, /* 88 - 95 */
2774 48, 65, 49, 66, 50, 67, 51, 66, /* 96 - 103 */
2775 52, 70, 53, 74, 54, 104, 55, 74, /* 104 - 111 */
2776 56, 64, 57, 69, 58, 78, 59, 68, /* 112 - 119 */
2777 60, 61, 61, 80, 62, 75, 63, 68, /* 120 - 127 */
2778 64, 65, 65, 128, 66, 129, 67, 90, /* 128 - 135 */
2779 68, 73, 69, 131, 70, 94, 71, 88, /* 136 - 143 */
2780 72, 128, 73, 98, 74, 132, 75, 121, /* 144 - 151 */
2781 76, 102, 77, 124, 78, 132, 79, 106, /* 152 - 159 */
2782 80, 97, 81, 160, 82, 99, 83, 134, /* 160 - 167 */
2783 84, 86, 85, 95, 86, 160, 87, 100, /* 168 - 175 */
2784 88, 113, 89, 98, 90, 107, 91, 122, /* 176 - 183 */
2785 92, 111, 93, 102, 94, 126, 95, 150, /* 184 - 191 */
2786 96, 128, 97, 130, 98, 133, 99, 195, /* 192 - 199 */
2787 100, 128, 101, 123, 102, 164, 103, 138, /* 200 - 207 */
2788 104, 145, 105, 146, 106, 109, 107, 149, /* 208 - 215 */
2789 108, 200, 109, 146, 110, 170, 111, 157, /* 216 - 223 */
2790 112, 128, 113, 130, 114, 182, 115, 132, /* 224 - 231 */
2791 116, 200, 117, 132, 118, 158, 119, 206, /* 232 - 239 */
2792 120, 240, 121, 162, 122, 147, 123, 152, /* 240 - 247 */
2793 124, 166, 125, 214, 126, 138, 127, 153, /* 248 - 255 */
2794 };
2795
2796
2797 /* Return the number of multiplications required to calculate
2798 powi(x,n) where n is less than POWI_TABLE_SIZE. This is a
2799 subroutine of powi_cost. CACHE is an array indicating
2800 which exponents have already been calculated. */
2801
2802 static int
2803 powi_lookup_cost (unsigned HOST_WIDE_INT n, bool *cache)
2804 {
2805 /* If we've already calculated this exponent, then this evaluation
2806 doesn't require any additional multiplications. */
2807 if (cache[n])
2808 return 0;
2809
2810 cache[n] = true;
2811 return powi_lookup_cost (n - powi_table[n], cache)
2812 + powi_lookup_cost (powi_table[n], cache) + 1;
2813 }
2814
2815 /* Return the number of multiplications required to calculate
2816 powi(x,n) for an arbitrary x, given the exponent N. This
2817 function needs to be kept in sync with expand_powi below. */
2818
2819 static int
2820 powi_cost (HOST_WIDE_INT n)
2821 {
2822 bool cache[POWI_TABLE_SIZE];
2823 unsigned HOST_WIDE_INT digit;
2824 unsigned HOST_WIDE_INT val;
2825 int result;
2826
2827 if (n == 0)
2828 return 0;
2829
2830 /* Ignore the reciprocal when calculating the cost. */
2831 val = (n < 0) ? -n : n;
2832
2833 /* Initialize the exponent cache. */
2834 memset (cache, 0, POWI_TABLE_SIZE * sizeof (bool));
2835 cache[1] = true;
2836
2837 result = 0;
2838
2839 while (val >= POWI_TABLE_SIZE)
2840 {
2841 if (val & 1)
2842 {
2843 digit = val & ((1 << POWI_WINDOW_SIZE) - 1);
2844 result += powi_lookup_cost (digit, cache)
2845 + POWI_WINDOW_SIZE + 1;
2846 val >>= POWI_WINDOW_SIZE;
2847 }
2848 else
2849 {
2850 val >>= 1;
2851 result++;
2852 }
2853 }
2854
2855 return result + powi_lookup_cost (val, cache);
2856 }
2857
2858 /* Recursive subroutine of expand_powi. This function takes the array,
2859 CACHE, of already calculated exponents and an exponent N and returns
2860 an RTX that corresponds to CACHE[1]**N, as calculated in mode MODE. */
2861
2862 static rtx
2863 expand_powi_1 (enum machine_mode mode, unsigned HOST_WIDE_INT n, rtx *cache)
2864 {
2865 unsigned HOST_WIDE_INT digit;
2866 rtx target, result;
2867 rtx op0, op1;
2868
2869 if (n < POWI_TABLE_SIZE)
2870 {
2871 if (cache[n])
2872 return cache[n];
2873
2874 target = gen_reg_rtx (mode);
2875 cache[n] = target;
2876
2877 op0 = expand_powi_1 (mode, n - powi_table[n], cache);
2878 op1 = expand_powi_1 (mode, powi_table[n], cache);
2879 }
2880 else if (n & 1)
2881 {
2882 target = gen_reg_rtx (mode);
2883 digit = n & ((1 << POWI_WINDOW_SIZE) - 1);
2884 op0 = expand_powi_1 (mode, n - digit, cache);
2885 op1 = expand_powi_1 (mode, digit, cache);
2886 }
2887 else
2888 {
2889 target = gen_reg_rtx (mode);
2890 op0 = expand_powi_1 (mode, n >> 1, cache);
2891 op1 = op0;
2892 }
2893
2894 result = expand_mult (mode, op0, op1, target, 0);
2895 if (result != target)
2896 emit_move_insn (target, result);
2897 return target;
2898 }
2899
2900 /* Expand the RTL to evaluate powi(x,n) in mode MODE. X is the
2901 floating point operand in mode MODE, and N is the exponent. This
2902 function needs to be kept in sync with powi_cost above. */
2903
2904 static rtx
2905 expand_powi (rtx x, enum machine_mode mode, HOST_WIDE_INT n)
2906 {
2907 rtx cache[POWI_TABLE_SIZE];
2908 rtx result;
2909
2910 if (n == 0)
2911 return CONST1_RTX (mode);
2912
2913 memset (cache, 0, sizeof (cache));
2914 cache[1] = x;
2915
2916 result = expand_powi_1 (mode, (n < 0) ? -n : n, cache);
2917
2918 /* If the original exponent was negative, reciprocate the result. */
2919 if (n < 0)
2920 result = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
2921 result, NULL_RTX, 0, OPTAB_LIB_WIDEN);
2922
2923 return result;
2924 }
2925
2926 /* Fold a builtin function call to pow, powf, or powl into a series of sqrts or
2927 cbrts. Return NULL_RTX if no simplification can be made or expand the tree
2928 if we can simplify it. */
2929 static rtx
2930 expand_builtin_pow_root (location_t loc, tree arg0, tree arg1, tree type,
2931 rtx subtarget)
2932 {
2933 if (TREE_CODE (arg1) == REAL_CST
2934 && !TREE_OVERFLOW (arg1)
2935 && flag_unsafe_math_optimizations)
2936 {
2937 enum machine_mode mode = TYPE_MODE (type);
2938 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
2939 tree cbrtfn = mathfn_built_in (type, BUILT_IN_CBRT);
2940 REAL_VALUE_TYPE c = TREE_REAL_CST (arg1);
2941 tree op = NULL_TREE;
2942
2943 if (sqrtfn)
2944 {
2945 /* Optimize pow (x, 0.5) into sqrt. */
2946 if (REAL_VALUES_EQUAL (c, dconsthalf))
2947 op = build_call_nofold_loc (loc, sqrtfn, 1, arg0);
2948
2949 else
2950 {
2951 REAL_VALUE_TYPE dconst1_4 = dconst1;
2952 REAL_VALUE_TYPE dconst3_4;
2953 SET_REAL_EXP (&dconst1_4, REAL_EXP (&dconst1_4) - 2);
2954
2955 real_from_integer (&dconst3_4, VOIDmode, 3, 0, 0);
2956 SET_REAL_EXP (&dconst3_4, REAL_EXP (&dconst3_4) - 2);
2957
2958 /* Optimize pow (x, 0.25) into sqrt (sqrt (x)). Assume on most
2959 machines that a builtin sqrt instruction is smaller than a
2960 call to pow with 0.25, so do this optimization even if
2961 -Os. */
2962 if (REAL_VALUES_EQUAL (c, dconst1_4))
2963 {
2964 op = build_call_nofold_loc (loc, sqrtfn, 1, arg0);
2965 op = build_call_nofold_loc (loc, sqrtfn, 1, op);
2966 }
2967
2968 /* Optimize pow (x, 0.75) = sqrt (x) * sqrt (sqrt (x)) unless we
2969 are optimizing for space. */
2970 else if (optimize_insn_for_speed_p ()
2971 && !TREE_SIDE_EFFECTS (arg0)
2972 && REAL_VALUES_EQUAL (c, dconst3_4))
2973 {
2974 tree sqrt1 = build_call_expr_loc (loc, sqrtfn, 1, arg0);
2975 tree sqrt2 = builtin_save_expr (sqrt1);
2976 tree sqrt3 = build_call_expr_loc (loc, sqrtfn, 1, sqrt1);
2977 op = fold_build2_loc (loc, MULT_EXPR, type, sqrt2, sqrt3);
2978 }
2979 }
2980 }
2981
2982 /* Check whether we can do cbrt insstead of pow (x, 1./3.) and
2983 cbrt/sqrts instead of pow (x, 1./6.). */
2984 if (cbrtfn && ! op
2985 && (tree_expr_nonnegative_p (arg0) || !HONOR_NANS (mode)))
2986 {
2987 /* First try 1/3. */
2988 REAL_VALUE_TYPE dconst1_3
2989 = real_value_truncate (mode, dconst_third ());
2990
2991 if (REAL_VALUES_EQUAL (c, dconst1_3))
2992 op = build_call_nofold_loc (loc, cbrtfn, 1, arg0);
2993
2994 /* Now try 1/6. */
2995 else if (optimize_insn_for_speed_p ())
2996 {
2997 REAL_VALUE_TYPE dconst1_6 = dconst1_3;
2998 SET_REAL_EXP (&dconst1_6, REAL_EXP (&dconst1_6) - 1);
2999
3000 if (REAL_VALUES_EQUAL (c, dconst1_6))
3001 {
3002 op = build_call_nofold_loc (loc, sqrtfn, 1, arg0);
3003 op = build_call_nofold_loc (loc, cbrtfn, 1, op);
3004 }
3005 }
3006 }
3007
3008 if (op)
3009 return expand_expr (op, subtarget, mode, EXPAND_NORMAL);
3010 }
3011
3012 return NULL_RTX;
3013 }
3014
3015 /* Expand a call to the pow built-in mathematical function. Return NULL_RTX if
3016 a normal call should be emitted rather than expanding the function
3017 in-line. EXP is the expression that is a call to the builtin
3018 function; if convenient, the result should be placed in TARGET. */
3019
3020 static rtx
3021 expand_builtin_pow (tree exp, rtx target, rtx subtarget)
3022 {
3023 tree arg0, arg1;
3024 tree fn, narg0;
3025 tree type = TREE_TYPE (exp);
3026 REAL_VALUE_TYPE cint, c, c2;
3027 HOST_WIDE_INT n;
3028 rtx op, op2;
3029 enum machine_mode mode = TYPE_MODE (type);
3030
3031 if (! validate_arglist (exp, REAL_TYPE, REAL_TYPE, VOID_TYPE))
3032 return NULL_RTX;
3033
3034 arg0 = CALL_EXPR_ARG (exp, 0);
3035 arg1 = CALL_EXPR_ARG (exp, 1);
3036
3037 if (TREE_CODE (arg1) != REAL_CST
3038 || TREE_OVERFLOW (arg1))
3039 return expand_builtin_mathfn_2 (exp, target, subtarget);
3040
3041 /* Handle constant exponents. */
3042
3043 /* For integer valued exponents we can expand to an optimal multiplication
3044 sequence using expand_powi. */
3045 c = TREE_REAL_CST (arg1);
3046 n = real_to_integer (&c);
3047 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
3048 if (real_identical (&c, &cint)
3049 && ((n >= -1 && n <= 2)
3050 || (flag_unsafe_math_optimizations
3051 && optimize_insn_for_speed_p ()
3052 && powi_cost (n) <= POWI_MAX_MULTS)))
3053 {
3054 op = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
3055 if (n != 1)
3056 {
3057 op = force_reg (mode, op);
3058 op = expand_powi (op, mode, n);
3059 }
3060 return op;
3061 }
3062
3063 narg0 = builtin_save_expr (arg0);
3064
3065 /* If the exponent is not integer valued, check if it is half of an integer.
3066 In this case we can expand to sqrt (x) * x**(n/2). */
3067 fn = mathfn_built_in (type, BUILT_IN_SQRT);
3068 if (fn != NULL_TREE)
3069 {
3070 real_arithmetic (&c2, MULT_EXPR, &c, &dconst2);
3071 n = real_to_integer (&c2);
3072 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
3073 if (real_identical (&c2, &cint)
3074 && ((flag_unsafe_math_optimizations
3075 && optimize_insn_for_speed_p ()
3076 && powi_cost (n/2) <= POWI_MAX_MULTS)
3077 /* Even the c == 0.5 case cannot be done unconditionally
3078 when we need to preserve signed zeros, as
3079 pow (-0, 0.5) is +0, while sqrt(-0) is -0. */
3080 || (!HONOR_SIGNED_ZEROS (mode) && n == 1)
3081 /* For c == 1.5 we can assume that x * sqrt (x) is always
3082 smaller than pow (x, 1.5) if sqrt will not be expanded
3083 as a call. */
3084 || (n == 3
3085 && (optab_handler (sqrt_optab, mode)->insn_code
3086 != CODE_FOR_nothing))))
3087 {
3088 tree call_expr = build_call_nofold (fn, 1, narg0);
3089 /* Use expand_expr in case the newly built call expression
3090 was folded to a non-call. */
3091 op = expand_expr (call_expr, subtarget, mode, EXPAND_NORMAL);
3092 if (n != 1)
3093 {
3094 op2 = expand_expr (narg0, subtarget, VOIDmode, EXPAND_NORMAL);
3095 op2 = force_reg (mode, op2);
3096 op2 = expand_powi (op2, mode, abs (n / 2));
3097 op = expand_simple_binop (mode, MULT, op, op2, NULL_RTX,
3098 0, OPTAB_LIB_WIDEN);
3099 /* If the original exponent was negative, reciprocate the
3100 result. */
3101 if (n < 0)
3102 op = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
3103 op, NULL_RTX, 0, OPTAB_LIB_WIDEN);
3104 }
3105 return op;
3106 }
3107 }
3108
3109 /* Check whether we can do a series of sqrt or cbrt's instead of the pow
3110 call. */
3111 op = expand_builtin_pow_root (EXPR_LOCATION (exp), arg0, arg1, type,
3112 subtarget);
3113 if (op)
3114 return op;
3115
3116 /* Try if the exponent is a third of an integer. In this case
3117 we can expand to x**(n/3) * cbrt(x)**(n%3). As cbrt (x) is
3118 different from pow (x, 1./3.) due to rounding and behavior
3119 with negative x we need to constrain this transformation to
3120 unsafe math and positive x or finite math. */
3121 fn = mathfn_built_in (type, BUILT_IN_CBRT);
3122 if (fn != NULL_TREE
3123 && flag_unsafe_math_optimizations
3124 && (tree_expr_nonnegative_p (arg0)
3125 || !HONOR_NANS (mode)))
3126 {
3127 REAL_VALUE_TYPE dconst3;
3128 real_from_integer (&dconst3, VOIDmode, 3, 0, 0);
3129 real_arithmetic (&c2, MULT_EXPR, &c, &dconst3);
3130 real_round (&c2, mode, &c2);
3131 n = real_to_integer (&c2);
3132 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
3133 real_arithmetic (&c2, RDIV_EXPR, &cint, &dconst3);
3134 real_convert (&c2, mode, &c2);
3135 if (real_identical (&c2, &c)
3136 && ((optimize_insn_for_speed_p ()
3137 && powi_cost (n/3) <= POWI_MAX_MULTS)
3138 || n == 1))
3139 {
3140 tree call_expr = build_call_nofold (fn, 1,narg0);
3141 op = expand_builtin (call_expr, NULL_RTX, subtarget, mode, 0);
3142 if (abs (n) % 3 == 2)
3143 op = expand_simple_binop (mode, MULT, op, op, op,
3144 0, OPTAB_LIB_WIDEN);
3145 if (n != 1)
3146 {
3147 op2 = expand_expr (narg0, subtarget, VOIDmode, EXPAND_NORMAL);
3148 op2 = force_reg (mode, op2);
3149 op2 = expand_powi (op2, mode, abs (n / 3));
3150 op = expand_simple_binop (mode, MULT, op, op2, NULL_RTX,
3151 0, OPTAB_LIB_WIDEN);
3152 /* If the original exponent was negative, reciprocate the
3153 result. */
3154 if (n < 0)
3155 op = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
3156 op, NULL_RTX, 0, OPTAB_LIB_WIDEN);
3157 }
3158 return op;
3159 }
3160 }
3161
3162 /* Fall back to optab expansion. */
3163 return expand_builtin_mathfn_2 (exp, target, subtarget);
3164 }
3165
3166 /* Expand a call to the powi built-in mathematical function. Return NULL_RTX if
3167 a normal call should be emitted rather than expanding the function
3168 in-line. EXP is the expression that is a call to the builtin
3169 function; if convenient, the result should be placed in TARGET. */
3170
3171 static rtx
3172 expand_builtin_powi (tree exp, rtx target, rtx subtarget)
3173 {
3174 tree arg0, arg1;
3175 rtx op0, op1;
3176 enum machine_mode mode;
3177 enum machine_mode mode2;
3178
3179 if (! validate_arglist (exp, REAL_TYPE, INTEGER_TYPE, VOID_TYPE))
3180 return NULL_RTX;
3181
3182 arg0 = CALL_EXPR_ARG (exp, 0);
3183 arg1 = CALL_EXPR_ARG (exp, 1);
3184 mode = TYPE_MODE (TREE_TYPE (exp));
3185
3186 /* Handle constant power. */
3187
3188 if (TREE_CODE (arg1) == INTEGER_CST
3189 && !TREE_OVERFLOW (arg1))
3190 {
3191 HOST_WIDE_INT n = TREE_INT_CST_LOW (arg1);
3192
3193 /* If the exponent is -1, 0, 1 or 2, then expand_powi is exact.
3194 Otherwise, check the number of multiplications required. */
3195 if ((TREE_INT_CST_HIGH (arg1) == 0
3196 || TREE_INT_CST_HIGH (arg1) == -1)
3197 && ((n >= -1 && n <= 2)
3198 || (optimize_insn_for_speed_p ()
3199 && powi_cost (n) <= POWI_MAX_MULTS)))
3200 {
3201 op0 = expand_expr (arg0, subtarget, VOIDmode, EXPAND_NORMAL);
3202 op0 = force_reg (mode, op0);
3203 return expand_powi (op0, mode, n);
3204 }
3205 }
3206
3207 /* Emit a libcall to libgcc. */
3208
3209 /* Mode of the 2nd argument must match that of an int. */
3210 mode2 = mode_for_size (INT_TYPE_SIZE, MODE_INT, 0);
3211
3212 if (target == NULL_RTX)
3213 target = gen_reg_rtx (mode);
3214
3215 op0 = expand_expr (arg0, subtarget, mode, EXPAND_NORMAL);
3216 if (GET_MODE (op0) != mode)
3217 op0 = convert_to_mode (mode, op0, 0);
3218 op1 = expand_expr (arg1, NULL_RTX, mode2, EXPAND_NORMAL);
3219 if (GET_MODE (op1) != mode2)
3220 op1 = convert_to_mode (mode2, op1, 0);
3221
3222 target = emit_library_call_value (optab_libfunc (powi_optab, mode),
3223 target, LCT_CONST, mode, 2,
3224 op0, mode, op1, mode2);
3225
3226 return target;
3227 }
3228
3229 /* Expand expression EXP which is a call to the strlen builtin. Return
3230 NULL_RTX if we failed the caller should emit a normal call, otherwise
3231 try to get the result in TARGET, if convenient. */
3232
3233 static rtx
3234 expand_builtin_strlen (tree exp, rtx target,
3235 enum machine_mode target_mode)
3236 {
3237 if (!validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
3238 return NULL_RTX;
3239 else
3240 {
3241 rtx pat;
3242 tree len;
3243 tree src = CALL_EXPR_ARG (exp, 0);
3244 rtx result, src_reg, char_rtx, before_strlen;
3245 enum machine_mode insn_mode = target_mode, char_mode;
3246 enum insn_code icode = CODE_FOR_nothing;
3247 int align;
3248
3249 /* If the length can be computed at compile-time, return it. */
3250 len = c_strlen (src, 0);
3251 if (len)
3252 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
3253
3254 /* If the length can be computed at compile-time and is constant
3255 integer, but there are side-effects in src, evaluate
3256 src for side-effects, then return len.
3257 E.g. x = strlen (i++ ? "xfoo" + 1 : "bar");
3258 can be optimized into: i++; x = 3; */
3259 len = c_strlen (src, 1);
3260 if (len && TREE_CODE (len) == INTEGER_CST)
3261 {
3262 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
3263 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
3264 }
3265
3266 align = get_pointer_alignment (src, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3267
3268 /* If SRC is not a pointer type, don't do this operation inline. */
3269 if (align == 0)
3270 return NULL_RTX;
3271
3272 /* Bail out if we can't compute strlen in the right mode. */
3273 while (insn_mode != VOIDmode)
3274 {
3275 icode = optab_handler (strlen_optab, insn_mode)->insn_code;
3276 if (icode != CODE_FOR_nothing)
3277 break;
3278
3279 insn_mode = GET_MODE_WIDER_MODE (insn_mode);
3280 }
3281 if (insn_mode == VOIDmode)
3282 return NULL_RTX;
3283
3284 /* Make a place to write the result of the instruction. */
3285 result = target;
3286 if (! (result != 0
3287 && REG_P (result)
3288 && GET_MODE (result) == insn_mode
3289 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
3290 result = gen_reg_rtx (insn_mode);
3291
3292 /* Make a place to hold the source address. We will not expand
3293 the actual source until we are sure that the expansion will
3294 not fail -- there are trees that cannot be expanded twice. */
3295 src_reg = gen_reg_rtx (Pmode);
3296
3297 /* Mark the beginning of the strlen sequence so we can emit the
3298 source operand later. */
3299 before_strlen = get_last_insn ();
3300
3301 char_rtx = const0_rtx;
3302 char_mode = insn_data[(int) icode].operand[2].mode;
3303 if (! (*insn_data[(int) icode].operand[2].predicate) (char_rtx,
3304 char_mode))
3305 char_rtx = copy_to_mode_reg (char_mode, char_rtx);
3306
3307 pat = GEN_FCN (icode) (result, gen_rtx_MEM (BLKmode, src_reg),
3308 char_rtx, GEN_INT (align));
3309 if (! pat)
3310 return NULL_RTX;
3311 emit_insn (pat);
3312
3313 /* Now that we are assured of success, expand the source. */
3314 start_sequence ();
3315 pat = expand_expr (src, src_reg, ptr_mode, EXPAND_NORMAL);
3316 if (pat != src_reg)
3317 emit_move_insn (src_reg, pat);
3318 pat = get_insns ();
3319 end_sequence ();
3320
3321 if (before_strlen)
3322 emit_insn_after (pat, before_strlen);
3323 else
3324 emit_insn_before (pat, get_insns ());
3325
3326 /* Return the value in the proper mode for this function. */
3327 if (GET_MODE (result) == target_mode)
3328 target = result;
3329 else if (target != 0)
3330 convert_move (target, result, 0);
3331 else
3332 target = convert_to_mode (target_mode, result, 0);
3333
3334 return target;
3335 }
3336 }
3337
3338 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3339 bytes from constant string DATA + OFFSET and return it as target
3340 constant. */
3341
3342 static rtx
3343 builtin_memcpy_read_str (void *data, HOST_WIDE_INT offset,
3344 enum machine_mode mode)
3345 {
3346 const char *str = (const char *) data;
3347
3348 gcc_assert (offset >= 0
3349 && ((unsigned HOST_WIDE_INT) offset + GET_MODE_SIZE (mode)
3350 <= strlen (str) + 1));
3351
3352 return c_readstr (str + offset, mode);
3353 }
3354
3355 /* Expand a call EXP to the memcpy builtin.
3356 Return NULL_RTX if we failed, the caller should emit a normal call,
3357 otherwise try to get the result in TARGET, if convenient (and in
3358 mode MODE if that's convenient). */
3359
3360 static rtx
3361 expand_builtin_memcpy (tree exp, rtx target)
3362 {
3363 if (!validate_arglist (exp,
3364 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3365 return NULL_RTX;
3366 else
3367 {
3368 tree dest = CALL_EXPR_ARG (exp, 0);
3369 tree src = CALL_EXPR_ARG (exp, 1);
3370 tree len = CALL_EXPR_ARG (exp, 2);
3371 const char *src_str;
3372 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
3373 unsigned int dest_align
3374 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3375 rtx dest_mem, src_mem, dest_addr, len_rtx;
3376 HOST_WIDE_INT expected_size = -1;
3377 unsigned int expected_align = 0;
3378
3379 /* If DEST is not a pointer type, call the normal function. */
3380 if (dest_align == 0)
3381 return NULL_RTX;
3382
3383 /* If either SRC is not a pointer type, don't do this
3384 operation in-line. */
3385 if (src_align == 0)
3386 return NULL_RTX;
3387
3388 if (currently_expanding_gimple_stmt)
3389 stringop_block_profile (currently_expanding_gimple_stmt,
3390 &expected_align, &expected_size);
3391
3392 if (expected_align < dest_align)
3393 expected_align = dest_align;
3394 dest_mem = get_memory_rtx (dest, len);
3395 set_mem_align (dest_mem, dest_align);
3396 len_rtx = expand_normal (len);
3397 src_str = c_getstr (src);
3398
3399 /* If SRC is a string constant and block move would be done
3400 by pieces, we can avoid loading the string from memory
3401 and only stored the computed constants. */
3402 if (src_str
3403 && CONST_INT_P (len_rtx)
3404 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
3405 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
3406 CONST_CAST (char *, src_str),
3407 dest_align, false))
3408 {
3409 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
3410 builtin_memcpy_read_str,
3411 CONST_CAST (char *, src_str),
3412 dest_align, false, 0);
3413 dest_mem = force_operand (XEXP (dest_mem, 0), target);
3414 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3415 return dest_mem;
3416 }
3417
3418 src_mem = get_memory_rtx (src, len);
3419 set_mem_align (src_mem, src_align);
3420
3421 /* Copy word part most expediently. */
3422 dest_addr = emit_block_move_hints (dest_mem, src_mem, len_rtx,
3423 CALL_EXPR_TAILCALL (exp)
3424 ? BLOCK_OP_TAILCALL : BLOCK_OP_NORMAL,
3425 expected_align, expected_size);
3426
3427 if (dest_addr == 0)
3428 {
3429 dest_addr = force_operand (XEXP (dest_mem, 0), target);
3430 dest_addr = convert_memory_address (ptr_mode, dest_addr);
3431 }
3432 return dest_addr;
3433 }
3434 }
3435
3436 /* Expand a call EXP to the mempcpy builtin.
3437 Return NULL_RTX if we failed; the caller should emit a normal call,
3438 otherwise try to get the result in TARGET, if convenient (and in
3439 mode MODE if that's convenient). If ENDP is 0 return the
3440 destination pointer, if ENDP is 1 return the end pointer ala
3441 mempcpy, and if ENDP is 2 return the end pointer minus one ala
3442 stpcpy. */
3443
3444 static rtx
3445 expand_builtin_mempcpy (tree exp, rtx target, enum machine_mode mode)
3446 {
3447 if (!validate_arglist (exp,
3448 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3449 return NULL_RTX;
3450 else
3451 {
3452 tree dest = CALL_EXPR_ARG (exp, 0);
3453 tree src = CALL_EXPR_ARG (exp, 1);
3454 tree len = CALL_EXPR_ARG (exp, 2);
3455 return expand_builtin_mempcpy_args (dest, src, len,
3456 target, mode, /*endp=*/ 1);
3457 }
3458 }
3459
3460 /* Helper function to do the actual work for expand_builtin_mempcpy. The
3461 arguments to the builtin_mempcpy call DEST, SRC, and LEN are broken out
3462 so that this can also be called without constructing an actual CALL_EXPR.
3463 The other arguments and return value are the same as for
3464 expand_builtin_mempcpy. */
3465
3466 static rtx
3467 expand_builtin_mempcpy_args (tree dest, tree src, tree len,
3468 rtx target, enum machine_mode mode, int endp)
3469 {
3470 /* If return value is ignored, transform mempcpy into memcpy. */
3471 if (target == const0_rtx && implicit_built_in_decls[BUILT_IN_MEMCPY])
3472 {
3473 tree fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
3474 tree result = build_call_nofold (fn, 3, dest, src, len);
3475 return expand_expr (result, target, mode, EXPAND_NORMAL);
3476 }
3477 else
3478 {
3479 const char *src_str;
3480 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
3481 unsigned int dest_align
3482 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3483 rtx dest_mem, src_mem, len_rtx;
3484
3485 /* If either SRC or DEST is not a pointer type, don't do this
3486 operation in-line. */
3487 if (dest_align == 0 || src_align == 0)
3488 return NULL_RTX;
3489
3490 /* If LEN is not constant, call the normal function. */
3491 if (! host_integerp (len, 1))
3492 return NULL_RTX;
3493
3494 len_rtx = expand_normal (len);
3495 src_str = c_getstr (src);
3496
3497 /* If SRC is a string constant and block move would be done
3498 by pieces, we can avoid loading the string from memory
3499 and only stored the computed constants. */
3500 if (src_str
3501 && CONST_INT_P (len_rtx)
3502 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
3503 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
3504 CONST_CAST (char *, src_str),
3505 dest_align, false))
3506 {
3507 dest_mem = get_memory_rtx (dest, len);
3508 set_mem_align (dest_mem, dest_align);
3509 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
3510 builtin_memcpy_read_str,
3511 CONST_CAST (char *, src_str),
3512 dest_align, false, endp);
3513 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3514 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3515 return dest_mem;
3516 }
3517
3518 if (CONST_INT_P (len_rtx)
3519 && can_move_by_pieces (INTVAL (len_rtx),
3520 MIN (dest_align, src_align)))
3521 {
3522 dest_mem = get_memory_rtx (dest, len);
3523 set_mem_align (dest_mem, dest_align);
3524 src_mem = get_memory_rtx (src, len);
3525 set_mem_align (src_mem, src_align);
3526 dest_mem = move_by_pieces (dest_mem, src_mem, INTVAL (len_rtx),
3527 MIN (dest_align, src_align), endp);
3528 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3529 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3530 return dest_mem;
3531 }
3532
3533 return NULL_RTX;
3534 }
3535 }
3536
3537 #ifndef HAVE_movstr
3538 # define HAVE_movstr 0
3539 # define CODE_FOR_movstr CODE_FOR_nothing
3540 #endif
3541
3542 /* Expand into a movstr instruction, if one is available. Return NULL_RTX if
3543 we failed, the caller should emit a normal call, otherwise try to
3544 get the result in TARGET, if convenient. If ENDP is 0 return the
3545 destination pointer, if ENDP is 1 return the end pointer ala
3546 mempcpy, and if ENDP is 2 return the end pointer minus one ala
3547 stpcpy. */
3548
3549 static rtx
3550 expand_movstr (tree dest, tree src, rtx target, int endp)
3551 {
3552 rtx end;
3553 rtx dest_mem;
3554 rtx src_mem;
3555 rtx insn;
3556 const struct insn_data * data;
3557
3558 if (!HAVE_movstr)
3559 return NULL_RTX;
3560
3561 dest_mem = get_memory_rtx (dest, NULL);
3562 src_mem = get_memory_rtx (src, NULL);
3563 if (!endp)
3564 {
3565 target = force_reg (Pmode, XEXP (dest_mem, 0));
3566 dest_mem = replace_equiv_address (dest_mem, target);
3567 end = gen_reg_rtx (Pmode);
3568 }
3569 else
3570 {
3571 if (target == 0 || target == const0_rtx)
3572 {
3573 end = gen_reg_rtx (Pmode);
3574 if (target == 0)
3575 target = end;
3576 }
3577 else
3578 end = target;
3579 }
3580
3581 data = insn_data + CODE_FOR_movstr;
3582
3583 if (data->operand[0].mode != VOIDmode)
3584 end = gen_lowpart (data->operand[0].mode, end);
3585
3586 insn = data->genfun (end, dest_mem, src_mem);
3587
3588 gcc_assert (insn);
3589
3590 emit_insn (insn);
3591
3592 /* movstr is supposed to set end to the address of the NUL
3593 terminator. If the caller requested a mempcpy-like return value,
3594 adjust it. */
3595 if (endp == 1 && target != const0_rtx)
3596 {
3597 rtx tem = plus_constant (gen_lowpart (GET_MODE (target), end), 1);
3598 emit_move_insn (target, force_operand (tem, NULL_RTX));
3599 }
3600
3601 return target;
3602 }
3603
3604 /* Expand expression EXP, which is a call to the strcpy builtin. Return
3605 NULL_RTX if we failed the caller should emit a normal call, otherwise
3606 try to get the result in TARGET, if convenient (and in mode MODE if that's
3607 convenient). */
3608
3609 static rtx
3610 expand_builtin_strcpy (tree exp, rtx target)
3611 {
3612 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3613 {
3614 tree dest = CALL_EXPR_ARG (exp, 0);
3615 tree src = CALL_EXPR_ARG (exp, 1);
3616 return expand_builtin_strcpy_args (dest, src, target);
3617 }
3618 return NULL_RTX;
3619 }
3620
3621 /* Helper function to do the actual work for expand_builtin_strcpy. The
3622 arguments to the builtin_strcpy call DEST and SRC are broken out
3623 so that this can also be called without constructing an actual CALL_EXPR.
3624 The other arguments and return value are the same as for
3625 expand_builtin_strcpy. */
3626
3627 static rtx
3628 expand_builtin_strcpy_args (tree dest, tree src, rtx target)
3629 {
3630 return expand_movstr (dest, src, target, /*endp=*/0);
3631 }
3632
3633 /* Expand a call EXP to the stpcpy builtin.
3634 Return NULL_RTX if we failed the caller should emit a normal call,
3635 otherwise try to get the result in TARGET, if convenient (and in
3636 mode MODE if that's convenient). */
3637
3638 static rtx
3639 expand_builtin_stpcpy (tree exp, rtx target, enum machine_mode mode)
3640 {
3641 tree dst, src;
3642 location_t loc = EXPR_LOCATION (exp);
3643
3644 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3645 return NULL_RTX;
3646
3647 dst = CALL_EXPR_ARG (exp, 0);
3648 src = CALL_EXPR_ARG (exp, 1);
3649
3650 /* If return value is ignored, transform stpcpy into strcpy. */
3651 if (target == const0_rtx && implicit_built_in_decls[BUILT_IN_STRCPY])
3652 {
3653 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
3654 tree result = build_call_nofold (fn, 2, dst, src);
3655 return expand_expr (result, target, mode, EXPAND_NORMAL);
3656 }
3657 else
3658 {
3659 tree len, lenp1;
3660 rtx ret;
3661
3662 /* Ensure we get an actual string whose length can be evaluated at
3663 compile-time, not an expression containing a string. This is
3664 because the latter will potentially produce pessimized code
3665 when used to produce the return value. */
3666 if (! c_getstr (src) || ! (len = c_strlen (src, 0)))
3667 return expand_movstr (dst, src, target, /*endp=*/2);
3668
3669 lenp1 = size_binop_loc (loc, PLUS_EXPR, len, ssize_int (1));
3670 ret = expand_builtin_mempcpy_args (dst, src, lenp1,
3671 target, mode, /*endp=*/2);
3672
3673 if (ret)
3674 return ret;
3675
3676 if (TREE_CODE (len) == INTEGER_CST)
3677 {
3678 rtx len_rtx = expand_normal (len);
3679
3680 if (CONST_INT_P (len_rtx))
3681 {
3682 ret = expand_builtin_strcpy_args (dst, src, target);
3683
3684 if (ret)
3685 {
3686 if (! target)
3687 {
3688 if (mode != VOIDmode)
3689 target = gen_reg_rtx (mode);
3690 else
3691 target = gen_reg_rtx (GET_MODE (ret));
3692 }
3693 if (GET_MODE (target) != GET_MODE (ret))
3694 ret = gen_lowpart (GET_MODE (target), ret);
3695
3696 ret = plus_constant (ret, INTVAL (len_rtx));
3697 ret = emit_move_insn (target, force_operand (ret, NULL_RTX));
3698 gcc_assert (ret);
3699
3700 return target;
3701 }
3702 }
3703 }
3704
3705 return expand_movstr (dst, src, target, /*endp=*/2);
3706 }
3707 }
3708
3709 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3710 bytes from constant string DATA + OFFSET and return it as target
3711 constant. */
3712
3713 rtx
3714 builtin_strncpy_read_str (void *data, HOST_WIDE_INT offset,
3715 enum machine_mode mode)
3716 {
3717 const char *str = (const char *) data;
3718
3719 if ((unsigned HOST_WIDE_INT) offset > strlen (str))
3720 return const0_rtx;
3721
3722 return c_readstr (str + offset, mode);
3723 }
3724
3725 /* Expand expression EXP, which is a call to the strncpy builtin. Return
3726 NULL_RTX if we failed the caller should emit a normal call. */
3727
3728 static rtx
3729 expand_builtin_strncpy (tree exp, rtx target)
3730 {
3731 location_t loc = EXPR_LOCATION (exp);
3732
3733 if (validate_arglist (exp,
3734 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3735 {
3736 tree dest = CALL_EXPR_ARG (exp, 0);
3737 tree src = CALL_EXPR_ARG (exp, 1);
3738 tree len = CALL_EXPR_ARG (exp, 2);
3739 tree slen = c_strlen (src, 1);
3740
3741 /* We must be passed a constant len and src parameter. */
3742 if (!host_integerp (len, 1) || !slen || !host_integerp (slen, 1))
3743 return NULL_RTX;
3744
3745 slen = size_binop_loc (loc, PLUS_EXPR, slen, ssize_int (1));
3746
3747 /* We're required to pad with trailing zeros if the requested
3748 len is greater than strlen(s2)+1. In that case try to
3749 use store_by_pieces, if it fails, punt. */
3750 if (tree_int_cst_lt (slen, len))
3751 {
3752 unsigned int dest_align
3753 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3754 const char *p = c_getstr (src);
3755 rtx dest_mem;
3756
3757 if (!p || dest_align == 0 || !host_integerp (len, 1)
3758 || !can_store_by_pieces (tree_low_cst (len, 1),
3759 builtin_strncpy_read_str,
3760 CONST_CAST (char *, p),
3761 dest_align, false))
3762 return NULL_RTX;
3763
3764 dest_mem = get_memory_rtx (dest, len);
3765 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3766 builtin_strncpy_read_str,
3767 CONST_CAST (char *, p), dest_align, false, 0);
3768 dest_mem = force_operand (XEXP (dest_mem, 0), target);
3769 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3770 return dest_mem;
3771 }
3772 }
3773 return NULL_RTX;
3774 }
3775
3776 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3777 bytes from constant string DATA + OFFSET and return it as target
3778 constant. */
3779
3780 rtx
3781 builtin_memset_read_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3782 enum machine_mode mode)
3783 {
3784 const char *c = (const char *) data;
3785 char *p = XALLOCAVEC (char, GET_MODE_SIZE (mode));
3786
3787 memset (p, *c, GET_MODE_SIZE (mode));
3788
3789 return c_readstr (p, mode);
3790 }
3791
3792 /* Callback routine for store_by_pieces. Return the RTL of a register
3793 containing GET_MODE_SIZE (MODE) consecutive copies of the unsigned
3794 char value given in the RTL register data. For example, if mode is
3795 4 bytes wide, return the RTL for 0x01010101*data. */
3796
3797 static rtx
3798 builtin_memset_gen_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3799 enum machine_mode mode)
3800 {
3801 rtx target, coeff;
3802 size_t size;
3803 char *p;
3804
3805 size = GET_MODE_SIZE (mode);
3806 if (size == 1)
3807 return (rtx) data;
3808
3809 p = XALLOCAVEC (char, size);
3810 memset (p, 1, size);
3811 coeff = c_readstr (p, mode);
3812
3813 target = convert_to_mode (mode, (rtx) data, 1);
3814 target = expand_mult (mode, target, coeff, NULL_RTX, 1);
3815 return force_reg (mode, target);
3816 }
3817
3818 /* Expand expression EXP, which is a call to the memset builtin. Return
3819 NULL_RTX if we failed the caller should emit a normal call, otherwise
3820 try to get the result in TARGET, if convenient (and in mode MODE if that's
3821 convenient). */
3822
3823 static rtx
3824 expand_builtin_memset (tree exp, rtx target, enum machine_mode mode)
3825 {
3826 if (!validate_arglist (exp,
3827 POINTER_TYPE, INTEGER_TYPE, INTEGER_TYPE, VOID_TYPE))
3828 return NULL_RTX;
3829 else
3830 {
3831 tree dest = CALL_EXPR_ARG (exp, 0);
3832 tree val = CALL_EXPR_ARG (exp, 1);
3833 tree len = CALL_EXPR_ARG (exp, 2);
3834 return expand_builtin_memset_args (dest, val, len, target, mode, exp);
3835 }
3836 }
3837
3838 /* Helper function to do the actual work for expand_builtin_memset. The
3839 arguments to the builtin_memset call DEST, VAL, and LEN are broken out
3840 so that this can also be called without constructing an actual CALL_EXPR.
3841 The other arguments and return value are the same as for
3842 expand_builtin_memset. */
3843
3844 static rtx
3845 expand_builtin_memset_args (tree dest, tree val, tree len,
3846 rtx target, enum machine_mode mode, tree orig_exp)
3847 {
3848 tree fndecl, fn;
3849 enum built_in_function fcode;
3850 char c;
3851 unsigned int dest_align;
3852 rtx dest_mem, dest_addr, len_rtx;
3853 HOST_WIDE_INT expected_size = -1;
3854 unsigned int expected_align = 0;
3855
3856 dest_align = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3857
3858 /* If DEST is not a pointer type, don't do this operation in-line. */
3859 if (dest_align == 0)
3860 return NULL_RTX;
3861
3862 if (currently_expanding_gimple_stmt)
3863 stringop_block_profile (currently_expanding_gimple_stmt,
3864 &expected_align, &expected_size);
3865
3866 if (expected_align < dest_align)
3867 expected_align = dest_align;
3868
3869 /* If the LEN parameter is zero, return DEST. */
3870 if (integer_zerop (len))
3871 {
3872 /* Evaluate and ignore VAL in case it has side-effects. */
3873 expand_expr (val, const0_rtx, VOIDmode, EXPAND_NORMAL);
3874 return expand_expr (dest, target, mode, EXPAND_NORMAL);
3875 }
3876
3877 /* Stabilize the arguments in case we fail. */
3878 dest = builtin_save_expr (dest);
3879 val = builtin_save_expr (val);
3880 len = builtin_save_expr (len);
3881
3882 len_rtx = expand_normal (len);
3883 dest_mem = get_memory_rtx (dest, len);
3884
3885 if (TREE_CODE (val) != INTEGER_CST)
3886 {
3887 rtx val_rtx;
3888
3889 val_rtx = expand_normal (val);
3890 val_rtx = convert_to_mode (TYPE_MODE (unsigned_char_type_node),
3891 val_rtx, 0);
3892
3893 /* Assume that we can memset by pieces if we can store
3894 * the coefficients by pieces (in the required modes).
3895 * We can't pass builtin_memset_gen_str as that emits RTL. */
3896 c = 1;
3897 if (host_integerp (len, 1)
3898 && can_store_by_pieces (tree_low_cst (len, 1),
3899 builtin_memset_read_str, &c, dest_align,
3900 true))
3901 {
3902 val_rtx = force_reg (TYPE_MODE (unsigned_char_type_node),
3903 val_rtx);
3904 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3905 builtin_memset_gen_str, val_rtx, dest_align,
3906 true, 0);
3907 }
3908 else if (!set_storage_via_setmem (dest_mem, len_rtx, val_rtx,
3909 dest_align, expected_align,
3910 expected_size))
3911 goto do_libcall;
3912
3913 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3914 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3915 return dest_mem;
3916 }
3917
3918 if (target_char_cast (val, &c))
3919 goto do_libcall;
3920
3921 if (c)
3922 {
3923 if (host_integerp (len, 1)
3924 && can_store_by_pieces (tree_low_cst (len, 1),
3925 builtin_memset_read_str, &c, dest_align,
3926 true))
3927 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3928 builtin_memset_read_str, &c, dest_align, true, 0);
3929 else if (!set_storage_via_setmem (dest_mem, len_rtx, GEN_INT (c),
3930 dest_align, expected_align,
3931 expected_size))
3932 goto do_libcall;
3933
3934 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3935 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3936 return dest_mem;
3937 }
3938
3939 set_mem_align (dest_mem, dest_align);
3940 dest_addr = clear_storage_hints (dest_mem, len_rtx,
3941 CALL_EXPR_TAILCALL (orig_exp)
3942 ? BLOCK_OP_TAILCALL : BLOCK_OP_NORMAL,
3943 expected_align, expected_size);
3944
3945 if (dest_addr == 0)
3946 {
3947 dest_addr = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3948 dest_addr = convert_memory_address (ptr_mode, dest_addr);
3949 }
3950
3951 return dest_addr;
3952
3953 do_libcall:
3954 fndecl = get_callee_fndecl (orig_exp);
3955 fcode = DECL_FUNCTION_CODE (fndecl);
3956 if (fcode == BUILT_IN_MEMSET)
3957 fn = build_call_nofold (fndecl, 3, dest, val, len);
3958 else if (fcode == BUILT_IN_BZERO)
3959 fn = build_call_nofold (fndecl, 2, dest, len);
3960 else
3961 gcc_unreachable ();
3962 gcc_assert (TREE_CODE (fn) == CALL_EXPR);
3963 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (orig_exp);
3964 return expand_call (fn, target, target == const0_rtx);
3965 }
3966
3967 /* Expand expression EXP, which is a call to the bzero builtin. Return
3968 NULL_RTX if we failed the caller should emit a normal call. */
3969
3970 static rtx
3971 expand_builtin_bzero (tree exp)
3972 {
3973 tree dest, size;
3974 location_t loc = EXPR_LOCATION (exp);
3975
3976 if (!validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3977 return NULL_RTX;
3978
3979 dest = CALL_EXPR_ARG (exp, 0);
3980 size = CALL_EXPR_ARG (exp, 1);
3981
3982 /* New argument list transforming bzero(ptr x, int y) to
3983 memset(ptr x, int 0, size_t y). This is done this way
3984 so that if it isn't expanded inline, we fallback to
3985 calling bzero instead of memset. */
3986
3987 return expand_builtin_memset_args (dest, integer_zero_node,
3988 fold_convert_loc (loc, sizetype, size),
3989 const0_rtx, VOIDmode, exp);
3990 }
3991
3992 /* Expand expression EXP, which is a call to the memcmp built-in function.
3993 Return NULL_RTX if we failed and the
3994 caller should emit a normal call, otherwise try to get the result in
3995 TARGET, if convenient (and in mode MODE, if that's convenient). */
3996
3997 static rtx
3998 expand_builtin_memcmp (tree exp, ATTRIBUTE_UNUSED rtx target,
3999 ATTRIBUTE_UNUSED enum machine_mode mode)
4000 {
4001 location_t loc ATTRIBUTE_UNUSED = EXPR_LOCATION (exp);
4002
4003 if (!validate_arglist (exp,
4004 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4005 return NULL_RTX;
4006
4007 #if defined HAVE_cmpmemsi || defined HAVE_cmpstrnsi
4008 {
4009 rtx arg1_rtx, arg2_rtx, arg3_rtx;
4010 rtx result;
4011 rtx insn;
4012 tree arg1 = CALL_EXPR_ARG (exp, 0);
4013 tree arg2 = CALL_EXPR_ARG (exp, 1);
4014 tree len = CALL_EXPR_ARG (exp, 2);
4015
4016 int arg1_align
4017 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4018 int arg2_align
4019 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4020 enum machine_mode insn_mode;
4021
4022 #ifdef HAVE_cmpmemsi
4023 if (HAVE_cmpmemsi)
4024 insn_mode = insn_data[(int) CODE_FOR_cmpmemsi].operand[0].mode;
4025 else
4026 #endif
4027 #ifdef HAVE_cmpstrnsi
4028 if (HAVE_cmpstrnsi)
4029 insn_mode = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4030 else
4031 #endif
4032 return NULL_RTX;
4033
4034 /* If we don't have POINTER_TYPE, call the function. */
4035 if (arg1_align == 0 || arg2_align == 0)
4036 return NULL_RTX;
4037
4038 /* Make a place to write the result of the instruction. */
4039 result = target;
4040 if (! (result != 0
4041 && REG_P (result) && GET_MODE (result) == insn_mode
4042 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4043 result = gen_reg_rtx (insn_mode);
4044
4045 arg1_rtx = get_memory_rtx (arg1, len);
4046 arg2_rtx = get_memory_rtx (arg2, len);
4047 arg3_rtx = expand_normal (fold_convert_loc (loc, sizetype, len));
4048
4049 /* Set MEM_SIZE as appropriate. */
4050 if (CONST_INT_P (arg3_rtx))
4051 {
4052 set_mem_size (arg1_rtx, arg3_rtx);
4053 set_mem_size (arg2_rtx, arg3_rtx);
4054 }
4055
4056 #ifdef HAVE_cmpmemsi
4057 if (HAVE_cmpmemsi)
4058 insn = gen_cmpmemsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4059 GEN_INT (MIN (arg1_align, arg2_align)));
4060 else
4061 #endif
4062 #ifdef HAVE_cmpstrnsi
4063 if (HAVE_cmpstrnsi)
4064 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4065 GEN_INT (MIN (arg1_align, arg2_align)));
4066 else
4067 #endif
4068 gcc_unreachable ();
4069
4070 if (insn)
4071 emit_insn (insn);
4072 else
4073 emit_library_call_value (memcmp_libfunc, result, LCT_PURE,
4074 TYPE_MODE (integer_type_node), 3,
4075 XEXP (arg1_rtx, 0), Pmode,
4076 XEXP (arg2_rtx, 0), Pmode,
4077 convert_to_mode (TYPE_MODE (sizetype), arg3_rtx,
4078 TYPE_UNSIGNED (sizetype)),
4079 TYPE_MODE (sizetype));
4080
4081 /* Return the value in the proper mode for this function. */
4082 mode = TYPE_MODE (TREE_TYPE (exp));
4083 if (GET_MODE (result) == mode)
4084 return result;
4085 else if (target != 0)
4086 {
4087 convert_move (target, result, 0);
4088 return target;
4089 }
4090 else
4091 return convert_to_mode (mode, result, 0);
4092 }
4093 #endif
4094
4095 return NULL_RTX;
4096 }
4097
4098 /* Expand expression EXP, which is a call to the strcmp builtin. Return NULL_RTX
4099 if we failed the caller should emit a normal call, otherwise try to get
4100 the result in TARGET, if convenient. */
4101
4102 static rtx
4103 expand_builtin_strcmp (tree exp, ATTRIBUTE_UNUSED rtx target)
4104 {
4105 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4106 return NULL_RTX;
4107
4108 #if defined HAVE_cmpstrsi || defined HAVE_cmpstrnsi
4109 if (cmpstr_optab[SImode] != CODE_FOR_nothing
4110 || cmpstrn_optab[SImode] != CODE_FOR_nothing)
4111 {
4112 rtx arg1_rtx, arg2_rtx;
4113 rtx result, insn = NULL_RTX;
4114 tree fndecl, fn;
4115 tree arg1 = CALL_EXPR_ARG (exp, 0);
4116 tree arg2 = CALL_EXPR_ARG (exp, 1);
4117
4118 int arg1_align
4119 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4120 int arg2_align
4121 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4122
4123 /* If we don't have POINTER_TYPE, call the function. */
4124 if (arg1_align == 0 || arg2_align == 0)
4125 return NULL_RTX;
4126
4127 /* Stabilize the arguments in case gen_cmpstr(n)si fail. */
4128 arg1 = builtin_save_expr (arg1);
4129 arg2 = builtin_save_expr (arg2);
4130
4131 arg1_rtx = get_memory_rtx (arg1, NULL);
4132 arg2_rtx = get_memory_rtx (arg2, NULL);
4133
4134 #ifdef HAVE_cmpstrsi
4135 /* Try to call cmpstrsi. */
4136 if (HAVE_cmpstrsi)
4137 {
4138 enum machine_mode insn_mode
4139 = insn_data[(int) CODE_FOR_cmpstrsi].operand[0].mode;
4140
4141 /* Make a place to write the result of the instruction. */
4142 result = target;
4143 if (! (result != 0
4144 && REG_P (result) && GET_MODE (result) == insn_mode
4145 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4146 result = gen_reg_rtx (insn_mode);
4147
4148 insn = gen_cmpstrsi (result, arg1_rtx, arg2_rtx,
4149 GEN_INT (MIN (arg1_align, arg2_align)));
4150 }
4151 #endif
4152 #ifdef HAVE_cmpstrnsi
4153 /* Try to determine at least one length and call cmpstrnsi. */
4154 if (!insn && HAVE_cmpstrnsi)
4155 {
4156 tree len;
4157 rtx arg3_rtx;
4158
4159 enum machine_mode insn_mode
4160 = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4161 tree len1 = c_strlen (arg1, 1);
4162 tree len2 = c_strlen (arg2, 1);
4163
4164 if (len1)
4165 len1 = size_binop (PLUS_EXPR, ssize_int (1), len1);
4166 if (len2)
4167 len2 = size_binop (PLUS_EXPR, ssize_int (1), len2);
4168
4169 /* If we don't have a constant length for the first, use the length
4170 of the second, if we know it. We don't require a constant for
4171 this case; some cost analysis could be done if both are available
4172 but neither is constant. For now, assume they're equally cheap,
4173 unless one has side effects. If both strings have constant lengths,
4174 use the smaller. */
4175
4176 if (!len1)
4177 len = len2;
4178 else if (!len2)
4179 len = len1;
4180 else if (TREE_SIDE_EFFECTS (len1))
4181 len = len2;
4182 else if (TREE_SIDE_EFFECTS (len2))
4183 len = len1;
4184 else if (TREE_CODE (len1) != INTEGER_CST)
4185 len = len2;
4186 else if (TREE_CODE (len2) != INTEGER_CST)
4187 len = len1;
4188 else if (tree_int_cst_lt (len1, len2))
4189 len = len1;
4190 else
4191 len = len2;
4192
4193 /* If both arguments have side effects, we cannot optimize. */
4194 if (!len || TREE_SIDE_EFFECTS (len))
4195 goto do_libcall;
4196
4197 arg3_rtx = expand_normal (len);
4198
4199 /* Make a place to write the result of the instruction. */
4200 result = target;
4201 if (! (result != 0
4202 && REG_P (result) && GET_MODE (result) == insn_mode
4203 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4204 result = gen_reg_rtx (insn_mode);
4205
4206 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4207 GEN_INT (MIN (arg1_align, arg2_align)));
4208 }
4209 #endif
4210
4211 if (insn)
4212 {
4213 enum machine_mode mode;
4214 emit_insn (insn);
4215
4216 /* Return the value in the proper mode for this function. */
4217 mode = TYPE_MODE (TREE_TYPE (exp));
4218 if (GET_MODE (result) == mode)
4219 return result;
4220 if (target == 0)
4221 return convert_to_mode (mode, result, 0);
4222 convert_move (target, result, 0);
4223 return target;
4224 }
4225
4226 /* Expand the library call ourselves using a stabilized argument
4227 list to avoid re-evaluating the function's arguments twice. */
4228 #ifdef HAVE_cmpstrnsi
4229 do_libcall:
4230 #endif
4231 fndecl = get_callee_fndecl (exp);
4232 fn = build_call_nofold (fndecl, 2, arg1, arg2);
4233 gcc_assert (TREE_CODE (fn) == CALL_EXPR);
4234 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
4235 return expand_call (fn, target, target == const0_rtx);
4236 }
4237 #endif
4238 return NULL_RTX;
4239 }
4240
4241 /* Expand expression EXP, which is a call to the strncmp builtin. Return
4242 NULL_RTX if we failed the caller should emit a normal call, otherwise try to get
4243 the result in TARGET, if convenient. */
4244
4245 static rtx
4246 expand_builtin_strncmp (tree exp, ATTRIBUTE_UNUSED rtx target,
4247 ATTRIBUTE_UNUSED enum machine_mode mode)
4248 {
4249 location_t loc ATTRIBUTE_UNUSED = EXPR_LOCATION (exp);
4250
4251 if (!validate_arglist (exp,
4252 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
4253 return NULL_RTX;
4254
4255 /* If c_strlen can determine an expression for one of the string
4256 lengths, and it doesn't have side effects, then emit cmpstrnsi
4257 using length MIN(strlen(string)+1, arg3). */
4258 #ifdef HAVE_cmpstrnsi
4259 if (HAVE_cmpstrnsi)
4260 {
4261 tree len, len1, len2;
4262 rtx arg1_rtx, arg2_rtx, arg3_rtx;
4263 rtx result, insn;
4264 tree fndecl, fn;
4265 tree arg1 = CALL_EXPR_ARG (exp, 0);
4266 tree arg2 = CALL_EXPR_ARG (exp, 1);
4267 tree arg3 = CALL_EXPR_ARG (exp, 2);
4268
4269 int arg1_align
4270 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4271 int arg2_align
4272 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
4273 enum machine_mode insn_mode
4274 = insn_data[(int) CODE_FOR_cmpstrnsi].operand[0].mode;
4275
4276 len1 = c_strlen (arg1, 1);
4277 len2 = c_strlen (arg2, 1);
4278
4279 if (len1)
4280 len1 = size_binop_loc (loc, PLUS_EXPR, ssize_int (1), len1);
4281 if (len2)
4282 len2 = size_binop_loc (loc, PLUS_EXPR, ssize_int (1), len2);
4283
4284 /* If we don't have a constant length for the first, use the length
4285 of the second, if we know it. We don't require a constant for
4286 this case; some cost analysis could be done if both are available
4287 but neither is constant. For now, assume they're equally cheap,
4288 unless one has side effects. If both strings have constant lengths,
4289 use the smaller. */
4290
4291 if (!len1)
4292 len = len2;
4293 else if (!len2)
4294 len = len1;
4295 else if (TREE_SIDE_EFFECTS (len1))
4296 len = len2;
4297 else if (TREE_SIDE_EFFECTS (len2))
4298 len = len1;
4299 else if (TREE_CODE (len1) != INTEGER_CST)
4300 len = len2;
4301 else if (TREE_CODE (len2) != INTEGER_CST)
4302 len = len1;
4303 else if (tree_int_cst_lt (len1, len2))
4304 len = len1;
4305 else
4306 len = len2;
4307
4308 /* If both arguments have side effects, we cannot optimize. */
4309 if (!len || TREE_SIDE_EFFECTS (len))
4310 return NULL_RTX;
4311
4312 /* The actual new length parameter is MIN(len,arg3). */
4313 len = fold_build2_loc (loc, MIN_EXPR, TREE_TYPE (len), len,
4314 fold_convert_loc (loc, TREE_TYPE (len), arg3));
4315
4316 /* If we don't have POINTER_TYPE, call the function. */
4317 if (arg1_align == 0 || arg2_align == 0)
4318 return NULL_RTX;
4319
4320 /* Make a place to write the result of the instruction. */
4321 result = target;
4322 if (! (result != 0
4323 && REG_P (result) && GET_MODE (result) == insn_mode
4324 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
4325 result = gen_reg_rtx (insn_mode);
4326
4327 /* Stabilize the arguments in case gen_cmpstrnsi fails. */
4328 arg1 = builtin_save_expr (arg1);
4329 arg2 = builtin_save_expr (arg2);
4330 len = builtin_save_expr (len);
4331
4332 arg1_rtx = get_memory_rtx (arg1, len);
4333 arg2_rtx = get_memory_rtx (arg2, len);
4334 arg3_rtx = expand_normal (len);
4335 insn = gen_cmpstrnsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
4336 GEN_INT (MIN (arg1_align, arg2_align)));
4337 if (insn)
4338 {
4339 emit_insn (insn);
4340
4341 /* Return the value in the proper mode for this function. */
4342 mode = TYPE_MODE (TREE_TYPE (exp));
4343 if (GET_MODE (result) == mode)
4344 return result;
4345 if (target == 0)
4346 return convert_to_mode (mode, result, 0);
4347 convert_move (target, result, 0);
4348 return target;
4349 }
4350
4351 /* Expand the library call ourselves using a stabilized argument
4352 list to avoid re-evaluating the function's arguments twice. */
4353 fndecl = get_callee_fndecl (exp);
4354 fn = build_call_nofold (fndecl, 3, arg1, arg2, len);
4355 gcc_assert (TREE_CODE (fn) == CALL_EXPR);
4356 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
4357 return expand_call (fn, target, target == const0_rtx);
4358 }
4359 #endif
4360 return NULL_RTX;
4361 }
4362
4363 /* Expand a call to __builtin_saveregs, generating the result in TARGET,
4364 if that's convenient. */
4365
4366 rtx
4367 expand_builtin_saveregs (void)
4368 {
4369 rtx val, seq;
4370
4371 /* Don't do __builtin_saveregs more than once in a function.
4372 Save the result of the first call and reuse it. */
4373 if (saveregs_value != 0)
4374 return saveregs_value;
4375
4376 /* When this function is called, it means that registers must be
4377 saved on entry to this function. So we migrate the call to the
4378 first insn of this function. */
4379
4380 start_sequence ();
4381
4382 /* Do whatever the machine needs done in this case. */
4383 val = targetm.calls.expand_builtin_saveregs ();
4384
4385 seq = get_insns ();
4386 end_sequence ();
4387
4388 saveregs_value = val;
4389
4390 /* Put the insns after the NOTE that starts the function. If this
4391 is inside a start_sequence, make the outer-level insn chain current, so
4392 the code is placed at the start of the function. */
4393 push_topmost_sequence ();
4394 emit_insn_after (seq, entry_of_function ());
4395 pop_topmost_sequence ();
4396
4397 return val;
4398 }
4399
4400 /* __builtin_args_info (N) returns word N of the arg space info
4401 for the current function. The number and meanings of words
4402 is controlled by the definition of CUMULATIVE_ARGS. */
4403
4404 static rtx
4405 expand_builtin_args_info (tree exp)
4406 {
4407 int nwords = sizeof (CUMULATIVE_ARGS) / sizeof (int);
4408 int *word_ptr = (int *) &crtl->args.info;
4409
4410 gcc_assert (sizeof (CUMULATIVE_ARGS) % sizeof (int) == 0);
4411
4412 if (call_expr_nargs (exp) != 0)
4413 {
4414 if (!host_integerp (CALL_EXPR_ARG (exp, 0), 0))
4415 error ("argument of %<__builtin_args_info%> must be constant");
4416 else
4417 {
4418 HOST_WIDE_INT wordnum = tree_low_cst (CALL_EXPR_ARG (exp, 0), 0);
4419
4420 if (wordnum < 0 || wordnum >= nwords)
4421 error ("argument of %<__builtin_args_info%> out of range");
4422 else
4423 return GEN_INT (word_ptr[wordnum]);
4424 }
4425 }
4426 else
4427 error ("missing argument in %<__builtin_args_info%>");
4428
4429 return const0_rtx;
4430 }
4431
4432 /* Expand a call to __builtin_next_arg. */
4433
4434 static rtx
4435 expand_builtin_next_arg (void)
4436 {
4437 /* Checking arguments is already done in fold_builtin_next_arg
4438 that must be called before this function. */
4439 return expand_binop (ptr_mode, add_optab,
4440 crtl->args.internal_arg_pointer,
4441 crtl->args.arg_offset_rtx,
4442 NULL_RTX, 0, OPTAB_LIB_WIDEN);
4443 }
4444
4445 /* Make it easier for the backends by protecting the valist argument
4446 from multiple evaluations. */
4447
4448 static tree
4449 stabilize_va_list_loc (location_t loc, tree valist, int needs_lvalue)
4450 {
4451 tree vatype = targetm.canonical_va_list_type (TREE_TYPE (valist));
4452
4453 gcc_assert (vatype != NULL_TREE);
4454
4455 if (TREE_CODE (vatype) == ARRAY_TYPE)
4456 {
4457 if (TREE_SIDE_EFFECTS (valist))
4458 valist = save_expr (valist);
4459
4460 /* For this case, the backends will be expecting a pointer to
4461 vatype, but it's possible we've actually been given an array
4462 (an actual TARGET_CANONICAL_VA_LIST_TYPE (valist)).
4463 So fix it. */
4464 if (TREE_CODE (TREE_TYPE (valist)) == ARRAY_TYPE)
4465 {
4466 tree p1 = build_pointer_type (TREE_TYPE (vatype));
4467 valist = build_fold_addr_expr_with_type_loc (loc, valist, p1);
4468 }
4469 }
4470 else
4471 {
4472 tree pt;
4473
4474 if (! needs_lvalue)
4475 {
4476 if (! TREE_SIDE_EFFECTS (valist))
4477 return valist;
4478
4479 pt = build_pointer_type (vatype);
4480 valist = fold_build1_loc (loc, ADDR_EXPR, pt, valist);
4481 TREE_SIDE_EFFECTS (valist) = 1;
4482 }
4483
4484 if (TREE_SIDE_EFFECTS (valist))
4485 valist = save_expr (valist);
4486 valist = build_fold_indirect_ref_loc (loc, valist);
4487 }
4488
4489 return valist;
4490 }
4491
4492 /* The "standard" definition of va_list is void*. */
4493
4494 tree
4495 std_build_builtin_va_list (void)
4496 {
4497 return ptr_type_node;
4498 }
4499
4500 /* The "standard" abi va_list is va_list_type_node. */
4501
4502 tree
4503 std_fn_abi_va_list (tree fndecl ATTRIBUTE_UNUSED)
4504 {
4505 return va_list_type_node;
4506 }
4507
4508 /* The "standard" type of va_list is va_list_type_node. */
4509
4510 tree
4511 std_canonical_va_list_type (tree type)
4512 {
4513 tree wtype, htype;
4514
4515 if (INDIRECT_REF_P (type))
4516 type = TREE_TYPE (type);
4517 else if (POINTER_TYPE_P (type) && POINTER_TYPE_P (TREE_TYPE(type)))
4518 type = TREE_TYPE (type);
4519 wtype = va_list_type_node;
4520 htype = type;
4521 /* Treat structure va_list types. */
4522 if (TREE_CODE (wtype) == RECORD_TYPE && POINTER_TYPE_P (htype))
4523 htype = TREE_TYPE (htype);
4524 else if (TREE_CODE (wtype) == ARRAY_TYPE)
4525 {
4526 /* If va_list is an array type, the argument may have decayed
4527 to a pointer type, e.g. by being passed to another function.
4528 In that case, unwrap both types so that we can compare the
4529 underlying records. */
4530 if (TREE_CODE (htype) == ARRAY_TYPE
4531 || POINTER_TYPE_P (htype))
4532 {
4533 wtype = TREE_TYPE (wtype);
4534 htype = TREE_TYPE (htype);
4535 }
4536 }
4537 if (TYPE_MAIN_VARIANT (wtype) == TYPE_MAIN_VARIANT (htype))
4538 return va_list_type_node;
4539
4540 return NULL_TREE;
4541 }
4542
4543 /* The "standard" implementation of va_start: just assign `nextarg' to
4544 the variable. */
4545
4546 void
4547 std_expand_builtin_va_start (tree valist, rtx nextarg)
4548 {
4549 rtx va_r = expand_expr (valist, NULL_RTX, VOIDmode, EXPAND_WRITE);
4550 convert_move (va_r, nextarg, 0);
4551 }
4552
4553 /* Expand EXP, a call to __builtin_va_start. */
4554
4555 static rtx
4556 expand_builtin_va_start (tree exp)
4557 {
4558 rtx nextarg;
4559 tree valist;
4560 location_t loc = EXPR_LOCATION (exp);
4561
4562 if (call_expr_nargs (exp) < 2)
4563 {
4564 error_at (loc, "too few arguments to function %<va_start%>");
4565 return const0_rtx;
4566 }
4567
4568 if (fold_builtin_next_arg (exp, true))
4569 return const0_rtx;
4570
4571 nextarg = expand_builtin_next_arg ();
4572 valist = stabilize_va_list_loc (loc, CALL_EXPR_ARG (exp, 0), 1);
4573
4574 if (targetm.expand_builtin_va_start)
4575 targetm.expand_builtin_va_start (valist, nextarg);
4576 else
4577 std_expand_builtin_va_start (valist, nextarg);
4578
4579 return const0_rtx;
4580 }
4581
4582 /* The "standard" implementation of va_arg: read the value from the
4583 current (padded) address and increment by the (padded) size. */
4584
4585 tree
4586 std_gimplify_va_arg_expr (tree valist, tree type, gimple_seq *pre_p,
4587 gimple_seq *post_p)
4588 {
4589 tree addr, t, type_size, rounded_size, valist_tmp;
4590 unsigned HOST_WIDE_INT align, boundary;
4591 bool indirect;
4592
4593 #ifdef ARGS_GROW_DOWNWARD
4594 /* All of the alignment and movement below is for args-grow-up machines.
4595 As of 2004, there are only 3 ARGS_GROW_DOWNWARD targets, and they all
4596 implement their own specialized gimplify_va_arg_expr routines. */
4597 gcc_unreachable ();
4598 #endif
4599
4600 indirect = pass_by_reference (NULL, TYPE_MODE (type), type, false);
4601 if (indirect)
4602 type = build_pointer_type (type);
4603
4604 align = PARM_BOUNDARY / BITS_PER_UNIT;
4605 boundary = FUNCTION_ARG_BOUNDARY (TYPE_MODE (type), type);
4606
4607 /* When we align parameter on stack for caller, if the parameter
4608 alignment is beyond MAX_SUPPORTED_STACK_ALIGNMENT, it will be
4609 aligned at MAX_SUPPORTED_STACK_ALIGNMENT. We will match callee
4610 here with caller. */
4611 if (boundary > MAX_SUPPORTED_STACK_ALIGNMENT)
4612 boundary = MAX_SUPPORTED_STACK_ALIGNMENT;
4613
4614 boundary /= BITS_PER_UNIT;
4615
4616 /* Hoist the valist value into a temporary for the moment. */
4617 valist_tmp = get_initialized_tmp_var (valist, pre_p, NULL);
4618
4619 /* va_list pointer is aligned to PARM_BOUNDARY. If argument actually
4620 requires greater alignment, we must perform dynamic alignment. */
4621 if (boundary > align
4622 && !integer_zerop (TYPE_SIZE (type)))
4623 {
4624 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
4625 fold_build2 (POINTER_PLUS_EXPR,
4626 TREE_TYPE (valist),
4627 valist_tmp, size_int (boundary - 1)));
4628 gimplify_and_add (t, pre_p);
4629
4630 t = fold_convert (sizetype, valist_tmp);
4631 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist_tmp,
4632 fold_convert (TREE_TYPE (valist),
4633 fold_build2 (BIT_AND_EXPR, sizetype, t,
4634 size_int (-boundary))));
4635 gimplify_and_add (t, pre_p);
4636 }
4637 else
4638 boundary = align;
4639
4640 /* If the actual alignment is less than the alignment of the type,
4641 adjust the type accordingly so that we don't assume strict alignment
4642 when dereferencing the pointer. */
4643 boundary *= BITS_PER_UNIT;
4644 if (boundary < TYPE_ALIGN (type))
4645 {
4646 type = build_variant_type_copy (type);
4647 TYPE_ALIGN (type) = boundary;
4648 }
4649
4650 /* Compute the rounded size of the type. */
4651 type_size = size_in_bytes (type);
4652 rounded_size = round_up (type_size, align);
4653
4654 /* Reduce rounded_size so it's sharable with the postqueue. */
4655 gimplify_expr (&rounded_size, pre_p, post_p, is_gimple_val, fb_rvalue);
4656
4657 /* Get AP. */
4658 addr = valist_tmp;
4659 if (PAD_VARARGS_DOWN && !integer_zerop (rounded_size))
4660 {
4661 /* Small args are padded downward. */
4662 t = fold_build2_loc (input_location, GT_EXPR, sizetype,
4663 rounded_size, size_int (align));
4664 t = fold_build3 (COND_EXPR, sizetype, t, size_zero_node,
4665 size_binop (MINUS_EXPR, rounded_size, type_size));
4666 addr = fold_build2 (POINTER_PLUS_EXPR,
4667 TREE_TYPE (addr), addr, t);
4668 }
4669
4670 /* Compute new value for AP. */
4671 t = build2 (POINTER_PLUS_EXPR, TREE_TYPE (valist), valist_tmp, rounded_size);
4672 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
4673 gimplify_and_add (t, pre_p);
4674
4675 addr = fold_convert (build_pointer_type (type), addr);
4676
4677 if (indirect)
4678 addr = build_va_arg_indirect_ref (addr);
4679
4680 return build_va_arg_indirect_ref (addr);
4681 }
4682
4683 /* Build an indirect-ref expression over the given TREE, which represents a
4684 piece of a va_arg() expansion. */
4685 tree
4686 build_va_arg_indirect_ref (tree addr)
4687 {
4688 addr = build_fold_indirect_ref_loc (EXPR_LOCATION (addr), addr);
4689
4690 if (flag_mudflap) /* Don't instrument va_arg INDIRECT_REF. */
4691 mf_mark (addr);
4692
4693 return addr;
4694 }
4695
4696 /* Return a dummy expression of type TYPE in order to keep going after an
4697 error. */
4698
4699 static tree
4700 dummy_object (tree type)
4701 {
4702 tree t = build_int_cst (build_pointer_type (type), 0);
4703 return build1 (INDIRECT_REF, type, t);
4704 }
4705
4706 /* Gimplify __builtin_va_arg, aka VA_ARG_EXPR, which is not really a
4707 builtin function, but a very special sort of operator. */
4708
4709 enum gimplify_status
4710 gimplify_va_arg_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
4711 {
4712 tree promoted_type, have_va_type;
4713 tree valist = TREE_OPERAND (*expr_p, 0);
4714 tree type = TREE_TYPE (*expr_p);
4715 tree t;
4716 location_t loc = EXPR_LOCATION (*expr_p);
4717
4718 /* Verify that valist is of the proper type. */
4719 have_va_type = TREE_TYPE (valist);
4720 if (have_va_type == error_mark_node)
4721 return GS_ERROR;
4722 have_va_type = targetm.canonical_va_list_type (have_va_type);
4723
4724 if (have_va_type == NULL_TREE)
4725 {
4726 error_at (loc, "first argument to %<va_arg%> not of type %<va_list%>");
4727 return GS_ERROR;
4728 }
4729
4730 /* Generate a diagnostic for requesting data of a type that cannot
4731 be passed through `...' due to type promotion at the call site. */
4732 if ((promoted_type = lang_hooks.types.type_promotes_to (type))
4733 != type)
4734 {
4735 static bool gave_help;
4736 bool warned;
4737
4738 /* Unfortunately, this is merely undefined, rather than a constraint
4739 violation, so we cannot make this an error. If this call is never
4740 executed, the program is still strictly conforming. */
4741 warned = warning_at (loc, 0,
4742 "%qT is promoted to %qT when passed through %<...%>",
4743 type, promoted_type);
4744 if (!gave_help && warned)
4745 {
4746 gave_help = true;
4747 inform (loc, "(so you should pass %qT not %qT to %<va_arg%>)",
4748 promoted_type, type);
4749 }
4750
4751 /* We can, however, treat "undefined" any way we please.
4752 Call abort to encourage the user to fix the program. */
4753 if (warned)
4754 inform (loc, "if this code is reached, the program will abort");
4755 /* Before the abort, allow the evaluation of the va_list
4756 expression to exit or longjmp. */
4757 gimplify_and_add (valist, pre_p);
4758 t = build_call_expr_loc (loc,
4759 implicit_built_in_decls[BUILT_IN_TRAP], 0);
4760 gimplify_and_add (t, pre_p);
4761
4762 /* This is dead code, but go ahead and finish so that the
4763 mode of the result comes out right. */
4764 *expr_p = dummy_object (type);
4765 return GS_ALL_DONE;
4766 }
4767 else
4768 {
4769 /* Make it easier for the backends by protecting the valist argument
4770 from multiple evaluations. */
4771 if (TREE_CODE (have_va_type) == ARRAY_TYPE)
4772 {
4773 /* For this case, the backends will be expecting a pointer to
4774 TREE_TYPE (abi), but it's possible we've
4775 actually been given an array (an actual TARGET_FN_ABI_VA_LIST).
4776 So fix it. */
4777 if (TREE_CODE (TREE_TYPE (valist)) == ARRAY_TYPE)
4778 {
4779 tree p1 = build_pointer_type (TREE_TYPE (have_va_type));
4780 valist = fold_convert_loc (loc, p1,
4781 build_fold_addr_expr_loc (loc, valist));
4782 }
4783
4784 gimplify_expr (&valist, pre_p, post_p, is_gimple_val, fb_rvalue);
4785 }
4786 else
4787 gimplify_expr (&valist, pre_p, post_p, is_gimple_min_lval, fb_lvalue);
4788
4789 if (!targetm.gimplify_va_arg_expr)
4790 /* FIXME: Once most targets are converted we should merely
4791 assert this is non-null. */
4792 return GS_ALL_DONE;
4793
4794 *expr_p = targetm.gimplify_va_arg_expr (valist, type, pre_p, post_p);
4795 return GS_OK;
4796 }
4797 }
4798
4799 /* Expand EXP, a call to __builtin_va_end. */
4800
4801 static rtx
4802 expand_builtin_va_end (tree exp)
4803 {
4804 tree valist = CALL_EXPR_ARG (exp, 0);
4805
4806 /* Evaluate for side effects, if needed. I hate macros that don't
4807 do that. */
4808 if (TREE_SIDE_EFFECTS (valist))
4809 expand_expr (valist, const0_rtx, VOIDmode, EXPAND_NORMAL);
4810
4811 return const0_rtx;
4812 }
4813
4814 /* Expand EXP, a call to __builtin_va_copy. We do this as a
4815 builtin rather than just as an assignment in stdarg.h because of the
4816 nastiness of array-type va_list types. */
4817
4818 static rtx
4819 expand_builtin_va_copy (tree exp)
4820 {
4821 tree dst, src, t;
4822 location_t loc = EXPR_LOCATION (exp);
4823
4824 dst = CALL_EXPR_ARG (exp, 0);
4825 src = CALL_EXPR_ARG (exp, 1);
4826
4827 dst = stabilize_va_list_loc (loc, dst, 1);
4828 src = stabilize_va_list_loc (loc, src, 0);
4829
4830 gcc_assert (cfun != NULL && cfun->decl != NULL_TREE);
4831
4832 if (TREE_CODE (targetm.fn_abi_va_list (cfun->decl)) != ARRAY_TYPE)
4833 {
4834 t = build2 (MODIFY_EXPR, targetm.fn_abi_va_list (cfun->decl), dst, src);
4835 TREE_SIDE_EFFECTS (t) = 1;
4836 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4837 }
4838 else
4839 {
4840 rtx dstb, srcb, size;
4841
4842 /* Evaluate to pointers. */
4843 dstb = expand_expr (dst, NULL_RTX, Pmode, EXPAND_NORMAL);
4844 srcb = expand_expr (src, NULL_RTX, Pmode, EXPAND_NORMAL);
4845 size = expand_expr (TYPE_SIZE_UNIT (targetm.fn_abi_va_list (cfun->decl)),
4846 NULL_RTX, VOIDmode, EXPAND_NORMAL);
4847
4848 dstb = convert_memory_address (Pmode, dstb);
4849 srcb = convert_memory_address (Pmode, srcb);
4850
4851 /* "Dereference" to BLKmode memories. */
4852 dstb = gen_rtx_MEM (BLKmode, dstb);
4853 set_mem_alias_set (dstb, get_alias_set (TREE_TYPE (TREE_TYPE (dst))));
4854 set_mem_align (dstb, TYPE_ALIGN (targetm.fn_abi_va_list (cfun->decl)));
4855 srcb = gen_rtx_MEM (BLKmode, srcb);
4856 set_mem_alias_set (srcb, get_alias_set (TREE_TYPE (TREE_TYPE (src))));
4857 set_mem_align (srcb, TYPE_ALIGN (targetm.fn_abi_va_list (cfun->decl)));
4858
4859 /* Copy. */
4860 emit_block_move (dstb, srcb, size, BLOCK_OP_NORMAL);
4861 }
4862
4863 return const0_rtx;
4864 }
4865
4866 /* Expand a call to one of the builtin functions __builtin_frame_address or
4867 __builtin_return_address. */
4868
4869 static rtx
4870 expand_builtin_frame_address (tree fndecl, tree exp)
4871 {
4872 /* The argument must be a nonnegative integer constant.
4873 It counts the number of frames to scan up the stack.
4874 The value is the return address saved in that frame. */
4875 if (call_expr_nargs (exp) == 0)
4876 /* Warning about missing arg was already issued. */
4877 return const0_rtx;
4878 else if (! host_integerp (CALL_EXPR_ARG (exp, 0), 1))
4879 {
4880 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4881 error ("invalid argument to %<__builtin_frame_address%>");
4882 else
4883 error ("invalid argument to %<__builtin_return_address%>");
4884 return const0_rtx;
4885 }
4886 else
4887 {
4888 rtx tem
4889 = expand_builtin_return_addr (DECL_FUNCTION_CODE (fndecl),
4890 tree_low_cst (CALL_EXPR_ARG (exp, 0), 1));
4891
4892 /* Some ports cannot access arbitrary stack frames. */
4893 if (tem == NULL)
4894 {
4895 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4896 warning (0, "unsupported argument to %<__builtin_frame_address%>");
4897 else
4898 warning (0, "unsupported argument to %<__builtin_return_address%>");
4899 return const0_rtx;
4900 }
4901
4902 /* For __builtin_frame_address, return what we've got. */
4903 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4904 return tem;
4905
4906 if (!REG_P (tem)
4907 && ! CONSTANT_P (tem))
4908 tem = copy_to_mode_reg (Pmode, tem);
4909 return tem;
4910 }
4911 }
4912
4913 /* Expand EXP, a call to the alloca builtin. Return NULL_RTX if
4914 we failed and the caller should emit a normal call, otherwise try to get
4915 the result in TARGET, if convenient. */
4916
4917 static rtx
4918 expand_builtin_alloca (tree exp, rtx target)
4919 {
4920 rtx op0;
4921 rtx result;
4922
4923 /* Emit normal call if marked not-inlineable. */
4924 if (CALL_CANNOT_INLINE_P (exp))
4925 return NULL_RTX;
4926
4927 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
4928 return NULL_RTX;
4929
4930 /* Compute the argument. */
4931 op0 = expand_normal (CALL_EXPR_ARG (exp, 0));
4932
4933 /* Allocate the desired space. */
4934 result = allocate_dynamic_stack_space (op0, target, BITS_PER_UNIT);
4935 result = convert_memory_address (ptr_mode, result);
4936
4937 return result;
4938 }
4939
4940 /* Expand a call to a bswap builtin with argument ARG0. MODE
4941 is the mode to expand with. */
4942
4943 static rtx
4944 expand_builtin_bswap (tree exp, rtx target, rtx subtarget)
4945 {
4946 enum machine_mode mode;
4947 tree arg;
4948 rtx op0;
4949
4950 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
4951 return NULL_RTX;
4952
4953 arg = CALL_EXPR_ARG (exp, 0);
4954 mode = TYPE_MODE (TREE_TYPE (arg));
4955 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
4956
4957 target = expand_unop (mode, bswap_optab, op0, target, 1);
4958
4959 gcc_assert (target);
4960
4961 return convert_to_mode (mode, target, 0);
4962 }
4963
4964 /* Expand a call to a unary builtin in EXP.
4965 Return NULL_RTX if a normal call should be emitted rather than expanding the
4966 function in-line. If convenient, the result should be placed in TARGET.
4967 SUBTARGET may be used as the target for computing one of EXP's operands. */
4968
4969 static rtx
4970 expand_builtin_unop (enum machine_mode target_mode, tree exp, rtx target,
4971 rtx subtarget, optab op_optab)
4972 {
4973 rtx op0;
4974
4975 if (!validate_arglist (exp, INTEGER_TYPE, VOID_TYPE))
4976 return NULL_RTX;
4977
4978 /* Compute the argument. */
4979 op0 = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
4980 VOIDmode, EXPAND_NORMAL);
4981 /* Compute op, into TARGET if possible.
4982 Set TARGET to wherever the result comes back. */
4983 target = expand_unop (TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 0))),
4984 op_optab, op0, target, 1);
4985 gcc_assert (target);
4986
4987 return convert_to_mode (target_mode, target, 0);
4988 }
4989
4990 /* Expand a call to __builtin_expect. We just return our argument
4991 as the builtin_expect semantic should've been already executed by
4992 tree branch prediction pass. */
4993
4994 static rtx
4995 expand_builtin_expect (tree exp, rtx target)
4996 {
4997 tree arg;
4998
4999 if (call_expr_nargs (exp) < 2)
5000 return const0_rtx;
5001 arg = CALL_EXPR_ARG (exp, 0);
5002
5003 target = expand_expr (arg, target, VOIDmode, EXPAND_NORMAL);
5004 /* When guessing was done, the hints should be already stripped away. */
5005 gcc_assert (!flag_guess_branch_prob
5006 || optimize == 0 || errorcount || sorrycount);
5007 return target;
5008 }
5009
5010 void
5011 expand_builtin_trap (void)
5012 {
5013 #ifdef HAVE_trap
5014 if (HAVE_trap)
5015 emit_insn (gen_trap ());
5016 else
5017 #endif
5018 emit_library_call (abort_libfunc, LCT_NORETURN, VOIDmode, 0);
5019 emit_barrier ();
5020 }
5021
5022 /* Expand a call to __builtin_unreachable. We do nothing except emit
5023 a barrier saying that control flow will not pass here.
5024
5025 It is the responsibility of the program being compiled to ensure
5026 that control flow does never reach __builtin_unreachable. */
5027 static void
5028 expand_builtin_unreachable (void)
5029 {
5030 emit_barrier ();
5031 }
5032
5033 /* Expand EXP, a call to fabs, fabsf or fabsl.
5034 Return NULL_RTX if a normal call should be emitted rather than expanding
5035 the function inline. If convenient, the result should be placed
5036 in TARGET. SUBTARGET may be used as the target for computing
5037 the operand. */
5038
5039 static rtx
5040 expand_builtin_fabs (tree exp, rtx target, rtx subtarget)
5041 {
5042 enum machine_mode mode;
5043 tree arg;
5044 rtx op0;
5045
5046 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
5047 return NULL_RTX;
5048
5049 arg = CALL_EXPR_ARG (exp, 0);
5050 CALL_EXPR_ARG (exp, 0) = arg = builtin_save_expr (arg);
5051 mode = TYPE_MODE (TREE_TYPE (arg));
5052 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
5053 return expand_abs (mode, op0, target, 0, safe_from_p (target, arg, 1));
5054 }
5055
5056 /* Expand EXP, a call to copysign, copysignf, or copysignl.
5057 Return NULL is a normal call should be emitted rather than expanding the
5058 function inline. If convenient, the result should be placed in TARGET.
5059 SUBTARGET may be used as the target for computing the operand. */
5060
5061 static rtx
5062 expand_builtin_copysign (tree exp, rtx target, rtx subtarget)
5063 {
5064 rtx op0, op1;
5065 tree arg;
5066
5067 if (!validate_arglist (exp, REAL_TYPE, REAL_TYPE, VOID_TYPE))
5068 return NULL_RTX;
5069
5070 arg = CALL_EXPR_ARG (exp, 0);
5071 op0 = expand_expr (arg, subtarget, VOIDmode, EXPAND_NORMAL);
5072
5073 arg = CALL_EXPR_ARG (exp, 1);
5074 op1 = expand_normal (arg);
5075
5076 return expand_copysign (op0, op1, target);
5077 }
5078
5079 /* Create a new constant string literal and return a char* pointer to it.
5080 The STRING_CST value is the LEN characters at STR. */
5081 tree
5082 build_string_literal (int len, const char *str)
5083 {
5084 tree t, elem, index, type;
5085
5086 t = build_string (len, str);
5087 elem = build_type_variant (char_type_node, 1, 0);
5088 index = build_index_type (size_int (len - 1));
5089 type = build_array_type (elem, index);
5090 TREE_TYPE (t) = type;
5091 TREE_CONSTANT (t) = 1;
5092 TREE_READONLY (t) = 1;
5093 TREE_STATIC (t) = 1;
5094
5095 type = build_pointer_type (elem);
5096 t = build1 (ADDR_EXPR, type,
5097 build4 (ARRAY_REF, elem,
5098 t, integer_zero_node, NULL_TREE, NULL_TREE));
5099 return t;
5100 }
5101
5102 /* Expand a call to either the entry or exit function profiler. */
5103
5104 static rtx
5105 expand_builtin_profile_func (bool exitp)
5106 {
5107 rtx this_rtx, which;
5108
5109 this_rtx = DECL_RTL (current_function_decl);
5110 gcc_assert (MEM_P (this_rtx));
5111 this_rtx = XEXP (this_rtx, 0);
5112
5113 if (exitp)
5114 which = profile_function_exit_libfunc;
5115 else
5116 which = profile_function_entry_libfunc;
5117
5118 emit_library_call (which, LCT_NORMAL, VOIDmode, 2, this_rtx, Pmode,
5119 expand_builtin_return_addr (BUILT_IN_RETURN_ADDRESS,
5120 0),
5121 Pmode);
5122
5123 return const0_rtx;
5124 }
5125
5126 /* Expand a call to __builtin___clear_cache. */
5127
5128 static rtx
5129 expand_builtin___clear_cache (tree exp ATTRIBUTE_UNUSED)
5130 {
5131 #ifndef HAVE_clear_cache
5132 #ifdef CLEAR_INSN_CACHE
5133 /* There is no "clear_cache" insn, and __clear_cache() in libgcc
5134 does something. Just do the default expansion to a call to
5135 __clear_cache(). */
5136 return NULL_RTX;
5137 #else
5138 /* There is no "clear_cache" insn, and __clear_cache() in libgcc
5139 does nothing. There is no need to call it. Do nothing. */
5140 return const0_rtx;
5141 #endif /* CLEAR_INSN_CACHE */
5142 #else
5143 /* We have a "clear_cache" insn, and it will handle everything. */
5144 tree begin, end;
5145 rtx begin_rtx, end_rtx;
5146 enum insn_code icode;
5147
5148 /* We must not expand to a library call. If we did, any
5149 fallback library function in libgcc that might contain a call to
5150 __builtin___clear_cache() would recurse infinitely. */
5151 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
5152 {
5153 error ("both arguments to %<__builtin___clear_cache%> must be pointers");
5154 return const0_rtx;
5155 }
5156
5157 if (HAVE_clear_cache)
5158 {
5159 icode = CODE_FOR_clear_cache;
5160
5161 begin = CALL_EXPR_ARG (exp, 0);
5162 begin_rtx = expand_expr (begin, NULL_RTX, Pmode, EXPAND_NORMAL);
5163 begin_rtx = convert_memory_address (Pmode, begin_rtx);
5164 if (!insn_data[icode].operand[0].predicate (begin_rtx, Pmode))
5165 begin_rtx = copy_to_mode_reg (Pmode, begin_rtx);
5166
5167 end = CALL_EXPR_ARG (exp, 1);
5168 end_rtx = expand_expr (end, NULL_RTX, Pmode, EXPAND_NORMAL);
5169 end_rtx = convert_memory_address (Pmode, end_rtx);
5170 if (!insn_data[icode].operand[1].predicate (end_rtx, Pmode))
5171 end_rtx = copy_to_mode_reg (Pmode, end_rtx);
5172
5173 emit_insn (gen_clear_cache (begin_rtx, end_rtx));
5174 }
5175 return const0_rtx;
5176 #endif /* HAVE_clear_cache */
5177 }
5178
5179 /* Given a trampoline address, make sure it satisfies TRAMPOLINE_ALIGNMENT. */
5180
5181 static rtx
5182 round_trampoline_addr (rtx tramp)
5183 {
5184 rtx temp, addend, mask;
5185
5186 /* If we don't need too much alignment, we'll have been guaranteed
5187 proper alignment by get_trampoline_type. */
5188 if (TRAMPOLINE_ALIGNMENT <= STACK_BOUNDARY)
5189 return tramp;
5190
5191 /* Round address up to desired boundary. */
5192 temp = gen_reg_rtx (Pmode);
5193 addend = GEN_INT (TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT - 1);
5194 mask = GEN_INT (-TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT);
5195
5196 temp = expand_simple_binop (Pmode, PLUS, tramp, addend,
5197 temp, 0, OPTAB_LIB_WIDEN);
5198 tramp = expand_simple_binop (Pmode, AND, temp, mask,
5199 temp, 0, OPTAB_LIB_WIDEN);
5200
5201 return tramp;
5202 }
5203
5204 static rtx
5205 expand_builtin_init_trampoline (tree exp)
5206 {
5207 tree t_tramp, t_func, t_chain;
5208 rtx m_tramp, r_tramp, r_chain, tmp;
5209
5210 if (!validate_arglist (exp, POINTER_TYPE, POINTER_TYPE,
5211 POINTER_TYPE, VOID_TYPE))
5212 return NULL_RTX;
5213
5214 t_tramp = CALL_EXPR_ARG (exp, 0);
5215 t_func = CALL_EXPR_ARG (exp, 1);
5216 t_chain = CALL_EXPR_ARG (exp, 2);
5217
5218 r_tramp = expand_normal (t_tramp);
5219 m_tramp = gen_rtx_MEM (BLKmode, r_tramp);
5220 MEM_NOTRAP_P (m_tramp) = 1;
5221
5222 /* The TRAMP argument should be the address of a field within the
5223 local function's FRAME decl. Let's see if we can fill in the
5224 to fill in the MEM_ATTRs for this memory. */
5225 if (TREE_CODE (t_tramp) == ADDR_EXPR)
5226 set_mem_attributes_minus_bitpos (m_tramp, TREE_OPERAND (t_tramp, 0),
5227 true, 0);
5228
5229 tmp = round_trampoline_addr (r_tramp);
5230 if (tmp != r_tramp)
5231 {
5232 m_tramp = change_address (m_tramp, BLKmode, tmp);
5233 set_mem_align (m_tramp, TRAMPOLINE_ALIGNMENT);
5234 set_mem_size (m_tramp, GEN_INT (TRAMPOLINE_SIZE));
5235 }
5236
5237 /* The FUNC argument should be the address of the nested function.
5238 Extract the actual function decl to pass to the hook. */
5239 gcc_assert (TREE_CODE (t_func) == ADDR_EXPR);
5240 t_func = TREE_OPERAND (t_func, 0);
5241 gcc_assert (TREE_CODE (t_func) == FUNCTION_DECL);
5242
5243 r_chain = expand_normal (t_chain);
5244
5245 /* Generate insns to initialize the trampoline. */
5246 targetm.calls.trampoline_init (m_tramp, t_func, r_chain);
5247
5248 trampolines_created = 1;
5249 return const0_rtx;
5250 }
5251
5252 static rtx
5253 expand_builtin_adjust_trampoline (tree exp)
5254 {
5255 rtx tramp;
5256
5257 if (!validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
5258 return NULL_RTX;
5259
5260 tramp = expand_normal (CALL_EXPR_ARG (exp, 0));
5261 tramp = round_trampoline_addr (tramp);
5262 if (targetm.calls.trampoline_adjust_address)
5263 tramp = targetm.calls.trampoline_adjust_address (tramp);
5264
5265 return tramp;
5266 }
5267
5268 /* Expand the call EXP to the built-in signbit, signbitf or signbitl
5269 function. The function first checks whether the back end provides
5270 an insn to implement signbit for the respective mode. If not, it
5271 checks whether the floating point format of the value is such that
5272 the sign bit can be extracted. If that is not the case, the
5273 function returns NULL_RTX to indicate that a normal call should be
5274 emitted rather than expanding the function in-line. EXP is the
5275 expression that is a call to the builtin function; if convenient,
5276 the result should be placed in TARGET. */
5277 static rtx
5278 expand_builtin_signbit (tree exp, rtx target)
5279 {
5280 const struct real_format *fmt;
5281 enum machine_mode fmode, imode, rmode;
5282 tree arg;
5283 int word, bitpos;
5284 enum insn_code icode;
5285 rtx temp;
5286 location_t loc = EXPR_LOCATION (exp);
5287
5288 if (!validate_arglist (exp, REAL_TYPE, VOID_TYPE))
5289 return NULL_RTX;
5290
5291 arg = CALL_EXPR_ARG (exp, 0);
5292 fmode = TYPE_MODE (TREE_TYPE (arg));
5293 rmode = TYPE_MODE (TREE_TYPE (exp));
5294 fmt = REAL_MODE_FORMAT (fmode);
5295
5296 arg = builtin_save_expr (arg);
5297
5298 /* Expand the argument yielding a RTX expression. */
5299 temp = expand_normal (arg);
5300
5301 /* Check if the back end provides an insn that handles signbit for the
5302 argument's mode. */
5303 icode = signbit_optab->handlers [(int) fmode].insn_code;
5304 if (icode != CODE_FOR_nothing)
5305 {
5306 rtx last = get_last_insn ();
5307 target = gen_reg_rtx (TYPE_MODE (TREE_TYPE (exp)));
5308 if (maybe_emit_unop_insn (icode, target, temp, UNKNOWN))
5309 return target;
5310 delete_insns_since (last);
5311 }
5312
5313 /* For floating point formats without a sign bit, implement signbit
5314 as "ARG < 0.0". */
5315 bitpos = fmt->signbit_ro;
5316 if (bitpos < 0)
5317 {
5318 /* But we can't do this if the format supports signed zero. */
5319 if (fmt->has_signed_zero && HONOR_SIGNED_ZEROS (fmode))
5320 return NULL_RTX;
5321
5322 arg = fold_build2_loc (loc, LT_EXPR, TREE_TYPE (exp), arg,
5323 build_real (TREE_TYPE (arg), dconst0));
5324 return expand_expr (arg, target, VOIDmode, EXPAND_NORMAL);
5325 }
5326
5327 if (GET_MODE_SIZE (fmode) <= UNITS_PER_WORD)
5328 {
5329 imode = int_mode_for_mode (fmode);
5330 if (imode == BLKmode)
5331 return NULL_RTX;
5332 temp = gen_lowpart (imode, temp);
5333 }
5334 else
5335 {
5336 imode = word_mode;
5337 /* Handle targets with different FP word orders. */
5338 if (FLOAT_WORDS_BIG_ENDIAN)
5339 word = (GET_MODE_BITSIZE (fmode) - bitpos) / BITS_PER_WORD;
5340 else
5341 word = bitpos / BITS_PER_WORD;
5342 temp = operand_subword_force (temp, word, fmode);
5343 bitpos = bitpos % BITS_PER_WORD;
5344 }
5345
5346 /* Force the intermediate word_mode (or narrower) result into a
5347 register. This avoids attempting to create paradoxical SUBREGs
5348 of floating point modes below. */
5349 temp = force_reg (imode, temp);
5350
5351 /* If the bitpos is within the "result mode" lowpart, the operation
5352 can be implement with a single bitwise AND. Otherwise, we need
5353 a right shift and an AND. */
5354
5355 if (bitpos < GET_MODE_BITSIZE (rmode))
5356 {
5357 double_int mask = double_int_setbit (double_int_zero, bitpos);
5358
5359 if (GET_MODE_SIZE (imode) > GET_MODE_SIZE (rmode))
5360 temp = gen_lowpart (rmode, temp);
5361 temp = expand_binop (rmode, and_optab, temp,
5362 immed_double_int_const (mask, rmode),
5363 NULL_RTX, 1, OPTAB_LIB_WIDEN);
5364 }
5365 else
5366 {
5367 /* Perform a logical right shift to place the signbit in the least
5368 significant bit, then truncate the result to the desired mode
5369 and mask just this bit. */
5370 temp = expand_shift (RSHIFT_EXPR, imode, temp,
5371 build_int_cst (NULL_TREE, bitpos), NULL_RTX, 1);
5372 temp = gen_lowpart (rmode, temp);
5373 temp = expand_binop (rmode, and_optab, temp, const1_rtx,
5374 NULL_RTX, 1, OPTAB_LIB_WIDEN);
5375 }
5376
5377 return temp;
5378 }
5379
5380 /* Expand fork or exec calls. TARGET is the desired target of the
5381 call. EXP is the call. FN is the
5382 identificator of the actual function. IGNORE is nonzero if the
5383 value is to be ignored. */
5384
5385 static rtx
5386 expand_builtin_fork_or_exec (tree fn, tree exp, rtx target, int ignore)
5387 {
5388 tree id, decl;
5389 tree call;
5390
5391 /* If we are not profiling, just call the function. */
5392 if (!profile_arc_flag)
5393 return NULL_RTX;
5394
5395 /* Otherwise call the wrapper. This should be equivalent for the rest of
5396 compiler, so the code does not diverge, and the wrapper may run the
5397 code necessary for keeping the profiling sane. */
5398
5399 switch (DECL_FUNCTION_CODE (fn))
5400 {
5401 case BUILT_IN_FORK:
5402 id = get_identifier ("__gcov_fork");
5403 break;
5404
5405 case BUILT_IN_EXECL:
5406 id = get_identifier ("__gcov_execl");
5407 break;
5408
5409 case BUILT_IN_EXECV:
5410 id = get_identifier ("__gcov_execv");
5411 break;
5412
5413 case BUILT_IN_EXECLP:
5414 id = get_identifier ("__gcov_execlp");
5415 break;
5416
5417 case BUILT_IN_EXECLE:
5418 id = get_identifier ("__gcov_execle");
5419 break;
5420
5421 case BUILT_IN_EXECVP:
5422 id = get_identifier ("__gcov_execvp");
5423 break;
5424
5425 case BUILT_IN_EXECVE:
5426 id = get_identifier ("__gcov_execve");
5427 break;
5428
5429 default:
5430 gcc_unreachable ();
5431 }
5432
5433 decl = build_decl (DECL_SOURCE_LOCATION (fn),
5434 FUNCTION_DECL, id, TREE_TYPE (fn));
5435 DECL_EXTERNAL (decl) = 1;
5436 TREE_PUBLIC (decl) = 1;
5437 DECL_ARTIFICIAL (decl) = 1;
5438 TREE_NOTHROW (decl) = 1;
5439 DECL_VISIBILITY (decl) = VISIBILITY_DEFAULT;
5440 DECL_VISIBILITY_SPECIFIED (decl) = 1;
5441 call = rewrite_call_expr (EXPR_LOCATION (exp), exp, 0, decl, 0);
5442 return expand_call (call, target, ignore);
5443 }
5444
5445
5446 \f
5447 /* Reconstitute a mode for a __sync intrinsic operation. Since the type of
5448 the pointer in these functions is void*, the tree optimizers may remove
5449 casts. The mode computed in expand_builtin isn't reliable either, due
5450 to __sync_bool_compare_and_swap.
5451
5452 FCODE_DIFF should be fcode - base, where base is the FOO_1 code for the
5453 group of builtins. This gives us log2 of the mode size. */
5454
5455 static inline enum machine_mode
5456 get_builtin_sync_mode (int fcode_diff)
5457 {
5458 /* The size is not negotiable, so ask not to get BLKmode in return
5459 if the target indicates that a smaller size would be better. */
5460 return mode_for_size (BITS_PER_UNIT << fcode_diff, MODE_INT, 0);
5461 }
5462
5463 /* Expand the memory expression LOC and return the appropriate memory operand
5464 for the builtin_sync operations. */
5465
5466 static rtx
5467 get_builtin_sync_mem (tree loc, enum machine_mode mode)
5468 {
5469 rtx addr, mem;
5470
5471 addr = expand_expr (loc, NULL_RTX, ptr_mode, EXPAND_SUM);
5472 addr = convert_memory_address (Pmode, addr);
5473
5474 /* Note that we explicitly do not want any alias information for this
5475 memory, so that we kill all other live memories. Otherwise we don't
5476 satisfy the full barrier semantics of the intrinsic. */
5477 mem = validize_mem (gen_rtx_MEM (mode, addr));
5478
5479 set_mem_align (mem, get_pointer_alignment (loc, BIGGEST_ALIGNMENT));
5480 set_mem_alias_set (mem, ALIAS_SET_MEMORY_BARRIER);
5481 MEM_VOLATILE_P (mem) = 1;
5482
5483 return mem;
5484 }
5485
5486 /* Expand the __sync_xxx_and_fetch and __sync_fetch_and_xxx intrinsics.
5487 EXP is the CALL_EXPR. CODE is the rtx code
5488 that corresponds to the arithmetic or logical operation from the name;
5489 an exception here is that NOT actually means NAND. TARGET is an optional
5490 place for us to store the results; AFTER is true if this is the
5491 fetch_and_xxx form. IGNORE is true if we don't actually care about
5492 the result of the operation at all. */
5493
5494 static rtx
5495 expand_builtin_sync_operation (enum machine_mode mode, tree exp,
5496 enum rtx_code code, bool after,
5497 rtx target, bool ignore)
5498 {
5499 rtx val, mem;
5500 enum machine_mode old_mode;
5501 location_t loc = EXPR_LOCATION (exp);
5502
5503 if (code == NOT && warn_sync_nand)
5504 {
5505 tree fndecl = get_callee_fndecl (exp);
5506 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
5507
5508 static bool warned_f_a_n, warned_n_a_f;
5509
5510 switch (fcode)
5511 {
5512 case BUILT_IN_FETCH_AND_NAND_1:
5513 case BUILT_IN_FETCH_AND_NAND_2:
5514 case BUILT_IN_FETCH_AND_NAND_4:
5515 case BUILT_IN_FETCH_AND_NAND_8:
5516 case BUILT_IN_FETCH_AND_NAND_16:
5517
5518 if (warned_f_a_n)
5519 break;
5520
5521 fndecl = implicit_built_in_decls[BUILT_IN_FETCH_AND_NAND_N];
5522 inform (loc, "%qD changed semantics in GCC 4.4", fndecl);
5523 warned_f_a_n = true;
5524 break;
5525
5526 case BUILT_IN_NAND_AND_FETCH_1:
5527 case BUILT_IN_NAND_AND_FETCH_2:
5528 case BUILT_IN_NAND_AND_FETCH_4:
5529 case BUILT_IN_NAND_AND_FETCH_8:
5530 case BUILT_IN_NAND_AND_FETCH_16:
5531
5532 if (warned_n_a_f)
5533 break;
5534
5535 fndecl = implicit_built_in_decls[BUILT_IN_NAND_AND_FETCH_N];
5536 inform (loc, "%qD changed semantics in GCC 4.4", fndecl);
5537 warned_n_a_f = true;
5538 break;
5539
5540 default:
5541 gcc_unreachable ();
5542 }
5543 }
5544
5545 /* Expand the operands. */
5546 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5547
5548 val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX, mode, EXPAND_NORMAL);
5549 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5550 of CONST_INTs, where we know the old_mode only from the call argument. */
5551 old_mode = GET_MODE (val);
5552 if (old_mode == VOIDmode)
5553 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5554 val = convert_modes (mode, old_mode, val, 1);
5555
5556 if (ignore)
5557 return expand_sync_operation (mem, val, code);
5558 else
5559 return expand_sync_fetch_operation (mem, val, code, after, target);
5560 }
5561
5562 /* Expand the __sync_val_compare_and_swap and __sync_bool_compare_and_swap
5563 intrinsics. EXP is the CALL_EXPR. IS_BOOL is
5564 true if this is the boolean form. TARGET is a place for us to store the
5565 results; this is NOT optional if IS_BOOL is true. */
5566
5567 static rtx
5568 expand_builtin_compare_and_swap (enum machine_mode mode, tree exp,
5569 bool is_bool, rtx target)
5570 {
5571 rtx old_val, new_val, mem;
5572 enum machine_mode old_mode;
5573
5574 /* Expand the operands. */
5575 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5576
5577
5578 old_val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX,
5579 mode, EXPAND_NORMAL);
5580 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5581 of CONST_INTs, where we know the old_mode only from the call argument. */
5582 old_mode = GET_MODE (old_val);
5583 if (old_mode == VOIDmode)
5584 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5585 old_val = convert_modes (mode, old_mode, old_val, 1);
5586
5587 new_val = expand_expr (CALL_EXPR_ARG (exp, 2), NULL_RTX,
5588 mode, EXPAND_NORMAL);
5589 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5590 of CONST_INTs, where we know the old_mode only from the call argument. */
5591 old_mode = GET_MODE (new_val);
5592 if (old_mode == VOIDmode)
5593 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 2)));
5594 new_val = convert_modes (mode, old_mode, new_val, 1);
5595
5596 if (is_bool)
5597 return expand_bool_compare_and_swap (mem, old_val, new_val, target);
5598 else
5599 return expand_val_compare_and_swap (mem, old_val, new_val, target);
5600 }
5601
5602 /* Expand the __sync_lock_test_and_set intrinsic. Note that the most
5603 general form is actually an atomic exchange, and some targets only
5604 support a reduced form with the second argument being a constant 1.
5605 EXP is the CALL_EXPR; TARGET is an optional place for us to store
5606 the results. */
5607
5608 static rtx
5609 expand_builtin_lock_test_and_set (enum machine_mode mode, tree exp,
5610 rtx target)
5611 {
5612 rtx val, mem;
5613 enum machine_mode old_mode;
5614
5615 /* Expand the operands. */
5616 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5617 val = expand_expr (CALL_EXPR_ARG (exp, 1), NULL_RTX, mode, EXPAND_NORMAL);
5618 /* If VAL is promoted to a wider mode, convert it back to MODE. Take care
5619 of CONST_INTs, where we know the old_mode only from the call argument. */
5620 old_mode = GET_MODE (val);
5621 if (old_mode == VOIDmode)
5622 old_mode = TYPE_MODE (TREE_TYPE (CALL_EXPR_ARG (exp, 1)));
5623 val = convert_modes (mode, old_mode, val, 1);
5624
5625 return expand_sync_lock_test_and_set (mem, val, target);
5626 }
5627
5628 /* Expand the __sync_synchronize intrinsic. */
5629
5630 static void
5631 expand_builtin_synchronize (void)
5632 {
5633 gimple x;
5634 VEC (tree, gc) *v_clobbers;
5635
5636 #ifdef HAVE_memory_barrier
5637 if (HAVE_memory_barrier)
5638 {
5639 emit_insn (gen_memory_barrier ());
5640 return;
5641 }
5642 #endif
5643
5644 if (synchronize_libfunc != NULL_RTX)
5645 {
5646 emit_library_call (synchronize_libfunc, LCT_NORMAL, VOIDmode, 0);
5647 return;
5648 }
5649
5650 /* If no explicit memory barrier instruction is available, create an
5651 empty asm stmt with a memory clobber. */
5652 v_clobbers = VEC_alloc (tree, gc, 1);
5653 VEC_quick_push (tree, v_clobbers,
5654 tree_cons (NULL, build_string (6, "memory"), NULL));
5655 x = gimple_build_asm_vec ("", NULL, NULL, v_clobbers, NULL);
5656 gimple_asm_set_volatile (x, true);
5657 expand_asm_stmt (x);
5658 }
5659
5660 /* Expand the __sync_lock_release intrinsic. EXP is the CALL_EXPR. */
5661
5662 static void
5663 expand_builtin_lock_release (enum machine_mode mode, tree exp)
5664 {
5665 enum insn_code icode;
5666 rtx mem, insn;
5667 rtx val = const0_rtx;
5668
5669 /* Expand the operands. */
5670 mem = get_builtin_sync_mem (CALL_EXPR_ARG (exp, 0), mode);
5671
5672 /* If there is an explicit operation in the md file, use it. */
5673 icode = sync_lock_release[mode];
5674 if (icode != CODE_FOR_nothing)
5675 {
5676 if (!insn_data[icode].operand[1].predicate (val, mode))
5677 val = force_reg (mode, val);
5678
5679 insn = GEN_FCN (icode) (mem, val);
5680 if (insn)
5681 {
5682 emit_insn (insn);
5683 return;
5684 }
5685 }
5686
5687 /* Otherwise we can implement this operation by emitting a barrier
5688 followed by a store of zero. */
5689 expand_builtin_synchronize ();
5690 emit_move_insn (mem, val);
5691 }
5692 \f
5693 /* Expand an expression EXP that calls a built-in function,
5694 with result going to TARGET if that's convenient
5695 (and in mode MODE if that's convenient).
5696 SUBTARGET may be used as the target for computing one of EXP's operands.
5697 IGNORE is nonzero if the value is to be ignored. */
5698
5699 rtx
5700 expand_builtin (tree exp, rtx target, rtx subtarget, enum machine_mode mode,
5701 int ignore)
5702 {
5703 tree fndecl = get_callee_fndecl (exp);
5704 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
5705 enum machine_mode target_mode = TYPE_MODE (TREE_TYPE (exp));
5706
5707 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
5708 return targetm.expand_builtin (exp, target, subtarget, mode, ignore);
5709
5710 /* When not optimizing, generate calls to library functions for a certain
5711 set of builtins. */
5712 if (!optimize
5713 && !called_as_built_in (fndecl)
5714 && DECL_ASSEMBLER_NAME_SET_P (fndecl)
5715 && fcode != BUILT_IN_ALLOCA
5716 && fcode != BUILT_IN_FREE)
5717 return expand_call (exp, target, ignore);
5718
5719 /* The built-in function expanders test for target == const0_rtx
5720 to determine whether the function's result will be ignored. */
5721 if (ignore)
5722 target = const0_rtx;
5723
5724 /* If the result of a pure or const built-in function is ignored, and
5725 none of its arguments are volatile, we can avoid expanding the
5726 built-in call and just evaluate the arguments for side-effects. */
5727 if (target == const0_rtx
5728 && (DECL_PURE_P (fndecl) || TREE_READONLY (fndecl)))
5729 {
5730 bool volatilep = false;
5731 tree arg;
5732 call_expr_arg_iterator iter;
5733
5734 FOR_EACH_CALL_EXPR_ARG (arg, iter, exp)
5735 if (TREE_THIS_VOLATILE (arg))
5736 {
5737 volatilep = true;
5738 break;
5739 }
5740
5741 if (! volatilep)
5742 {
5743 FOR_EACH_CALL_EXPR_ARG (arg, iter, exp)
5744 expand_expr (arg, const0_rtx, VOIDmode, EXPAND_NORMAL);
5745 return const0_rtx;
5746 }
5747 }
5748
5749 switch (fcode)
5750 {
5751 CASE_FLT_FN (BUILT_IN_FABS):
5752 target = expand_builtin_fabs (exp, target, subtarget);
5753 if (target)
5754 return target;
5755 break;
5756
5757 CASE_FLT_FN (BUILT_IN_COPYSIGN):
5758 target = expand_builtin_copysign (exp, target, subtarget);
5759 if (target)
5760 return target;
5761 break;
5762
5763 /* Just do a normal library call if we were unable to fold
5764 the values. */
5765 CASE_FLT_FN (BUILT_IN_CABS):
5766 break;
5767
5768 CASE_FLT_FN (BUILT_IN_EXP):
5769 CASE_FLT_FN (BUILT_IN_EXP10):
5770 CASE_FLT_FN (BUILT_IN_POW10):
5771 CASE_FLT_FN (BUILT_IN_EXP2):
5772 CASE_FLT_FN (BUILT_IN_EXPM1):
5773 CASE_FLT_FN (BUILT_IN_LOGB):
5774 CASE_FLT_FN (BUILT_IN_LOG):
5775 CASE_FLT_FN (BUILT_IN_LOG10):
5776 CASE_FLT_FN (BUILT_IN_LOG2):
5777 CASE_FLT_FN (BUILT_IN_LOG1P):
5778 CASE_FLT_FN (BUILT_IN_TAN):
5779 CASE_FLT_FN (BUILT_IN_ASIN):
5780 CASE_FLT_FN (BUILT_IN_ACOS):
5781 CASE_FLT_FN (BUILT_IN_ATAN):
5782 CASE_FLT_FN (BUILT_IN_SIGNIFICAND):
5783 /* Treat these like sqrt only if unsafe math optimizations are allowed,
5784 because of possible accuracy problems. */
5785 if (! flag_unsafe_math_optimizations)
5786 break;
5787 CASE_FLT_FN (BUILT_IN_SQRT):
5788 CASE_FLT_FN (BUILT_IN_FLOOR):
5789 CASE_FLT_FN (BUILT_IN_CEIL):
5790 CASE_FLT_FN (BUILT_IN_TRUNC):
5791 CASE_FLT_FN (BUILT_IN_ROUND):
5792 CASE_FLT_FN (BUILT_IN_NEARBYINT):
5793 CASE_FLT_FN (BUILT_IN_RINT):
5794 target = expand_builtin_mathfn (exp, target, subtarget);
5795 if (target)
5796 return target;
5797 break;
5798
5799 CASE_FLT_FN (BUILT_IN_ILOGB):
5800 if (! flag_unsafe_math_optimizations)
5801 break;
5802 CASE_FLT_FN (BUILT_IN_ISINF):
5803 CASE_FLT_FN (BUILT_IN_FINITE):
5804 case BUILT_IN_ISFINITE:
5805 case BUILT_IN_ISNORMAL:
5806 target = expand_builtin_interclass_mathfn (exp, target, subtarget);
5807 if (target)
5808 return target;
5809 break;
5810
5811 CASE_FLT_FN (BUILT_IN_LCEIL):
5812 CASE_FLT_FN (BUILT_IN_LLCEIL):
5813 CASE_FLT_FN (BUILT_IN_LFLOOR):
5814 CASE_FLT_FN (BUILT_IN_LLFLOOR):
5815 target = expand_builtin_int_roundingfn (exp, target);
5816 if (target)
5817 return target;
5818 break;
5819
5820 CASE_FLT_FN (BUILT_IN_LRINT):
5821 CASE_FLT_FN (BUILT_IN_LLRINT):
5822 CASE_FLT_FN (BUILT_IN_LROUND):
5823 CASE_FLT_FN (BUILT_IN_LLROUND):
5824 target = expand_builtin_int_roundingfn_2 (exp, target);
5825 if (target)
5826 return target;
5827 break;
5828
5829 CASE_FLT_FN (BUILT_IN_POW):
5830 target = expand_builtin_pow (exp, target, subtarget);
5831 if (target)
5832 return target;
5833 break;
5834
5835 CASE_FLT_FN (BUILT_IN_POWI):
5836 target = expand_builtin_powi (exp, target, subtarget);
5837 if (target)
5838 return target;
5839 break;
5840
5841 CASE_FLT_FN (BUILT_IN_ATAN2):
5842 CASE_FLT_FN (BUILT_IN_LDEXP):
5843 CASE_FLT_FN (BUILT_IN_SCALB):
5844 CASE_FLT_FN (BUILT_IN_SCALBN):
5845 CASE_FLT_FN (BUILT_IN_SCALBLN):
5846 if (! flag_unsafe_math_optimizations)
5847 break;
5848
5849 CASE_FLT_FN (BUILT_IN_FMOD):
5850 CASE_FLT_FN (BUILT_IN_REMAINDER):
5851 CASE_FLT_FN (BUILT_IN_DREM):
5852 target = expand_builtin_mathfn_2 (exp, target, subtarget);
5853 if (target)
5854 return target;
5855 break;
5856
5857 CASE_FLT_FN (BUILT_IN_CEXPI):
5858 target = expand_builtin_cexpi (exp, target, subtarget);
5859 gcc_assert (target);
5860 return target;
5861
5862 CASE_FLT_FN (BUILT_IN_SIN):
5863 CASE_FLT_FN (BUILT_IN_COS):
5864 if (! flag_unsafe_math_optimizations)
5865 break;
5866 target = expand_builtin_mathfn_3 (exp, target, subtarget);
5867 if (target)
5868 return target;
5869 break;
5870
5871 CASE_FLT_FN (BUILT_IN_SINCOS):
5872 if (! flag_unsafe_math_optimizations)
5873 break;
5874 target = expand_builtin_sincos (exp);
5875 if (target)
5876 return target;
5877 break;
5878
5879 case BUILT_IN_APPLY_ARGS:
5880 return expand_builtin_apply_args ();
5881
5882 /* __builtin_apply (FUNCTION, ARGUMENTS, ARGSIZE) invokes
5883 FUNCTION with a copy of the parameters described by
5884 ARGUMENTS, and ARGSIZE. It returns a block of memory
5885 allocated on the stack into which is stored all the registers
5886 that might possibly be used for returning the result of a
5887 function. ARGUMENTS is the value returned by
5888 __builtin_apply_args. ARGSIZE is the number of bytes of
5889 arguments that must be copied. ??? How should this value be
5890 computed? We'll also need a safe worst case value for varargs
5891 functions. */
5892 case BUILT_IN_APPLY:
5893 if (!validate_arglist (exp, POINTER_TYPE,
5894 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE)
5895 && !validate_arglist (exp, REFERENCE_TYPE,
5896 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
5897 return const0_rtx;
5898 else
5899 {
5900 rtx ops[3];
5901
5902 ops[0] = expand_normal (CALL_EXPR_ARG (exp, 0));
5903 ops[1] = expand_normal (CALL_EXPR_ARG (exp, 1));
5904 ops[2] = expand_normal (CALL_EXPR_ARG (exp, 2));
5905
5906 return expand_builtin_apply (ops[0], ops[1], ops[2]);
5907 }
5908
5909 /* __builtin_return (RESULT) causes the function to return the
5910 value described by RESULT. RESULT is address of the block of
5911 memory returned by __builtin_apply. */
5912 case BUILT_IN_RETURN:
5913 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
5914 expand_builtin_return (expand_normal (CALL_EXPR_ARG (exp, 0)));
5915 return const0_rtx;
5916
5917 case BUILT_IN_SAVEREGS:
5918 return expand_builtin_saveregs ();
5919
5920 case BUILT_IN_ARGS_INFO:
5921 return expand_builtin_args_info (exp);
5922
5923 case BUILT_IN_VA_ARG_PACK:
5924 /* All valid uses of __builtin_va_arg_pack () are removed during
5925 inlining. */
5926 error ("%Kinvalid use of %<__builtin_va_arg_pack ()%>", exp);
5927 return const0_rtx;
5928
5929 case BUILT_IN_VA_ARG_PACK_LEN:
5930 /* All valid uses of __builtin_va_arg_pack_len () are removed during
5931 inlining. */
5932 error ("%Kinvalid use of %<__builtin_va_arg_pack_len ()%>", exp);
5933 return const0_rtx;
5934
5935 /* Return the address of the first anonymous stack arg. */
5936 case BUILT_IN_NEXT_ARG:
5937 if (fold_builtin_next_arg (exp, false))
5938 return const0_rtx;
5939 return expand_builtin_next_arg ();
5940
5941 case BUILT_IN_CLEAR_CACHE:
5942 target = expand_builtin___clear_cache (exp);
5943 if (target)
5944 return target;
5945 break;
5946
5947 case BUILT_IN_CLASSIFY_TYPE:
5948 return expand_builtin_classify_type (exp);
5949
5950 case BUILT_IN_CONSTANT_P:
5951 return const0_rtx;
5952
5953 case BUILT_IN_FRAME_ADDRESS:
5954 case BUILT_IN_RETURN_ADDRESS:
5955 return expand_builtin_frame_address (fndecl, exp);
5956
5957 /* Returns the address of the area where the structure is returned.
5958 0 otherwise. */
5959 case BUILT_IN_AGGREGATE_INCOMING_ADDRESS:
5960 if (call_expr_nargs (exp) != 0
5961 || ! AGGREGATE_TYPE_P (TREE_TYPE (TREE_TYPE (current_function_decl)))
5962 || !MEM_P (DECL_RTL (DECL_RESULT (current_function_decl))))
5963 return const0_rtx;
5964 else
5965 return XEXP (DECL_RTL (DECL_RESULT (current_function_decl)), 0);
5966
5967 case BUILT_IN_ALLOCA:
5968 target = expand_builtin_alloca (exp, target);
5969 if (target)
5970 return target;
5971 break;
5972
5973 case BUILT_IN_STACK_SAVE:
5974 return expand_stack_save ();
5975
5976 case BUILT_IN_STACK_RESTORE:
5977 expand_stack_restore (CALL_EXPR_ARG (exp, 0));
5978 return const0_rtx;
5979
5980 case BUILT_IN_BSWAP32:
5981 case BUILT_IN_BSWAP64:
5982 target = expand_builtin_bswap (exp, target, subtarget);
5983
5984 if (target)
5985 return target;
5986 break;
5987
5988 CASE_INT_FN (BUILT_IN_FFS):
5989 case BUILT_IN_FFSIMAX:
5990 target = expand_builtin_unop (target_mode, exp, target,
5991 subtarget, ffs_optab);
5992 if (target)
5993 return target;
5994 break;
5995
5996 CASE_INT_FN (BUILT_IN_CLZ):
5997 case BUILT_IN_CLZIMAX:
5998 target = expand_builtin_unop (target_mode, exp, target,
5999 subtarget, clz_optab);
6000 if (target)
6001 return target;
6002 break;
6003
6004 CASE_INT_FN (BUILT_IN_CTZ):
6005 case BUILT_IN_CTZIMAX:
6006 target = expand_builtin_unop (target_mode, exp, target,
6007 subtarget, ctz_optab);
6008 if (target)
6009 return target;
6010 break;
6011
6012 CASE_INT_FN (BUILT_IN_POPCOUNT):
6013 case BUILT_IN_POPCOUNTIMAX:
6014 target = expand_builtin_unop (target_mode, exp, target,
6015 subtarget, popcount_optab);
6016 if (target)
6017 return target;
6018 break;
6019
6020 CASE_INT_FN (BUILT_IN_PARITY):
6021 case BUILT_IN_PARITYIMAX:
6022 target = expand_builtin_unop (target_mode, exp, target,
6023 subtarget, parity_optab);
6024 if (target)
6025 return target;
6026 break;
6027
6028 case BUILT_IN_STRLEN:
6029 target = expand_builtin_strlen (exp, target, target_mode);
6030 if (target)
6031 return target;
6032 break;
6033
6034 case BUILT_IN_STRCPY:
6035 target = expand_builtin_strcpy (exp, target);
6036 if (target)
6037 return target;
6038 break;
6039
6040 case BUILT_IN_STRNCPY:
6041 target = expand_builtin_strncpy (exp, target);
6042 if (target)
6043 return target;
6044 break;
6045
6046 case BUILT_IN_STPCPY:
6047 target = expand_builtin_stpcpy (exp, target, mode);
6048 if (target)
6049 return target;
6050 break;
6051
6052 case BUILT_IN_MEMCPY:
6053 target = expand_builtin_memcpy (exp, target);
6054 if (target)
6055 return target;
6056 break;
6057
6058 case BUILT_IN_MEMPCPY:
6059 target = expand_builtin_mempcpy (exp, target, mode);
6060 if (target)
6061 return target;
6062 break;
6063
6064 case BUILT_IN_MEMSET:
6065 target = expand_builtin_memset (exp, target, mode);
6066 if (target)
6067 return target;
6068 break;
6069
6070 case BUILT_IN_BZERO:
6071 target = expand_builtin_bzero (exp);
6072 if (target)
6073 return target;
6074 break;
6075
6076 case BUILT_IN_STRCMP:
6077 target = expand_builtin_strcmp (exp, target);
6078 if (target)
6079 return target;
6080 break;
6081
6082 case BUILT_IN_STRNCMP:
6083 target = expand_builtin_strncmp (exp, target, mode);
6084 if (target)
6085 return target;
6086 break;
6087
6088 case BUILT_IN_BCMP:
6089 case BUILT_IN_MEMCMP:
6090 target = expand_builtin_memcmp (exp, target, mode);
6091 if (target)
6092 return target;
6093 break;
6094
6095 case BUILT_IN_SETJMP:
6096 /* This should have been lowered to the builtins below. */
6097 gcc_unreachable ();
6098
6099 case BUILT_IN_SETJMP_SETUP:
6100 /* __builtin_setjmp_setup is passed a pointer to an array of five words
6101 and the receiver label. */
6102 if (validate_arglist (exp, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
6103 {
6104 rtx buf_addr = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
6105 VOIDmode, EXPAND_NORMAL);
6106 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 1), 0);
6107 rtx label_r = label_rtx (label);
6108
6109 /* This is copied from the handling of non-local gotos. */
6110 expand_builtin_setjmp_setup (buf_addr, label_r);
6111 nonlocal_goto_handler_labels
6112 = gen_rtx_EXPR_LIST (VOIDmode, label_r,
6113 nonlocal_goto_handler_labels);
6114 /* ??? Do not let expand_label treat us as such since we would
6115 not want to be both on the list of non-local labels and on
6116 the list of forced labels. */
6117 FORCED_LABEL (label) = 0;
6118 return const0_rtx;
6119 }
6120 break;
6121
6122 case BUILT_IN_SETJMP_DISPATCHER:
6123 /* __builtin_setjmp_dispatcher is passed the dispatcher label. */
6124 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6125 {
6126 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 0), 0);
6127 rtx label_r = label_rtx (label);
6128
6129 /* Remove the dispatcher label from the list of non-local labels
6130 since the receiver labels have been added to it above. */
6131 remove_node_from_expr_list (label_r, &nonlocal_goto_handler_labels);
6132 return const0_rtx;
6133 }
6134 break;
6135
6136 case BUILT_IN_SETJMP_RECEIVER:
6137 /* __builtin_setjmp_receiver is passed the receiver label. */
6138 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6139 {
6140 tree label = TREE_OPERAND (CALL_EXPR_ARG (exp, 0), 0);
6141 rtx label_r = label_rtx (label);
6142
6143 expand_builtin_setjmp_receiver (label_r);
6144 return const0_rtx;
6145 }
6146 break;
6147
6148 /* __builtin_longjmp is passed a pointer to an array of five words.
6149 It's similar to the C library longjmp function but works with
6150 __builtin_setjmp above. */
6151 case BUILT_IN_LONGJMP:
6152 if (validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
6153 {
6154 rtx buf_addr = expand_expr (CALL_EXPR_ARG (exp, 0), subtarget,
6155 VOIDmode, EXPAND_NORMAL);
6156 rtx value = expand_normal (CALL_EXPR_ARG (exp, 1));
6157
6158 if (value != const1_rtx)
6159 {
6160 error ("%<__builtin_longjmp%> second argument must be 1");
6161 return const0_rtx;
6162 }
6163
6164 expand_builtin_longjmp (buf_addr, value);
6165 return const0_rtx;
6166 }
6167 break;
6168
6169 case BUILT_IN_NONLOCAL_GOTO:
6170 target = expand_builtin_nonlocal_goto (exp);
6171 if (target)
6172 return target;
6173 break;
6174
6175 /* This updates the setjmp buffer that is its argument with the value
6176 of the current stack pointer. */
6177 case BUILT_IN_UPDATE_SETJMP_BUF:
6178 if (validate_arglist (exp, POINTER_TYPE, VOID_TYPE))
6179 {
6180 rtx buf_addr
6181 = expand_normal (CALL_EXPR_ARG (exp, 0));
6182
6183 expand_builtin_update_setjmp_buf (buf_addr);
6184 return const0_rtx;
6185 }
6186 break;
6187
6188 case BUILT_IN_TRAP:
6189 expand_builtin_trap ();
6190 return const0_rtx;
6191
6192 case BUILT_IN_UNREACHABLE:
6193 expand_builtin_unreachable ();
6194 return const0_rtx;
6195
6196 CASE_FLT_FN (BUILT_IN_SIGNBIT):
6197 case BUILT_IN_SIGNBITD32:
6198 case BUILT_IN_SIGNBITD64:
6199 case BUILT_IN_SIGNBITD128:
6200 target = expand_builtin_signbit (exp, target);
6201 if (target)
6202 return target;
6203 break;
6204
6205 /* Various hooks for the DWARF 2 __throw routine. */
6206 case BUILT_IN_UNWIND_INIT:
6207 expand_builtin_unwind_init ();
6208 return const0_rtx;
6209 case BUILT_IN_DWARF_CFA:
6210 return virtual_cfa_rtx;
6211 #ifdef DWARF2_UNWIND_INFO
6212 case BUILT_IN_DWARF_SP_COLUMN:
6213 return expand_builtin_dwarf_sp_column ();
6214 case BUILT_IN_INIT_DWARF_REG_SIZES:
6215 expand_builtin_init_dwarf_reg_sizes (CALL_EXPR_ARG (exp, 0));
6216 return const0_rtx;
6217 #endif
6218 case BUILT_IN_FROB_RETURN_ADDR:
6219 return expand_builtin_frob_return_addr (CALL_EXPR_ARG (exp, 0));
6220 case BUILT_IN_EXTRACT_RETURN_ADDR:
6221 return expand_builtin_extract_return_addr (CALL_EXPR_ARG (exp, 0));
6222 case BUILT_IN_EH_RETURN:
6223 expand_builtin_eh_return (CALL_EXPR_ARG (exp, 0),
6224 CALL_EXPR_ARG (exp, 1));
6225 return const0_rtx;
6226 #ifdef EH_RETURN_DATA_REGNO
6227 case BUILT_IN_EH_RETURN_DATA_REGNO:
6228 return expand_builtin_eh_return_data_regno (exp);
6229 #endif
6230 case BUILT_IN_EXTEND_POINTER:
6231 return expand_builtin_extend_pointer (CALL_EXPR_ARG (exp, 0));
6232 case BUILT_IN_EH_POINTER:
6233 return expand_builtin_eh_pointer (exp);
6234 case BUILT_IN_EH_FILTER:
6235 return expand_builtin_eh_filter (exp);
6236 case BUILT_IN_EH_COPY_VALUES:
6237 return expand_builtin_eh_copy_values (exp);
6238
6239 case BUILT_IN_VA_START:
6240 return expand_builtin_va_start (exp);
6241 case BUILT_IN_VA_END:
6242 return expand_builtin_va_end (exp);
6243 case BUILT_IN_VA_COPY:
6244 return expand_builtin_va_copy (exp);
6245 case BUILT_IN_EXPECT:
6246 return expand_builtin_expect (exp, target);
6247 case BUILT_IN_PREFETCH:
6248 expand_builtin_prefetch (exp);
6249 return const0_rtx;
6250
6251 case BUILT_IN_PROFILE_FUNC_ENTER:
6252 return expand_builtin_profile_func (false);
6253 case BUILT_IN_PROFILE_FUNC_EXIT:
6254 return expand_builtin_profile_func (true);
6255
6256 case BUILT_IN_INIT_TRAMPOLINE:
6257 return expand_builtin_init_trampoline (exp);
6258 case BUILT_IN_ADJUST_TRAMPOLINE:
6259 return expand_builtin_adjust_trampoline (exp);
6260
6261 case BUILT_IN_FORK:
6262 case BUILT_IN_EXECL:
6263 case BUILT_IN_EXECV:
6264 case BUILT_IN_EXECLP:
6265 case BUILT_IN_EXECLE:
6266 case BUILT_IN_EXECVP:
6267 case BUILT_IN_EXECVE:
6268 target = expand_builtin_fork_or_exec (fndecl, exp, target, ignore);
6269 if (target)
6270 return target;
6271 break;
6272
6273 case BUILT_IN_FETCH_AND_ADD_1:
6274 case BUILT_IN_FETCH_AND_ADD_2:
6275 case BUILT_IN_FETCH_AND_ADD_4:
6276 case BUILT_IN_FETCH_AND_ADD_8:
6277 case BUILT_IN_FETCH_AND_ADD_16:
6278 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_ADD_1);
6279 target = expand_builtin_sync_operation (mode, exp, PLUS,
6280 false, target, ignore);
6281 if (target)
6282 return target;
6283 break;
6284
6285 case BUILT_IN_FETCH_AND_SUB_1:
6286 case BUILT_IN_FETCH_AND_SUB_2:
6287 case BUILT_IN_FETCH_AND_SUB_4:
6288 case BUILT_IN_FETCH_AND_SUB_8:
6289 case BUILT_IN_FETCH_AND_SUB_16:
6290 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_SUB_1);
6291 target = expand_builtin_sync_operation (mode, exp, MINUS,
6292 false, target, ignore);
6293 if (target)
6294 return target;
6295 break;
6296
6297 case BUILT_IN_FETCH_AND_OR_1:
6298 case BUILT_IN_FETCH_AND_OR_2:
6299 case BUILT_IN_FETCH_AND_OR_4:
6300 case BUILT_IN_FETCH_AND_OR_8:
6301 case BUILT_IN_FETCH_AND_OR_16:
6302 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_OR_1);
6303 target = expand_builtin_sync_operation (mode, exp, IOR,
6304 false, target, ignore);
6305 if (target)
6306 return target;
6307 break;
6308
6309 case BUILT_IN_FETCH_AND_AND_1:
6310 case BUILT_IN_FETCH_AND_AND_2:
6311 case BUILT_IN_FETCH_AND_AND_4:
6312 case BUILT_IN_FETCH_AND_AND_8:
6313 case BUILT_IN_FETCH_AND_AND_16:
6314 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_AND_1);
6315 target = expand_builtin_sync_operation (mode, exp, AND,
6316 false, target, ignore);
6317 if (target)
6318 return target;
6319 break;
6320
6321 case BUILT_IN_FETCH_AND_XOR_1:
6322 case BUILT_IN_FETCH_AND_XOR_2:
6323 case BUILT_IN_FETCH_AND_XOR_4:
6324 case BUILT_IN_FETCH_AND_XOR_8:
6325 case BUILT_IN_FETCH_AND_XOR_16:
6326 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_XOR_1);
6327 target = expand_builtin_sync_operation (mode, exp, XOR,
6328 false, target, ignore);
6329 if (target)
6330 return target;
6331 break;
6332
6333 case BUILT_IN_FETCH_AND_NAND_1:
6334 case BUILT_IN_FETCH_AND_NAND_2:
6335 case BUILT_IN_FETCH_AND_NAND_4:
6336 case BUILT_IN_FETCH_AND_NAND_8:
6337 case BUILT_IN_FETCH_AND_NAND_16:
6338 mode = get_builtin_sync_mode (fcode - BUILT_IN_FETCH_AND_NAND_1);
6339 target = expand_builtin_sync_operation (mode, exp, NOT,
6340 false, target, ignore);
6341 if (target)
6342 return target;
6343 break;
6344
6345 case BUILT_IN_ADD_AND_FETCH_1:
6346 case BUILT_IN_ADD_AND_FETCH_2:
6347 case BUILT_IN_ADD_AND_FETCH_4:
6348 case BUILT_IN_ADD_AND_FETCH_8:
6349 case BUILT_IN_ADD_AND_FETCH_16:
6350 mode = get_builtin_sync_mode (fcode - BUILT_IN_ADD_AND_FETCH_1);
6351 target = expand_builtin_sync_operation (mode, exp, PLUS,
6352 true, target, ignore);
6353 if (target)
6354 return target;
6355 break;
6356
6357 case BUILT_IN_SUB_AND_FETCH_1:
6358 case BUILT_IN_SUB_AND_FETCH_2:
6359 case BUILT_IN_SUB_AND_FETCH_4:
6360 case BUILT_IN_SUB_AND_FETCH_8:
6361 case BUILT_IN_SUB_AND_FETCH_16:
6362 mode = get_builtin_sync_mode (fcode - BUILT_IN_SUB_AND_FETCH_1);
6363 target = expand_builtin_sync_operation (mode, exp, MINUS,
6364 true, target, ignore);
6365 if (target)
6366 return target;
6367 break;
6368
6369 case BUILT_IN_OR_AND_FETCH_1:
6370 case BUILT_IN_OR_AND_FETCH_2:
6371 case BUILT_IN_OR_AND_FETCH_4:
6372 case BUILT_IN_OR_AND_FETCH_8:
6373 case BUILT_IN_OR_AND_FETCH_16:
6374 mode = get_builtin_sync_mode (fcode - BUILT_IN_OR_AND_FETCH_1);
6375 target = expand_builtin_sync_operation (mode, exp, IOR,
6376 true, target, ignore);
6377 if (target)
6378 return target;
6379 break;
6380
6381 case BUILT_IN_AND_AND_FETCH_1:
6382 case BUILT_IN_AND_AND_FETCH_2:
6383 case BUILT_IN_AND_AND_FETCH_4:
6384 case BUILT_IN_AND_AND_FETCH_8:
6385 case BUILT_IN_AND_AND_FETCH_16:
6386 mode = get_builtin_sync_mode (fcode - BUILT_IN_AND_AND_FETCH_1);
6387 target = expand_builtin_sync_operation (mode, exp, AND,
6388 true, target, ignore);
6389 if (target)
6390 return target;
6391 break;
6392
6393 case BUILT_IN_XOR_AND_FETCH_1:
6394 case BUILT_IN_XOR_AND_FETCH_2:
6395 case BUILT_IN_XOR_AND_FETCH_4:
6396 case BUILT_IN_XOR_AND_FETCH_8:
6397 case BUILT_IN_XOR_AND_FETCH_16:
6398 mode = get_builtin_sync_mode (fcode - BUILT_IN_XOR_AND_FETCH_1);
6399 target = expand_builtin_sync_operation (mode, exp, XOR,
6400 true, target, ignore);
6401 if (target)
6402 return target;
6403 break;
6404
6405 case BUILT_IN_NAND_AND_FETCH_1:
6406 case BUILT_IN_NAND_AND_FETCH_2:
6407 case BUILT_IN_NAND_AND_FETCH_4:
6408 case BUILT_IN_NAND_AND_FETCH_8:
6409 case BUILT_IN_NAND_AND_FETCH_16:
6410 mode = get_builtin_sync_mode (fcode - BUILT_IN_NAND_AND_FETCH_1);
6411 target = expand_builtin_sync_operation (mode, exp, NOT,
6412 true, target, ignore);
6413 if (target)
6414 return target;
6415 break;
6416
6417 case BUILT_IN_BOOL_COMPARE_AND_SWAP_1:
6418 case BUILT_IN_BOOL_COMPARE_AND_SWAP_2:
6419 case BUILT_IN_BOOL_COMPARE_AND_SWAP_4:
6420 case BUILT_IN_BOOL_COMPARE_AND_SWAP_8:
6421 case BUILT_IN_BOOL_COMPARE_AND_SWAP_16:
6422 if (mode == VOIDmode)
6423 mode = TYPE_MODE (boolean_type_node);
6424 if (!target || !register_operand (target, mode))
6425 target = gen_reg_rtx (mode);
6426
6427 mode = get_builtin_sync_mode (fcode - BUILT_IN_BOOL_COMPARE_AND_SWAP_1);
6428 target = expand_builtin_compare_and_swap (mode, exp, true, target);
6429 if (target)
6430 return target;
6431 break;
6432
6433 case BUILT_IN_VAL_COMPARE_AND_SWAP_1:
6434 case BUILT_IN_VAL_COMPARE_AND_SWAP_2:
6435 case BUILT_IN_VAL_COMPARE_AND_SWAP_4:
6436 case BUILT_IN_VAL_COMPARE_AND_SWAP_8:
6437 case BUILT_IN_VAL_COMPARE_AND_SWAP_16:
6438 mode = get_builtin_sync_mode (fcode - BUILT_IN_VAL_COMPARE_AND_SWAP_1);
6439 target = expand_builtin_compare_and_swap (mode, exp, false, target);
6440 if (target)
6441 return target;
6442 break;
6443
6444 case BUILT_IN_LOCK_TEST_AND_SET_1:
6445 case BUILT_IN_LOCK_TEST_AND_SET_2:
6446 case BUILT_IN_LOCK_TEST_AND_SET_4:
6447 case BUILT_IN_LOCK_TEST_AND_SET_8:
6448 case BUILT_IN_LOCK_TEST_AND_SET_16:
6449 mode = get_builtin_sync_mode (fcode - BUILT_IN_LOCK_TEST_AND_SET_1);
6450 target = expand_builtin_lock_test_and_set (mode, exp, target);
6451 if (target)
6452 return target;
6453 break;
6454
6455 case BUILT_IN_LOCK_RELEASE_1:
6456 case BUILT_IN_LOCK_RELEASE_2:
6457 case BUILT_IN_LOCK_RELEASE_4:
6458 case BUILT_IN_LOCK_RELEASE_8:
6459 case BUILT_IN_LOCK_RELEASE_16:
6460 mode = get_builtin_sync_mode (fcode - BUILT_IN_LOCK_RELEASE_1);
6461 expand_builtin_lock_release (mode, exp);
6462 return const0_rtx;
6463
6464 case BUILT_IN_SYNCHRONIZE:
6465 expand_builtin_synchronize ();
6466 return const0_rtx;
6467
6468 case BUILT_IN_OBJECT_SIZE:
6469 return expand_builtin_object_size (exp);
6470
6471 case BUILT_IN_MEMCPY_CHK:
6472 case BUILT_IN_MEMPCPY_CHK:
6473 case BUILT_IN_MEMMOVE_CHK:
6474 case BUILT_IN_MEMSET_CHK:
6475 target = expand_builtin_memory_chk (exp, target, mode, fcode);
6476 if (target)
6477 return target;
6478 break;
6479
6480 case BUILT_IN_STRCPY_CHK:
6481 case BUILT_IN_STPCPY_CHK:
6482 case BUILT_IN_STRNCPY_CHK:
6483 case BUILT_IN_STRCAT_CHK:
6484 case BUILT_IN_STRNCAT_CHK:
6485 case BUILT_IN_SNPRINTF_CHK:
6486 case BUILT_IN_VSNPRINTF_CHK:
6487 maybe_emit_chk_warning (exp, fcode);
6488 break;
6489
6490 case BUILT_IN_SPRINTF_CHK:
6491 case BUILT_IN_VSPRINTF_CHK:
6492 maybe_emit_sprintf_chk_warning (exp, fcode);
6493 break;
6494
6495 case BUILT_IN_FREE:
6496 maybe_emit_free_warning (exp);
6497 break;
6498
6499 default: /* just do library call, if unknown builtin */
6500 break;
6501 }
6502
6503 /* The switch statement above can drop through to cause the function
6504 to be called normally. */
6505 return expand_call (exp, target, ignore);
6506 }
6507
6508 /* Determine whether a tree node represents a call to a built-in
6509 function. If the tree T is a call to a built-in function with
6510 the right number of arguments of the appropriate types, return
6511 the DECL_FUNCTION_CODE of the call, e.g. BUILT_IN_SQRT.
6512 Otherwise the return value is END_BUILTINS. */
6513
6514 enum built_in_function
6515 builtin_mathfn_code (const_tree t)
6516 {
6517 const_tree fndecl, arg, parmlist;
6518 const_tree argtype, parmtype;
6519 const_call_expr_arg_iterator iter;
6520
6521 if (TREE_CODE (t) != CALL_EXPR
6522 || TREE_CODE (CALL_EXPR_FN (t)) != ADDR_EXPR)
6523 return END_BUILTINS;
6524
6525 fndecl = get_callee_fndecl (t);
6526 if (fndecl == NULL_TREE
6527 || TREE_CODE (fndecl) != FUNCTION_DECL
6528 || ! DECL_BUILT_IN (fndecl)
6529 || DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
6530 return END_BUILTINS;
6531
6532 parmlist = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
6533 init_const_call_expr_arg_iterator (t, &iter);
6534 for (; parmlist; parmlist = TREE_CHAIN (parmlist))
6535 {
6536 /* If a function doesn't take a variable number of arguments,
6537 the last element in the list will have type `void'. */
6538 parmtype = TREE_VALUE (parmlist);
6539 if (VOID_TYPE_P (parmtype))
6540 {
6541 if (more_const_call_expr_args_p (&iter))
6542 return END_BUILTINS;
6543 return DECL_FUNCTION_CODE (fndecl);
6544 }
6545
6546 if (! more_const_call_expr_args_p (&iter))
6547 return END_BUILTINS;
6548
6549 arg = next_const_call_expr_arg (&iter);
6550 argtype = TREE_TYPE (arg);
6551
6552 if (SCALAR_FLOAT_TYPE_P (parmtype))
6553 {
6554 if (! SCALAR_FLOAT_TYPE_P (argtype))
6555 return END_BUILTINS;
6556 }
6557 else if (COMPLEX_FLOAT_TYPE_P (parmtype))
6558 {
6559 if (! COMPLEX_FLOAT_TYPE_P (argtype))
6560 return END_BUILTINS;
6561 }
6562 else if (POINTER_TYPE_P (parmtype))
6563 {
6564 if (! POINTER_TYPE_P (argtype))
6565 return END_BUILTINS;
6566 }
6567 else if (INTEGRAL_TYPE_P (parmtype))
6568 {
6569 if (! INTEGRAL_TYPE_P (argtype))
6570 return END_BUILTINS;
6571 }
6572 else
6573 return END_BUILTINS;
6574 }
6575
6576 /* Variable-length argument list. */
6577 return DECL_FUNCTION_CODE (fndecl);
6578 }
6579
6580 /* Fold a call to __builtin_constant_p, if we know its argument ARG will
6581 evaluate to a constant. */
6582
6583 static tree
6584 fold_builtin_constant_p (tree arg)
6585 {
6586 /* We return 1 for a numeric type that's known to be a constant
6587 value at compile-time or for an aggregate type that's a
6588 literal constant. */
6589 STRIP_NOPS (arg);
6590
6591 /* If we know this is a constant, emit the constant of one. */
6592 if (CONSTANT_CLASS_P (arg)
6593 || (TREE_CODE (arg) == CONSTRUCTOR
6594 && TREE_CONSTANT (arg)))
6595 return integer_one_node;
6596 if (TREE_CODE (arg) == ADDR_EXPR)
6597 {
6598 tree op = TREE_OPERAND (arg, 0);
6599 if (TREE_CODE (op) == STRING_CST
6600 || (TREE_CODE (op) == ARRAY_REF
6601 && integer_zerop (TREE_OPERAND (op, 1))
6602 && TREE_CODE (TREE_OPERAND (op, 0)) == STRING_CST))
6603 return integer_one_node;
6604 }
6605
6606 /* If this expression has side effects, show we don't know it to be a
6607 constant. Likewise if it's a pointer or aggregate type since in
6608 those case we only want literals, since those are only optimized
6609 when generating RTL, not later.
6610 And finally, if we are compiling an initializer, not code, we
6611 need to return a definite result now; there's not going to be any
6612 more optimization done. */
6613 if (TREE_SIDE_EFFECTS (arg)
6614 || AGGREGATE_TYPE_P (TREE_TYPE (arg))
6615 || POINTER_TYPE_P (TREE_TYPE (arg))
6616 || cfun == 0
6617 || folding_initializer)
6618 return integer_zero_node;
6619
6620 return NULL_TREE;
6621 }
6622
6623 /* Create builtin_expect with PRED and EXPECTED as its arguments and
6624 return it as a truthvalue. */
6625
6626 static tree
6627 build_builtin_expect_predicate (location_t loc, tree pred, tree expected)
6628 {
6629 tree fn, arg_types, pred_type, expected_type, call_expr, ret_type;
6630
6631 fn = built_in_decls[BUILT_IN_EXPECT];
6632 arg_types = TYPE_ARG_TYPES (TREE_TYPE (fn));
6633 ret_type = TREE_TYPE (TREE_TYPE (fn));
6634 pred_type = TREE_VALUE (arg_types);
6635 expected_type = TREE_VALUE (TREE_CHAIN (arg_types));
6636
6637 pred = fold_convert_loc (loc, pred_type, pred);
6638 expected = fold_convert_loc (loc, expected_type, expected);
6639 call_expr = build_call_expr_loc (loc, fn, 2, pred, expected);
6640
6641 return build2 (NE_EXPR, TREE_TYPE (pred), call_expr,
6642 build_int_cst (ret_type, 0));
6643 }
6644
6645 /* Fold a call to builtin_expect with arguments ARG0 and ARG1. Return
6646 NULL_TREE if no simplification is possible. */
6647
6648 static tree
6649 fold_builtin_expect (location_t loc, tree arg0, tree arg1)
6650 {
6651 tree inner, fndecl;
6652 enum tree_code code;
6653
6654 /* If this is a builtin_expect within a builtin_expect keep the
6655 inner one. See through a comparison against a constant. It
6656 might have been added to create a thruthvalue. */
6657 inner = arg0;
6658 if (COMPARISON_CLASS_P (inner)
6659 && TREE_CODE (TREE_OPERAND (inner, 1)) == INTEGER_CST)
6660 inner = TREE_OPERAND (inner, 0);
6661
6662 if (TREE_CODE (inner) == CALL_EXPR
6663 && (fndecl = get_callee_fndecl (inner))
6664 && DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_NORMAL
6665 && DECL_FUNCTION_CODE (fndecl) == BUILT_IN_EXPECT)
6666 return arg0;
6667
6668 /* Distribute the expected value over short-circuiting operators.
6669 See through the cast from truthvalue_type_node to long. */
6670 inner = arg0;
6671 while (TREE_CODE (inner) == NOP_EXPR
6672 && INTEGRAL_TYPE_P (TREE_TYPE (inner))
6673 && INTEGRAL_TYPE_P (TREE_TYPE (TREE_OPERAND (inner, 0))))
6674 inner = TREE_OPERAND (inner, 0);
6675
6676 code = TREE_CODE (inner);
6677 if (code == TRUTH_ANDIF_EXPR || code == TRUTH_ORIF_EXPR)
6678 {
6679 tree op0 = TREE_OPERAND (inner, 0);
6680 tree op1 = TREE_OPERAND (inner, 1);
6681
6682 op0 = build_builtin_expect_predicate (loc, op0, arg1);
6683 op1 = build_builtin_expect_predicate (loc, op1, arg1);
6684 inner = build2 (code, TREE_TYPE (inner), op0, op1);
6685
6686 return fold_convert_loc (loc, TREE_TYPE (arg0), inner);
6687 }
6688
6689 /* If the argument isn't invariant then there's nothing else we can do. */
6690 if (!TREE_CONSTANT (arg0))
6691 return NULL_TREE;
6692
6693 /* If we expect that a comparison against the argument will fold to
6694 a constant return the constant. In practice, this means a true
6695 constant or the address of a non-weak symbol. */
6696 inner = arg0;
6697 STRIP_NOPS (inner);
6698 if (TREE_CODE (inner) == ADDR_EXPR)
6699 {
6700 do
6701 {
6702 inner = TREE_OPERAND (inner, 0);
6703 }
6704 while (TREE_CODE (inner) == COMPONENT_REF
6705 || TREE_CODE (inner) == ARRAY_REF);
6706 if ((TREE_CODE (inner) == VAR_DECL
6707 || TREE_CODE (inner) == FUNCTION_DECL)
6708 && DECL_WEAK (inner))
6709 return NULL_TREE;
6710 }
6711
6712 /* Otherwise, ARG0 already has the proper type for the return value. */
6713 return arg0;
6714 }
6715
6716 /* Fold a call to __builtin_classify_type with argument ARG. */
6717
6718 static tree
6719 fold_builtin_classify_type (tree arg)
6720 {
6721 if (arg == 0)
6722 return build_int_cst (NULL_TREE, no_type_class);
6723
6724 return build_int_cst (NULL_TREE, type_to_class (TREE_TYPE (arg)));
6725 }
6726
6727 /* Fold a call to __builtin_strlen with argument ARG. */
6728
6729 static tree
6730 fold_builtin_strlen (location_t loc, tree type, tree arg)
6731 {
6732 if (!validate_arg (arg, POINTER_TYPE))
6733 return NULL_TREE;
6734 else
6735 {
6736 tree len = c_strlen (arg, 0);
6737
6738 if (len)
6739 return fold_convert_loc (loc, type, len);
6740
6741 return NULL_TREE;
6742 }
6743 }
6744
6745 /* Fold a call to __builtin_inf or __builtin_huge_val. */
6746
6747 static tree
6748 fold_builtin_inf (location_t loc, tree type, int warn)
6749 {
6750 REAL_VALUE_TYPE real;
6751
6752 /* __builtin_inff is intended to be usable to define INFINITY on all
6753 targets. If an infinity is not available, INFINITY expands "to a
6754 positive constant of type float that overflows at translation
6755 time", footnote "In this case, using INFINITY will violate the
6756 constraint in 6.4.4 and thus require a diagnostic." (C99 7.12#4).
6757 Thus we pedwarn to ensure this constraint violation is
6758 diagnosed. */
6759 if (!MODE_HAS_INFINITIES (TYPE_MODE (type)) && warn)
6760 pedwarn (loc, 0, "target format does not support infinity");
6761
6762 real_inf (&real);
6763 return build_real (type, real);
6764 }
6765
6766 /* Fold a call to __builtin_nan or __builtin_nans with argument ARG. */
6767
6768 static tree
6769 fold_builtin_nan (tree arg, tree type, int quiet)
6770 {
6771 REAL_VALUE_TYPE real;
6772 const char *str;
6773
6774 if (!validate_arg (arg, POINTER_TYPE))
6775 return NULL_TREE;
6776 str = c_getstr (arg);
6777 if (!str)
6778 return NULL_TREE;
6779
6780 if (!real_nan (&real, str, quiet, TYPE_MODE (type)))
6781 return NULL_TREE;
6782
6783 return build_real (type, real);
6784 }
6785
6786 /* Return true if the floating point expression T has an integer value.
6787 We also allow +Inf, -Inf and NaN to be considered integer values. */
6788
6789 static bool
6790 integer_valued_real_p (tree t)
6791 {
6792 switch (TREE_CODE (t))
6793 {
6794 case FLOAT_EXPR:
6795 return true;
6796
6797 case ABS_EXPR:
6798 case SAVE_EXPR:
6799 return integer_valued_real_p (TREE_OPERAND (t, 0));
6800
6801 case COMPOUND_EXPR:
6802 case MODIFY_EXPR:
6803 case BIND_EXPR:
6804 return integer_valued_real_p (TREE_OPERAND (t, 1));
6805
6806 case PLUS_EXPR:
6807 case MINUS_EXPR:
6808 case MULT_EXPR:
6809 case MIN_EXPR:
6810 case MAX_EXPR:
6811 return integer_valued_real_p (TREE_OPERAND (t, 0))
6812 && integer_valued_real_p (TREE_OPERAND (t, 1));
6813
6814 case COND_EXPR:
6815 return integer_valued_real_p (TREE_OPERAND (t, 1))
6816 && integer_valued_real_p (TREE_OPERAND (t, 2));
6817
6818 case REAL_CST:
6819 return real_isinteger (TREE_REAL_CST_PTR (t), TYPE_MODE (TREE_TYPE (t)));
6820
6821 case NOP_EXPR:
6822 {
6823 tree type = TREE_TYPE (TREE_OPERAND (t, 0));
6824 if (TREE_CODE (type) == INTEGER_TYPE)
6825 return true;
6826 if (TREE_CODE (type) == REAL_TYPE)
6827 return integer_valued_real_p (TREE_OPERAND (t, 0));
6828 break;
6829 }
6830
6831 case CALL_EXPR:
6832 switch (builtin_mathfn_code (t))
6833 {
6834 CASE_FLT_FN (BUILT_IN_CEIL):
6835 CASE_FLT_FN (BUILT_IN_FLOOR):
6836 CASE_FLT_FN (BUILT_IN_NEARBYINT):
6837 CASE_FLT_FN (BUILT_IN_RINT):
6838 CASE_FLT_FN (BUILT_IN_ROUND):
6839 CASE_FLT_FN (BUILT_IN_TRUNC):
6840 return true;
6841
6842 CASE_FLT_FN (BUILT_IN_FMIN):
6843 CASE_FLT_FN (BUILT_IN_FMAX):
6844 return integer_valued_real_p (CALL_EXPR_ARG (t, 0))
6845 && integer_valued_real_p (CALL_EXPR_ARG (t, 1));
6846
6847 default:
6848 break;
6849 }
6850 break;
6851
6852 default:
6853 break;
6854 }
6855 return false;
6856 }
6857
6858 /* FNDECL is assumed to be a builtin where truncation can be propagated
6859 across (for instance floor((double)f) == (double)floorf (f).
6860 Do the transformation for a call with argument ARG. */
6861
6862 static tree
6863 fold_trunc_transparent_mathfn (location_t loc, tree fndecl, tree arg)
6864 {
6865 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
6866
6867 if (!validate_arg (arg, REAL_TYPE))
6868 return NULL_TREE;
6869
6870 /* Integer rounding functions are idempotent. */
6871 if (fcode == builtin_mathfn_code (arg))
6872 return arg;
6873
6874 /* If argument is already integer valued, and we don't need to worry
6875 about setting errno, there's no need to perform rounding. */
6876 if (! flag_errno_math && integer_valued_real_p (arg))
6877 return arg;
6878
6879 if (optimize)
6880 {
6881 tree arg0 = strip_float_extensions (arg);
6882 tree ftype = TREE_TYPE (TREE_TYPE (fndecl));
6883 tree newtype = TREE_TYPE (arg0);
6884 tree decl;
6885
6886 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
6887 && (decl = mathfn_built_in (newtype, fcode)))
6888 return fold_convert_loc (loc, ftype,
6889 build_call_expr_loc (loc, decl, 1,
6890 fold_convert_loc (loc,
6891 newtype,
6892 arg0)));
6893 }
6894 return NULL_TREE;
6895 }
6896
6897 /* FNDECL is assumed to be builtin which can narrow the FP type of
6898 the argument, for instance lround((double)f) -> lroundf (f).
6899 Do the transformation for a call with argument ARG. */
6900
6901 static tree
6902 fold_fixed_mathfn (location_t loc, tree fndecl, tree arg)
6903 {
6904 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
6905
6906 if (!validate_arg (arg, REAL_TYPE))
6907 return NULL_TREE;
6908
6909 /* If argument is already integer valued, and we don't need to worry
6910 about setting errno, there's no need to perform rounding. */
6911 if (! flag_errno_math && integer_valued_real_p (arg))
6912 return fold_build1_loc (loc, FIX_TRUNC_EXPR,
6913 TREE_TYPE (TREE_TYPE (fndecl)), arg);
6914
6915 if (optimize)
6916 {
6917 tree ftype = TREE_TYPE (arg);
6918 tree arg0 = strip_float_extensions (arg);
6919 tree newtype = TREE_TYPE (arg0);
6920 tree decl;
6921
6922 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
6923 && (decl = mathfn_built_in (newtype, fcode)))
6924 return build_call_expr_loc (loc, decl, 1,
6925 fold_convert_loc (loc, newtype, arg0));
6926 }
6927
6928 /* Canonicalize llround (x) to lround (x) on LP64 targets where
6929 sizeof (long long) == sizeof (long). */
6930 if (TYPE_PRECISION (long_long_integer_type_node)
6931 == TYPE_PRECISION (long_integer_type_node))
6932 {
6933 tree newfn = NULL_TREE;
6934 switch (fcode)
6935 {
6936 CASE_FLT_FN (BUILT_IN_LLCEIL):
6937 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LCEIL);
6938 break;
6939
6940 CASE_FLT_FN (BUILT_IN_LLFLOOR):
6941 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LFLOOR);
6942 break;
6943
6944 CASE_FLT_FN (BUILT_IN_LLROUND):
6945 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LROUND);
6946 break;
6947
6948 CASE_FLT_FN (BUILT_IN_LLRINT):
6949 newfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_LRINT);
6950 break;
6951
6952 default:
6953 break;
6954 }
6955
6956 if (newfn)
6957 {
6958 tree newcall = build_call_expr_loc (loc, newfn, 1, arg);
6959 return fold_convert_loc (loc,
6960 TREE_TYPE (TREE_TYPE (fndecl)), newcall);
6961 }
6962 }
6963
6964 return NULL_TREE;
6965 }
6966
6967 /* Fold call to builtin cabs, cabsf or cabsl with argument ARG. TYPE is the
6968 return type. Return NULL_TREE if no simplification can be made. */
6969
6970 static tree
6971 fold_builtin_cabs (location_t loc, tree arg, tree type, tree fndecl)
6972 {
6973 tree res;
6974
6975 if (!validate_arg (arg, COMPLEX_TYPE)
6976 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
6977 return NULL_TREE;
6978
6979 /* Calculate the result when the argument is a constant. */
6980 if (TREE_CODE (arg) == COMPLEX_CST
6981 && (res = do_mpfr_arg2 (TREE_REALPART (arg), TREE_IMAGPART (arg),
6982 type, mpfr_hypot)))
6983 return res;
6984
6985 if (TREE_CODE (arg) == COMPLEX_EXPR)
6986 {
6987 tree real = TREE_OPERAND (arg, 0);
6988 tree imag = TREE_OPERAND (arg, 1);
6989
6990 /* If either part is zero, cabs is fabs of the other. */
6991 if (real_zerop (real))
6992 return fold_build1_loc (loc, ABS_EXPR, type, imag);
6993 if (real_zerop (imag))
6994 return fold_build1_loc (loc, ABS_EXPR, type, real);
6995
6996 /* cabs(x+xi) -> fabs(x)*sqrt(2). */
6997 if (flag_unsafe_math_optimizations
6998 && operand_equal_p (real, imag, OEP_PURE_SAME))
6999 {
7000 const REAL_VALUE_TYPE sqrt2_trunc
7001 = real_value_truncate (TYPE_MODE (type), dconst_sqrt2 ());
7002 STRIP_NOPS (real);
7003 return fold_build2_loc (loc, MULT_EXPR, type,
7004 fold_build1_loc (loc, ABS_EXPR, type, real),
7005 build_real (type, sqrt2_trunc));
7006 }
7007 }
7008
7009 /* Optimize cabs(-z) and cabs(conj(z)) as cabs(z). */
7010 if (TREE_CODE (arg) == NEGATE_EXPR
7011 || TREE_CODE (arg) == CONJ_EXPR)
7012 return build_call_expr_loc (loc, fndecl, 1, TREE_OPERAND (arg, 0));
7013
7014 /* Don't do this when optimizing for size. */
7015 if (flag_unsafe_math_optimizations
7016 && optimize && optimize_function_for_speed_p (cfun))
7017 {
7018 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
7019
7020 if (sqrtfn != NULL_TREE)
7021 {
7022 tree rpart, ipart, result;
7023
7024 arg = builtin_save_expr (arg);
7025
7026 rpart = fold_build1_loc (loc, REALPART_EXPR, type, arg);
7027 ipart = fold_build1_loc (loc, IMAGPART_EXPR, type, arg);
7028
7029 rpart = builtin_save_expr (rpart);
7030 ipart = builtin_save_expr (ipart);
7031
7032 result = fold_build2_loc (loc, PLUS_EXPR, type,
7033 fold_build2_loc (loc, MULT_EXPR, type,
7034 rpart, rpart),
7035 fold_build2_loc (loc, MULT_EXPR, type,
7036 ipart, ipart));
7037
7038 return build_call_expr_loc (loc, sqrtfn, 1, result);
7039 }
7040 }
7041
7042 return NULL_TREE;
7043 }
7044
7045 /* Build a complex (inf +- 0i) for the result of cproj. TYPE is the
7046 complex tree type of the result. If NEG is true, the imaginary
7047 zero is negative. */
7048
7049 static tree
7050 build_complex_cproj (tree type, bool neg)
7051 {
7052 REAL_VALUE_TYPE rinf, rzero = dconst0;
7053
7054 real_inf (&rinf);
7055 rzero.sign = neg;
7056 return build_complex (type, build_real (TREE_TYPE (type), rinf),
7057 build_real (TREE_TYPE (type), rzero));
7058 }
7059
7060 /* Fold call to builtin cproj, cprojf or cprojl with argument ARG. TYPE is the
7061 return type. Return NULL_TREE if no simplification can be made. */
7062
7063 static tree
7064 fold_builtin_cproj (location_t loc, tree arg, tree type)
7065 {
7066 if (!validate_arg (arg, COMPLEX_TYPE)
7067 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
7068 return NULL_TREE;
7069
7070 /* If there are no infinities, return arg. */
7071 if (! HONOR_INFINITIES (TYPE_MODE (TREE_TYPE (type))))
7072 return non_lvalue_loc (loc, arg);
7073
7074 /* Calculate the result when the argument is a constant. */
7075 if (TREE_CODE (arg) == COMPLEX_CST)
7076 {
7077 const REAL_VALUE_TYPE *real = TREE_REAL_CST_PTR (TREE_REALPART (arg));
7078 const REAL_VALUE_TYPE *imag = TREE_REAL_CST_PTR (TREE_IMAGPART (arg));
7079
7080 if (real_isinf (real) || real_isinf (imag))
7081 return build_complex_cproj (type, imag->sign);
7082 else
7083 return arg;
7084 }
7085 else if (TREE_CODE (arg) == COMPLEX_EXPR)
7086 {
7087 tree real = TREE_OPERAND (arg, 0);
7088 tree imag = TREE_OPERAND (arg, 1);
7089
7090 STRIP_NOPS (real);
7091 STRIP_NOPS (imag);
7092
7093 /* If the real part is inf and the imag part is known to be
7094 nonnegative, return (inf + 0i). Remember side-effects are
7095 possible in the imag part. */
7096 if (TREE_CODE (real) == REAL_CST
7097 && real_isinf (TREE_REAL_CST_PTR (real))
7098 && tree_expr_nonnegative_p (imag))
7099 return omit_one_operand_loc (loc, type,
7100 build_complex_cproj (type, false),
7101 arg);
7102
7103 /* If the imag part is inf, return (inf+I*copysign(0,imag)).
7104 Remember side-effects are possible in the real part. */
7105 if (TREE_CODE (imag) == REAL_CST
7106 && real_isinf (TREE_REAL_CST_PTR (imag)))
7107 return
7108 omit_one_operand_loc (loc, type,
7109 build_complex_cproj (type, TREE_REAL_CST_PTR
7110 (imag)->sign), arg);
7111 }
7112
7113 return NULL_TREE;
7114 }
7115
7116 /* Fold a builtin function call to sqrt, sqrtf, or sqrtl with argument ARG.
7117 Return NULL_TREE if no simplification can be made. */
7118
7119 static tree
7120 fold_builtin_sqrt (location_t loc, tree arg, tree type)
7121 {
7122
7123 enum built_in_function fcode;
7124 tree res;
7125
7126 if (!validate_arg (arg, REAL_TYPE))
7127 return NULL_TREE;
7128
7129 /* Calculate the result when the argument is a constant. */
7130 if ((res = do_mpfr_arg1 (arg, type, mpfr_sqrt, &dconst0, NULL, true)))
7131 return res;
7132
7133 /* Optimize sqrt(expN(x)) = expN(x*0.5). */
7134 fcode = builtin_mathfn_code (arg);
7135 if (flag_unsafe_math_optimizations && BUILTIN_EXPONENT_P (fcode))
7136 {
7137 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7138 arg = fold_build2_loc (loc, MULT_EXPR, type,
7139 CALL_EXPR_ARG (arg, 0),
7140 build_real (type, dconsthalf));
7141 return build_call_expr_loc (loc, expfn, 1, arg);
7142 }
7143
7144 /* Optimize sqrt(Nroot(x)) -> pow(x,1/(2*N)). */
7145 if (flag_unsafe_math_optimizations && BUILTIN_ROOT_P (fcode))
7146 {
7147 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7148
7149 if (powfn)
7150 {
7151 tree arg0 = CALL_EXPR_ARG (arg, 0);
7152 tree tree_root;
7153 /* The inner root was either sqrt or cbrt. */
7154 /* This was a conditional expression but it triggered a bug
7155 in Sun C 5.5. */
7156 REAL_VALUE_TYPE dconstroot;
7157 if (BUILTIN_SQRT_P (fcode))
7158 dconstroot = dconsthalf;
7159 else
7160 dconstroot = dconst_third ();
7161
7162 /* Adjust for the outer root. */
7163 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7164 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7165 tree_root = build_real (type, dconstroot);
7166 return build_call_expr_loc (loc, powfn, 2, arg0, tree_root);
7167 }
7168 }
7169
7170 /* Optimize sqrt(pow(x,y)) = pow(|x|,y*0.5). */
7171 if (flag_unsafe_math_optimizations
7172 && (fcode == BUILT_IN_POW
7173 || fcode == BUILT_IN_POWF
7174 || fcode == BUILT_IN_POWL))
7175 {
7176 tree powfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7177 tree arg0 = CALL_EXPR_ARG (arg, 0);
7178 tree arg1 = CALL_EXPR_ARG (arg, 1);
7179 tree narg1;
7180 if (!tree_expr_nonnegative_p (arg0))
7181 arg0 = build1 (ABS_EXPR, type, arg0);
7182 narg1 = fold_build2_loc (loc, MULT_EXPR, type, arg1,
7183 build_real (type, dconsthalf));
7184 return build_call_expr_loc (loc, powfn, 2, arg0, narg1);
7185 }
7186
7187 return NULL_TREE;
7188 }
7189
7190 /* Fold a builtin function call to cbrt, cbrtf, or cbrtl with argument ARG.
7191 Return NULL_TREE if no simplification can be made. */
7192
7193 static tree
7194 fold_builtin_cbrt (location_t loc, tree arg, tree type)
7195 {
7196 const enum built_in_function fcode = builtin_mathfn_code (arg);
7197 tree res;
7198
7199 if (!validate_arg (arg, REAL_TYPE))
7200 return NULL_TREE;
7201
7202 /* Calculate the result when the argument is a constant. */
7203 if ((res = do_mpfr_arg1 (arg, type, mpfr_cbrt, NULL, NULL, 0)))
7204 return res;
7205
7206 if (flag_unsafe_math_optimizations)
7207 {
7208 /* Optimize cbrt(expN(x)) -> expN(x/3). */
7209 if (BUILTIN_EXPONENT_P (fcode))
7210 {
7211 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7212 const REAL_VALUE_TYPE third_trunc =
7213 real_value_truncate (TYPE_MODE (type), dconst_third ());
7214 arg = fold_build2_loc (loc, MULT_EXPR, type,
7215 CALL_EXPR_ARG (arg, 0),
7216 build_real (type, third_trunc));
7217 return build_call_expr_loc (loc, expfn, 1, arg);
7218 }
7219
7220 /* Optimize cbrt(sqrt(x)) -> pow(x,1/6). */
7221 if (BUILTIN_SQRT_P (fcode))
7222 {
7223 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7224
7225 if (powfn)
7226 {
7227 tree arg0 = CALL_EXPR_ARG (arg, 0);
7228 tree tree_root;
7229 REAL_VALUE_TYPE dconstroot = dconst_third ();
7230
7231 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7232 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7233 tree_root = build_real (type, dconstroot);
7234 return build_call_expr_loc (loc, powfn, 2, arg0, tree_root);
7235 }
7236 }
7237
7238 /* Optimize cbrt(cbrt(x)) -> pow(x,1/9) iff x is nonnegative. */
7239 if (BUILTIN_CBRT_P (fcode))
7240 {
7241 tree arg0 = CALL_EXPR_ARG (arg, 0);
7242 if (tree_expr_nonnegative_p (arg0))
7243 {
7244 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7245
7246 if (powfn)
7247 {
7248 tree tree_root;
7249 REAL_VALUE_TYPE dconstroot;
7250
7251 real_arithmetic (&dconstroot, MULT_EXPR,
7252 dconst_third_ptr (), dconst_third_ptr ());
7253 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7254 tree_root = build_real (type, dconstroot);
7255 return build_call_expr_loc (loc, powfn, 2, arg0, tree_root);
7256 }
7257 }
7258 }
7259
7260 /* Optimize cbrt(pow(x,y)) -> pow(x,y/3) iff x is nonnegative. */
7261 if (fcode == BUILT_IN_POW
7262 || fcode == BUILT_IN_POWF
7263 || fcode == BUILT_IN_POWL)
7264 {
7265 tree arg00 = CALL_EXPR_ARG (arg, 0);
7266 tree arg01 = CALL_EXPR_ARG (arg, 1);
7267 if (tree_expr_nonnegative_p (arg00))
7268 {
7269 tree powfn = TREE_OPERAND (CALL_EXPR_FN (arg), 0);
7270 const REAL_VALUE_TYPE dconstroot
7271 = real_value_truncate (TYPE_MODE (type), dconst_third ());
7272 tree narg01 = fold_build2_loc (loc, MULT_EXPR, type, arg01,
7273 build_real (type, dconstroot));
7274 return build_call_expr_loc (loc, powfn, 2, arg00, narg01);
7275 }
7276 }
7277 }
7278 return NULL_TREE;
7279 }
7280
7281 /* Fold function call to builtin cos, cosf, or cosl with argument ARG.
7282 TYPE is the type of the return value. Return NULL_TREE if no
7283 simplification can be made. */
7284
7285 static tree
7286 fold_builtin_cos (location_t loc,
7287 tree arg, tree type, tree fndecl)
7288 {
7289 tree res, narg;
7290
7291 if (!validate_arg (arg, REAL_TYPE))
7292 return NULL_TREE;
7293
7294 /* Calculate the result when the argument is a constant. */
7295 if ((res = do_mpfr_arg1 (arg, type, mpfr_cos, NULL, NULL, 0)))
7296 return res;
7297
7298 /* Optimize cos(-x) into cos (x). */
7299 if ((narg = fold_strip_sign_ops (arg)))
7300 return build_call_expr_loc (loc, fndecl, 1, narg);
7301
7302 return NULL_TREE;
7303 }
7304
7305 /* Fold function call to builtin cosh, coshf, or coshl with argument ARG.
7306 Return NULL_TREE if no simplification can be made. */
7307
7308 static tree
7309 fold_builtin_cosh (location_t loc, tree arg, tree type, tree fndecl)
7310 {
7311 if (validate_arg (arg, REAL_TYPE))
7312 {
7313 tree res, narg;
7314
7315 /* Calculate the result when the argument is a constant. */
7316 if ((res = do_mpfr_arg1 (arg, type, mpfr_cosh, NULL, NULL, 0)))
7317 return res;
7318
7319 /* Optimize cosh(-x) into cosh (x). */
7320 if ((narg = fold_strip_sign_ops (arg)))
7321 return build_call_expr_loc (loc, fndecl, 1, narg);
7322 }
7323
7324 return NULL_TREE;
7325 }
7326
7327 /* Fold function call to builtin ccos (or ccosh if HYPER is TRUE) with
7328 argument ARG. TYPE is the type of the return value. Return
7329 NULL_TREE if no simplification can be made. */
7330
7331 static tree
7332 fold_builtin_ccos (location_t loc, tree arg, tree type, tree fndecl,
7333 bool hyper)
7334 {
7335 if (validate_arg (arg, COMPLEX_TYPE)
7336 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) == REAL_TYPE)
7337 {
7338 tree tmp;
7339
7340 /* Calculate the result when the argument is a constant. */
7341 if ((tmp = do_mpc_arg1 (arg, type, (hyper ? mpc_cosh : mpc_cos))))
7342 return tmp;
7343
7344 /* Optimize fn(-x) into fn(x). */
7345 if ((tmp = fold_strip_sign_ops (arg)))
7346 return build_call_expr_loc (loc, fndecl, 1, tmp);
7347 }
7348
7349 return NULL_TREE;
7350 }
7351
7352 /* Fold function call to builtin tan, tanf, or tanl with argument ARG.
7353 Return NULL_TREE if no simplification can be made. */
7354
7355 static tree
7356 fold_builtin_tan (tree arg, tree type)
7357 {
7358 enum built_in_function fcode;
7359 tree res;
7360
7361 if (!validate_arg (arg, REAL_TYPE))
7362 return NULL_TREE;
7363
7364 /* Calculate the result when the argument is a constant. */
7365 if ((res = do_mpfr_arg1 (arg, type, mpfr_tan, NULL, NULL, 0)))
7366 return res;
7367
7368 /* Optimize tan(atan(x)) = x. */
7369 fcode = builtin_mathfn_code (arg);
7370 if (flag_unsafe_math_optimizations
7371 && (fcode == BUILT_IN_ATAN
7372 || fcode == BUILT_IN_ATANF
7373 || fcode == BUILT_IN_ATANL))
7374 return CALL_EXPR_ARG (arg, 0);
7375
7376 return NULL_TREE;
7377 }
7378
7379 /* Fold function call to builtin sincos, sincosf, or sincosl. Return
7380 NULL_TREE if no simplification can be made. */
7381
7382 static tree
7383 fold_builtin_sincos (location_t loc,
7384 tree arg0, tree arg1, tree arg2)
7385 {
7386 tree type;
7387 tree res, fn, call;
7388
7389 if (!validate_arg (arg0, REAL_TYPE)
7390 || !validate_arg (arg1, POINTER_TYPE)
7391 || !validate_arg (arg2, POINTER_TYPE))
7392 return NULL_TREE;
7393
7394 type = TREE_TYPE (arg0);
7395
7396 /* Calculate the result when the argument is a constant. */
7397 if ((res = do_mpfr_sincos (arg0, arg1, arg2)))
7398 return res;
7399
7400 /* Canonicalize sincos to cexpi. */
7401 if (!TARGET_C99_FUNCTIONS)
7402 return NULL_TREE;
7403 fn = mathfn_built_in (type, BUILT_IN_CEXPI);
7404 if (!fn)
7405 return NULL_TREE;
7406
7407 call = build_call_expr_loc (loc, fn, 1, arg0);
7408 call = builtin_save_expr (call);
7409
7410 return build2 (COMPOUND_EXPR, void_type_node,
7411 build2 (MODIFY_EXPR, void_type_node,
7412 build_fold_indirect_ref_loc (loc, arg1),
7413 build1 (IMAGPART_EXPR, type, call)),
7414 build2 (MODIFY_EXPR, void_type_node,
7415 build_fold_indirect_ref_loc (loc, arg2),
7416 build1 (REALPART_EXPR, type, call)));
7417 }
7418
7419 /* Fold function call to builtin cexp, cexpf, or cexpl. Return
7420 NULL_TREE if no simplification can be made. */
7421
7422 static tree
7423 fold_builtin_cexp (location_t loc, tree arg0, tree type)
7424 {
7425 tree rtype;
7426 tree realp, imagp, ifn;
7427 tree res;
7428
7429 if (!validate_arg (arg0, COMPLEX_TYPE)
7430 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) != REAL_TYPE)
7431 return NULL_TREE;
7432
7433 /* Calculate the result when the argument is a constant. */
7434 if ((res = do_mpc_arg1 (arg0, type, mpc_exp)))
7435 return res;
7436
7437 rtype = TREE_TYPE (TREE_TYPE (arg0));
7438
7439 /* In case we can figure out the real part of arg0 and it is constant zero
7440 fold to cexpi. */
7441 if (!TARGET_C99_FUNCTIONS)
7442 return NULL_TREE;
7443 ifn = mathfn_built_in (rtype, BUILT_IN_CEXPI);
7444 if (!ifn)
7445 return NULL_TREE;
7446
7447 if ((realp = fold_unary_loc (loc, REALPART_EXPR, rtype, arg0))
7448 && real_zerop (realp))
7449 {
7450 tree narg = fold_build1_loc (loc, IMAGPART_EXPR, rtype, arg0);
7451 return build_call_expr_loc (loc, ifn, 1, narg);
7452 }
7453
7454 /* In case we can easily decompose real and imaginary parts split cexp
7455 to exp (r) * cexpi (i). */
7456 if (flag_unsafe_math_optimizations
7457 && realp)
7458 {
7459 tree rfn, rcall, icall;
7460
7461 rfn = mathfn_built_in (rtype, BUILT_IN_EXP);
7462 if (!rfn)
7463 return NULL_TREE;
7464
7465 imagp = fold_unary_loc (loc, IMAGPART_EXPR, rtype, arg0);
7466 if (!imagp)
7467 return NULL_TREE;
7468
7469 icall = build_call_expr_loc (loc, ifn, 1, imagp);
7470 icall = builtin_save_expr (icall);
7471 rcall = build_call_expr_loc (loc, rfn, 1, realp);
7472 rcall = builtin_save_expr (rcall);
7473 return fold_build2_loc (loc, COMPLEX_EXPR, type,
7474 fold_build2_loc (loc, MULT_EXPR, rtype,
7475 rcall,
7476 fold_build1_loc (loc, REALPART_EXPR,
7477 rtype, icall)),
7478 fold_build2_loc (loc, MULT_EXPR, rtype,
7479 rcall,
7480 fold_build1_loc (loc, IMAGPART_EXPR,
7481 rtype, icall)));
7482 }
7483
7484 return NULL_TREE;
7485 }
7486
7487 /* Fold function call to builtin trunc, truncf or truncl with argument ARG.
7488 Return NULL_TREE if no simplification can be made. */
7489
7490 static tree
7491 fold_builtin_trunc (location_t loc, tree fndecl, tree arg)
7492 {
7493 if (!validate_arg (arg, REAL_TYPE))
7494 return NULL_TREE;
7495
7496 /* Optimize trunc of constant value. */
7497 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7498 {
7499 REAL_VALUE_TYPE r, x;
7500 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7501
7502 x = TREE_REAL_CST (arg);
7503 real_trunc (&r, TYPE_MODE (type), &x);
7504 return build_real (type, r);
7505 }
7506
7507 return fold_trunc_transparent_mathfn (loc, fndecl, arg);
7508 }
7509
7510 /* Fold function call to builtin floor, floorf or floorl with argument ARG.
7511 Return NULL_TREE if no simplification can be made. */
7512
7513 static tree
7514 fold_builtin_floor (location_t loc, tree fndecl, tree arg)
7515 {
7516 if (!validate_arg (arg, REAL_TYPE))
7517 return NULL_TREE;
7518
7519 /* Optimize floor of constant value. */
7520 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7521 {
7522 REAL_VALUE_TYPE x;
7523
7524 x = TREE_REAL_CST (arg);
7525 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7526 {
7527 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7528 REAL_VALUE_TYPE r;
7529
7530 real_floor (&r, TYPE_MODE (type), &x);
7531 return build_real (type, r);
7532 }
7533 }
7534
7535 /* Fold floor (x) where x is nonnegative to trunc (x). */
7536 if (tree_expr_nonnegative_p (arg))
7537 {
7538 tree truncfn = mathfn_built_in (TREE_TYPE (arg), BUILT_IN_TRUNC);
7539 if (truncfn)
7540 return build_call_expr_loc (loc, truncfn, 1, arg);
7541 }
7542
7543 return fold_trunc_transparent_mathfn (loc, fndecl, arg);
7544 }
7545
7546 /* Fold function call to builtin ceil, ceilf or ceill with argument ARG.
7547 Return NULL_TREE if no simplification can be made. */
7548
7549 static tree
7550 fold_builtin_ceil (location_t loc, tree fndecl, tree arg)
7551 {
7552 if (!validate_arg (arg, REAL_TYPE))
7553 return NULL_TREE;
7554
7555 /* Optimize ceil of constant value. */
7556 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7557 {
7558 REAL_VALUE_TYPE x;
7559
7560 x = TREE_REAL_CST (arg);
7561 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7562 {
7563 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7564 REAL_VALUE_TYPE r;
7565
7566 real_ceil (&r, TYPE_MODE (type), &x);
7567 return build_real (type, r);
7568 }
7569 }
7570
7571 return fold_trunc_transparent_mathfn (loc, fndecl, arg);
7572 }
7573
7574 /* Fold function call to builtin round, roundf or roundl with argument ARG.
7575 Return NULL_TREE if no simplification can be made. */
7576
7577 static tree
7578 fold_builtin_round (location_t loc, tree fndecl, tree arg)
7579 {
7580 if (!validate_arg (arg, REAL_TYPE))
7581 return NULL_TREE;
7582
7583 /* Optimize round of constant value. */
7584 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7585 {
7586 REAL_VALUE_TYPE x;
7587
7588 x = TREE_REAL_CST (arg);
7589 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
7590 {
7591 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7592 REAL_VALUE_TYPE r;
7593
7594 real_round (&r, TYPE_MODE (type), &x);
7595 return build_real (type, r);
7596 }
7597 }
7598
7599 return fold_trunc_transparent_mathfn (loc, fndecl, arg);
7600 }
7601
7602 /* Fold function call to builtin lround, lroundf or lroundl (or the
7603 corresponding long long versions) and other rounding functions. ARG
7604 is the argument to the call. Return NULL_TREE if no simplification
7605 can be made. */
7606
7607 static tree
7608 fold_builtin_int_roundingfn (location_t loc, tree fndecl, tree arg)
7609 {
7610 if (!validate_arg (arg, REAL_TYPE))
7611 return NULL_TREE;
7612
7613 /* Optimize lround of constant value. */
7614 if (TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
7615 {
7616 const REAL_VALUE_TYPE x = TREE_REAL_CST (arg);
7617
7618 if (real_isfinite (&x))
7619 {
7620 tree itype = TREE_TYPE (TREE_TYPE (fndecl));
7621 tree ftype = TREE_TYPE (arg);
7622 unsigned HOST_WIDE_INT lo2;
7623 HOST_WIDE_INT hi, lo;
7624 REAL_VALUE_TYPE r;
7625
7626 switch (DECL_FUNCTION_CODE (fndecl))
7627 {
7628 CASE_FLT_FN (BUILT_IN_LFLOOR):
7629 CASE_FLT_FN (BUILT_IN_LLFLOOR):
7630 real_floor (&r, TYPE_MODE (ftype), &x);
7631 break;
7632
7633 CASE_FLT_FN (BUILT_IN_LCEIL):
7634 CASE_FLT_FN (BUILT_IN_LLCEIL):
7635 real_ceil (&r, TYPE_MODE (ftype), &x);
7636 break;
7637
7638 CASE_FLT_FN (BUILT_IN_LROUND):
7639 CASE_FLT_FN (BUILT_IN_LLROUND):
7640 real_round (&r, TYPE_MODE (ftype), &x);
7641 break;
7642
7643 default:
7644 gcc_unreachable ();
7645 }
7646
7647 REAL_VALUE_TO_INT (&lo, &hi, r);
7648 if (!fit_double_type (lo, hi, &lo2, &hi, itype))
7649 return build_int_cst_wide (itype, lo2, hi);
7650 }
7651 }
7652
7653 switch (DECL_FUNCTION_CODE (fndecl))
7654 {
7655 CASE_FLT_FN (BUILT_IN_LFLOOR):
7656 CASE_FLT_FN (BUILT_IN_LLFLOOR):
7657 /* Fold lfloor (x) where x is nonnegative to FIX_TRUNC (x). */
7658 if (tree_expr_nonnegative_p (arg))
7659 return fold_build1_loc (loc, FIX_TRUNC_EXPR,
7660 TREE_TYPE (TREE_TYPE (fndecl)), arg);
7661 break;
7662 default:;
7663 }
7664
7665 return fold_fixed_mathfn (loc, fndecl, arg);
7666 }
7667
7668 /* Fold function call to builtin ffs, clz, ctz, popcount and parity
7669 and their long and long long variants (i.e. ffsl and ffsll). ARG is
7670 the argument to the call. Return NULL_TREE if no simplification can
7671 be made. */
7672
7673 static tree
7674 fold_builtin_bitop (tree fndecl, tree arg)
7675 {
7676 if (!validate_arg (arg, INTEGER_TYPE))
7677 return NULL_TREE;
7678
7679 /* Optimize for constant argument. */
7680 if (TREE_CODE (arg) == INTEGER_CST && !TREE_OVERFLOW (arg))
7681 {
7682 HOST_WIDE_INT hi, width, result;
7683 unsigned HOST_WIDE_INT lo;
7684 tree type;
7685
7686 type = TREE_TYPE (arg);
7687 width = TYPE_PRECISION (type);
7688 lo = TREE_INT_CST_LOW (arg);
7689
7690 /* Clear all the bits that are beyond the type's precision. */
7691 if (width > HOST_BITS_PER_WIDE_INT)
7692 {
7693 hi = TREE_INT_CST_HIGH (arg);
7694 if (width < 2 * HOST_BITS_PER_WIDE_INT)
7695 hi &= ~((HOST_WIDE_INT) (-1) >> (width - HOST_BITS_PER_WIDE_INT));
7696 }
7697 else
7698 {
7699 hi = 0;
7700 if (width < HOST_BITS_PER_WIDE_INT)
7701 lo &= ~((unsigned HOST_WIDE_INT) (-1) << width);
7702 }
7703
7704 switch (DECL_FUNCTION_CODE (fndecl))
7705 {
7706 CASE_INT_FN (BUILT_IN_FFS):
7707 if (lo != 0)
7708 result = exact_log2 (lo & -lo) + 1;
7709 else if (hi != 0)
7710 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi) + 1;
7711 else
7712 result = 0;
7713 break;
7714
7715 CASE_INT_FN (BUILT_IN_CLZ):
7716 if (hi != 0)
7717 result = width - floor_log2 (hi) - 1 - HOST_BITS_PER_WIDE_INT;
7718 else if (lo != 0)
7719 result = width - floor_log2 (lo) - 1;
7720 else if (! CLZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
7721 result = width;
7722 break;
7723
7724 CASE_INT_FN (BUILT_IN_CTZ):
7725 if (lo != 0)
7726 result = exact_log2 (lo & -lo);
7727 else if (hi != 0)
7728 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi);
7729 else if (! CTZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
7730 result = width;
7731 break;
7732
7733 CASE_INT_FN (BUILT_IN_POPCOUNT):
7734 result = 0;
7735 while (lo)
7736 result++, lo &= lo - 1;
7737 while (hi)
7738 result++, hi &= hi - 1;
7739 break;
7740
7741 CASE_INT_FN (BUILT_IN_PARITY):
7742 result = 0;
7743 while (lo)
7744 result++, lo &= lo - 1;
7745 while (hi)
7746 result++, hi &= hi - 1;
7747 result &= 1;
7748 break;
7749
7750 default:
7751 gcc_unreachable ();
7752 }
7753
7754 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), result);
7755 }
7756
7757 return NULL_TREE;
7758 }
7759
7760 /* Fold function call to builtin_bswap and the long and long long
7761 variants. Return NULL_TREE if no simplification can be made. */
7762 static tree
7763 fold_builtin_bswap (tree fndecl, tree arg)
7764 {
7765 if (! validate_arg (arg, INTEGER_TYPE))
7766 return NULL_TREE;
7767
7768 /* Optimize constant value. */
7769 if (TREE_CODE (arg) == INTEGER_CST && !TREE_OVERFLOW (arg))
7770 {
7771 HOST_WIDE_INT hi, width, r_hi = 0;
7772 unsigned HOST_WIDE_INT lo, r_lo = 0;
7773 tree type;
7774
7775 type = TREE_TYPE (arg);
7776 width = TYPE_PRECISION (type);
7777 lo = TREE_INT_CST_LOW (arg);
7778 hi = TREE_INT_CST_HIGH (arg);
7779
7780 switch (DECL_FUNCTION_CODE (fndecl))
7781 {
7782 case BUILT_IN_BSWAP32:
7783 case BUILT_IN_BSWAP64:
7784 {
7785 int s;
7786
7787 for (s = 0; s < width; s += 8)
7788 {
7789 int d = width - s - 8;
7790 unsigned HOST_WIDE_INT byte;
7791
7792 if (s < HOST_BITS_PER_WIDE_INT)
7793 byte = (lo >> s) & 0xff;
7794 else
7795 byte = (hi >> (s - HOST_BITS_PER_WIDE_INT)) & 0xff;
7796
7797 if (d < HOST_BITS_PER_WIDE_INT)
7798 r_lo |= byte << d;
7799 else
7800 r_hi |= byte << (d - HOST_BITS_PER_WIDE_INT);
7801 }
7802 }
7803
7804 break;
7805
7806 default:
7807 gcc_unreachable ();
7808 }
7809
7810 if (width < HOST_BITS_PER_WIDE_INT)
7811 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), r_lo);
7812 else
7813 return build_int_cst_wide (TREE_TYPE (TREE_TYPE (fndecl)), r_lo, r_hi);
7814 }
7815
7816 return NULL_TREE;
7817 }
7818
7819 /* A subroutine of fold_builtin to fold the various logarithmic
7820 functions. Return NULL_TREE if no simplification can me made.
7821 FUNC is the corresponding MPFR logarithm function. */
7822
7823 static tree
7824 fold_builtin_logarithm (location_t loc, tree fndecl, tree arg,
7825 int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t))
7826 {
7827 if (validate_arg (arg, REAL_TYPE))
7828 {
7829 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7830 tree res;
7831 const enum built_in_function fcode = builtin_mathfn_code (arg);
7832
7833 /* Calculate the result when the argument is a constant. */
7834 if ((res = do_mpfr_arg1 (arg, type, func, &dconst0, NULL, false)))
7835 return res;
7836
7837 /* Special case, optimize logN(expN(x)) = x. */
7838 if (flag_unsafe_math_optimizations
7839 && ((func == mpfr_log
7840 && (fcode == BUILT_IN_EXP
7841 || fcode == BUILT_IN_EXPF
7842 || fcode == BUILT_IN_EXPL))
7843 || (func == mpfr_log2
7844 && (fcode == BUILT_IN_EXP2
7845 || fcode == BUILT_IN_EXP2F
7846 || fcode == BUILT_IN_EXP2L))
7847 || (func == mpfr_log10 && (BUILTIN_EXP10_P (fcode)))))
7848 return fold_convert_loc (loc, type, CALL_EXPR_ARG (arg, 0));
7849
7850 /* Optimize logN(func()) for various exponential functions. We
7851 want to determine the value "x" and the power "exponent" in
7852 order to transform logN(x**exponent) into exponent*logN(x). */
7853 if (flag_unsafe_math_optimizations)
7854 {
7855 tree exponent = 0, x = 0;
7856
7857 switch (fcode)
7858 {
7859 CASE_FLT_FN (BUILT_IN_EXP):
7860 /* Prepare to do logN(exp(exponent) -> exponent*logN(e). */
7861 x = build_real (type, real_value_truncate (TYPE_MODE (type),
7862 dconst_e ()));
7863 exponent = CALL_EXPR_ARG (arg, 0);
7864 break;
7865 CASE_FLT_FN (BUILT_IN_EXP2):
7866 /* Prepare to do logN(exp2(exponent) -> exponent*logN(2). */
7867 x = build_real (type, dconst2);
7868 exponent = CALL_EXPR_ARG (arg, 0);
7869 break;
7870 CASE_FLT_FN (BUILT_IN_EXP10):
7871 CASE_FLT_FN (BUILT_IN_POW10):
7872 /* Prepare to do logN(exp10(exponent) -> exponent*logN(10). */
7873 {
7874 REAL_VALUE_TYPE dconst10;
7875 real_from_integer (&dconst10, VOIDmode, 10, 0, 0);
7876 x = build_real (type, dconst10);
7877 }
7878 exponent = CALL_EXPR_ARG (arg, 0);
7879 break;
7880 CASE_FLT_FN (BUILT_IN_SQRT):
7881 /* Prepare to do logN(sqrt(x) -> 0.5*logN(x). */
7882 x = CALL_EXPR_ARG (arg, 0);
7883 exponent = build_real (type, dconsthalf);
7884 break;
7885 CASE_FLT_FN (BUILT_IN_CBRT):
7886 /* Prepare to do logN(cbrt(x) -> (1/3)*logN(x). */
7887 x = CALL_EXPR_ARG (arg, 0);
7888 exponent = build_real (type, real_value_truncate (TYPE_MODE (type),
7889 dconst_third ()));
7890 break;
7891 CASE_FLT_FN (BUILT_IN_POW):
7892 /* Prepare to do logN(pow(x,exponent) -> exponent*logN(x). */
7893 x = CALL_EXPR_ARG (arg, 0);
7894 exponent = CALL_EXPR_ARG (arg, 1);
7895 break;
7896 default:
7897 break;
7898 }
7899
7900 /* Now perform the optimization. */
7901 if (x && exponent)
7902 {
7903 tree logfn = build_call_expr_loc (loc, fndecl, 1, x);
7904 return fold_build2_loc (loc, MULT_EXPR, type, exponent, logfn);
7905 }
7906 }
7907 }
7908
7909 return NULL_TREE;
7910 }
7911
7912 /* Fold a builtin function call to hypot, hypotf, or hypotl. Return
7913 NULL_TREE if no simplification can be made. */
7914
7915 static tree
7916 fold_builtin_hypot (location_t loc, tree fndecl,
7917 tree arg0, tree arg1, tree type)
7918 {
7919 tree res, narg0, narg1;
7920
7921 if (!validate_arg (arg0, REAL_TYPE)
7922 || !validate_arg (arg1, REAL_TYPE))
7923 return NULL_TREE;
7924
7925 /* Calculate the result when the argument is a constant. */
7926 if ((res = do_mpfr_arg2 (arg0, arg1, type, mpfr_hypot)))
7927 return res;
7928
7929 /* If either argument to hypot has a negate or abs, strip that off.
7930 E.g. hypot(-x,fabs(y)) -> hypot(x,y). */
7931 narg0 = fold_strip_sign_ops (arg0);
7932 narg1 = fold_strip_sign_ops (arg1);
7933 if (narg0 || narg1)
7934 {
7935 return build_call_expr_loc (loc, fndecl, 2, narg0 ? narg0 : arg0,
7936 narg1 ? narg1 : arg1);
7937 }
7938
7939 /* If either argument is zero, hypot is fabs of the other. */
7940 if (real_zerop (arg0))
7941 return fold_build1_loc (loc, ABS_EXPR, type, arg1);
7942 else if (real_zerop (arg1))
7943 return fold_build1_loc (loc, ABS_EXPR, type, arg0);
7944
7945 /* hypot(x,x) -> fabs(x)*sqrt(2). */
7946 if (flag_unsafe_math_optimizations
7947 && operand_equal_p (arg0, arg1, OEP_PURE_SAME))
7948 {
7949 const REAL_VALUE_TYPE sqrt2_trunc
7950 = real_value_truncate (TYPE_MODE (type), dconst_sqrt2 ());
7951 return fold_build2_loc (loc, MULT_EXPR, type,
7952 fold_build1_loc (loc, ABS_EXPR, type, arg0),
7953 build_real (type, sqrt2_trunc));
7954 }
7955
7956 return NULL_TREE;
7957 }
7958
7959
7960 /* Fold a builtin function call to pow, powf, or powl. Return
7961 NULL_TREE if no simplification can be made. */
7962 static tree
7963 fold_builtin_pow (location_t loc, tree fndecl, tree arg0, tree arg1, tree type)
7964 {
7965 tree res;
7966
7967 if (!validate_arg (arg0, REAL_TYPE)
7968 || !validate_arg (arg1, REAL_TYPE))
7969 return NULL_TREE;
7970
7971 /* Calculate the result when the argument is a constant. */
7972 if ((res = do_mpfr_arg2 (arg0, arg1, type, mpfr_pow)))
7973 return res;
7974
7975 /* Optimize pow(1.0,y) = 1.0. */
7976 if (real_onep (arg0))
7977 return omit_one_operand_loc (loc, type, build_real (type, dconst1), arg1);
7978
7979 if (TREE_CODE (arg1) == REAL_CST
7980 && !TREE_OVERFLOW (arg1))
7981 {
7982 REAL_VALUE_TYPE cint;
7983 REAL_VALUE_TYPE c;
7984 HOST_WIDE_INT n;
7985
7986 c = TREE_REAL_CST (arg1);
7987
7988 /* Optimize pow(x,0.0) = 1.0. */
7989 if (REAL_VALUES_EQUAL (c, dconst0))
7990 return omit_one_operand_loc (loc, type, build_real (type, dconst1),
7991 arg0);
7992
7993 /* Optimize pow(x,1.0) = x. */
7994 if (REAL_VALUES_EQUAL (c, dconst1))
7995 return arg0;
7996
7997 /* Optimize pow(x,-1.0) = 1.0/x. */
7998 if (REAL_VALUES_EQUAL (c, dconstm1))
7999 return fold_build2_loc (loc, RDIV_EXPR, type,
8000 build_real (type, dconst1), arg0);
8001
8002 /* Optimize pow(x,0.5) = sqrt(x). */
8003 if (flag_unsafe_math_optimizations
8004 && REAL_VALUES_EQUAL (c, dconsthalf))
8005 {
8006 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
8007
8008 if (sqrtfn != NULL_TREE)
8009 return build_call_expr_loc (loc, sqrtfn, 1, arg0);
8010 }
8011
8012 /* Optimize pow(x,1.0/3.0) = cbrt(x). */
8013 if (flag_unsafe_math_optimizations)
8014 {
8015 const REAL_VALUE_TYPE dconstroot
8016 = real_value_truncate (TYPE_MODE (type), dconst_third ());
8017
8018 if (REAL_VALUES_EQUAL (c, dconstroot))
8019 {
8020 tree cbrtfn = mathfn_built_in (type, BUILT_IN_CBRT);
8021 if (cbrtfn != NULL_TREE)
8022 return build_call_expr_loc (loc, cbrtfn, 1, arg0);
8023 }
8024 }
8025
8026 /* Check for an integer exponent. */
8027 n = real_to_integer (&c);
8028 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
8029 if (real_identical (&c, &cint))
8030 {
8031 /* Attempt to evaluate pow at compile-time, unless this should
8032 raise an exception. */
8033 if (TREE_CODE (arg0) == REAL_CST
8034 && !TREE_OVERFLOW (arg0)
8035 && (n > 0
8036 || (!flag_trapping_math && !flag_errno_math)
8037 || !REAL_VALUES_EQUAL (TREE_REAL_CST (arg0), dconst0)))
8038 {
8039 REAL_VALUE_TYPE x;
8040 bool inexact;
8041
8042 x = TREE_REAL_CST (arg0);
8043 inexact = real_powi (&x, TYPE_MODE (type), &x, n);
8044 if (flag_unsafe_math_optimizations || !inexact)
8045 return build_real (type, x);
8046 }
8047
8048 /* Strip sign ops from even integer powers. */
8049 if ((n & 1) == 0 && flag_unsafe_math_optimizations)
8050 {
8051 tree narg0 = fold_strip_sign_ops (arg0);
8052 if (narg0)
8053 return build_call_expr_loc (loc, fndecl, 2, narg0, arg1);
8054 }
8055 }
8056 }
8057
8058 if (flag_unsafe_math_optimizations)
8059 {
8060 const enum built_in_function fcode = builtin_mathfn_code (arg0);
8061
8062 /* Optimize pow(expN(x),y) = expN(x*y). */
8063 if (BUILTIN_EXPONENT_P (fcode))
8064 {
8065 tree expfn = TREE_OPERAND (CALL_EXPR_FN (arg0), 0);
8066 tree arg = CALL_EXPR_ARG (arg0, 0);
8067 arg = fold_build2_loc (loc, MULT_EXPR, type, arg, arg1);
8068 return build_call_expr_loc (loc, expfn, 1, arg);
8069 }
8070
8071 /* Optimize pow(sqrt(x),y) = pow(x,y*0.5). */
8072 if (BUILTIN_SQRT_P (fcode))
8073 {
8074 tree narg0 = CALL_EXPR_ARG (arg0, 0);
8075 tree narg1 = fold_build2_loc (loc, MULT_EXPR, type, arg1,
8076 build_real (type, dconsthalf));
8077 return build_call_expr_loc (loc, fndecl, 2, narg0, narg1);
8078 }
8079
8080 /* Optimize pow(cbrt(x),y) = pow(x,y/3) iff x is nonnegative. */
8081 if (BUILTIN_CBRT_P (fcode))
8082 {
8083 tree arg = CALL_EXPR_ARG (arg0, 0);
8084 if (tree_expr_nonnegative_p (arg))
8085 {
8086 const REAL_VALUE_TYPE dconstroot
8087 = real_value_truncate (TYPE_MODE (type), dconst_third ());
8088 tree narg1 = fold_build2_loc (loc, MULT_EXPR, type, arg1,
8089 build_real (type, dconstroot));
8090 return build_call_expr_loc (loc, fndecl, 2, arg, narg1);
8091 }
8092 }
8093
8094 /* Optimize pow(pow(x,y),z) = pow(x,y*z) iff x is nonnegative. */
8095 if (fcode == BUILT_IN_POW
8096 || fcode == BUILT_IN_POWF
8097 || fcode == BUILT_IN_POWL)
8098 {
8099 tree arg00 = CALL_EXPR_ARG (arg0, 0);
8100 if (tree_expr_nonnegative_p (arg00))
8101 {
8102 tree arg01 = CALL_EXPR_ARG (arg0, 1);
8103 tree narg1 = fold_build2_loc (loc, MULT_EXPR, type, arg01, arg1);
8104 return build_call_expr_loc (loc, fndecl, 2, arg00, narg1);
8105 }
8106 }
8107 }
8108
8109 return NULL_TREE;
8110 }
8111
8112 /* Fold a builtin function call to powi, powif, or powil with argument ARG.
8113 Return NULL_TREE if no simplification can be made. */
8114 static tree
8115 fold_builtin_powi (location_t loc, tree fndecl ATTRIBUTE_UNUSED,
8116 tree arg0, tree arg1, tree type)
8117 {
8118 if (!validate_arg (arg0, REAL_TYPE)
8119 || !validate_arg (arg1, INTEGER_TYPE))
8120 return NULL_TREE;
8121
8122 /* Optimize pow(1.0,y) = 1.0. */
8123 if (real_onep (arg0))
8124 return omit_one_operand_loc (loc, type, build_real (type, dconst1), arg1);
8125
8126 if (host_integerp (arg1, 0))
8127 {
8128 HOST_WIDE_INT c = TREE_INT_CST_LOW (arg1);
8129
8130 /* Evaluate powi at compile-time. */
8131 if (TREE_CODE (arg0) == REAL_CST
8132 && !TREE_OVERFLOW (arg0))
8133 {
8134 REAL_VALUE_TYPE x;
8135 x = TREE_REAL_CST (arg0);
8136 real_powi (&x, TYPE_MODE (type), &x, c);
8137 return build_real (type, x);
8138 }
8139
8140 /* Optimize pow(x,0) = 1.0. */
8141 if (c == 0)
8142 return omit_one_operand_loc (loc, type, build_real (type, dconst1),
8143 arg0);
8144
8145 /* Optimize pow(x,1) = x. */
8146 if (c == 1)
8147 return arg0;
8148
8149 /* Optimize pow(x,-1) = 1.0/x. */
8150 if (c == -1)
8151 return fold_build2_loc (loc, RDIV_EXPR, type,
8152 build_real (type, dconst1), arg0);
8153 }
8154
8155 return NULL_TREE;
8156 }
8157
8158 /* A subroutine of fold_builtin to fold the various exponent
8159 functions. Return NULL_TREE if no simplification can be made.
8160 FUNC is the corresponding MPFR exponent function. */
8161
8162 static tree
8163 fold_builtin_exponent (location_t loc, tree fndecl, tree arg,
8164 int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t))
8165 {
8166 if (validate_arg (arg, REAL_TYPE))
8167 {
8168 tree type = TREE_TYPE (TREE_TYPE (fndecl));
8169 tree res;
8170
8171 /* Calculate the result when the argument is a constant. */
8172 if ((res = do_mpfr_arg1 (arg, type, func, NULL, NULL, 0)))
8173 return res;
8174
8175 /* Optimize expN(logN(x)) = x. */
8176 if (flag_unsafe_math_optimizations)
8177 {
8178 const enum built_in_function fcode = builtin_mathfn_code (arg);
8179
8180 if ((func == mpfr_exp
8181 && (fcode == BUILT_IN_LOG
8182 || fcode == BUILT_IN_LOGF
8183 || fcode == BUILT_IN_LOGL))
8184 || (func == mpfr_exp2
8185 && (fcode == BUILT_IN_LOG2
8186 || fcode == BUILT_IN_LOG2F
8187 || fcode == BUILT_IN_LOG2L))
8188 || (func == mpfr_exp10
8189 && (fcode == BUILT_IN_LOG10
8190 || fcode == BUILT_IN_LOG10F
8191 || fcode == BUILT_IN_LOG10L)))
8192 return fold_convert_loc (loc, type, CALL_EXPR_ARG (arg, 0));
8193 }
8194 }
8195
8196 return NULL_TREE;
8197 }
8198
8199 /* Return true if VAR is a VAR_DECL or a component thereof. */
8200
8201 static bool
8202 var_decl_component_p (tree var)
8203 {
8204 tree inner = var;
8205 while (handled_component_p (inner))
8206 inner = TREE_OPERAND (inner, 0);
8207 return SSA_VAR_P (inner);
8208 }
8209
8210 /* Fold function call to builtin memset. Return
8211 NULL_TREE if no simplification can be made. */
8212
8213 static tree
8214 fold_builtin_memset (location_t loc, tree dest, tree c, tree len,
8215 tree type, bool ignore)
8216 {
8217 tree var, ret, etype;
8218 unsigned HOST_WIDE_INT length, cval;
8219
8220 if (! validate_arg (dest, POINTER_TYPE)
8221 || ! validate_arg (c, INTEGER_TYPE)
8222 || ! validate_arg (len, INTEGER_TYPE))
8223 return NULL_TREE;
8224
8225 if (! host_integerp (len, 1))
8226 return NULL_TREE;
8227
8228 /* If the LEN parameter is zero, return DEST. */
8229 if (integer_zerop (len))
8230 return omit_one_operand_loc (loc, type, dest, c);
8231
8232 if (! host_integerp (c, 1) || TREE_SIDE_EFFECTS (dest))
8233 return NULL_TREE;
8234
8235 var = dest;
8236 STRIP_NOPS (var);
8237 if (TREE_CODE (var) != ADDR_EXPR)
8238 return NULL_TREE;
8239
8240 var = TREE_OPERAND (var, 0);
8241 if (TREE_THIS_VOLATILE (var))
8242 return NULL_TREE;
8243
8244 etype = TREE_TYPE (var);
8245 if (TREE_CODE (etype) == ARRAY_TYPE)
8246 etype = TREE_TYPE (etype);
8247
8248 if (!INTEGRAL_TYPE_P (etype)
8249 && !POINTER_TYPE_P (etype))
8250 return NULL_TREE;
8251
8252 if (! var_decl_component_p (var))
8253 return NULL_TREE;
8254
8255 length = tree_low_cst (len, 1);
8256 if (GET_MODE_SIZE (TYPE_MODE (etype)) != length
8257 || get_pointer_alignment (dest, BIGGEST_ALIGNMENT) / BITS_PER_UNIT
8258 < (int) length)
8259 return NULL_TREE;
8260
8261 if (length > HOST_BITS_PER_WIDE_INT / BITS_PER_UNIT)
8262 return NULL_TREE;
8263
8264 if (integer_zerop (c))
8265 cval = 0;
8266 else
8267 {
8268 if (CHAR_BIT != 8 || BITS_PER_UNIT != 8 || HOST_BITS_PER_WIDE_INT > 64)
8269 return NULL_TREE;
8270
8271 cval = tree_low_cst (c, 1);
8272 cval &= 0xff;
8273 cval |= cval << 8;
8274 cval |= cval << 16;
8275 cval |= (cval << 31) << 1;
8276 }
8277
8278 ret = build_int_cst_type (etype, cval);
8279 var = build_fold_indirect_ref_loc (loc,
8280 fold_convert_loc (loc,
8281 build_pointer_type (etype),
8282 dest));
8283 ret = build2 (MODIFY_EXPR, etype, var, ret);
8284 if (ignore)
8285 return ret;
8286
8287 return omit_one_operand_loc (loc, type, dest, ret);
8288 }
8289
8290 /* Fold function call to builtin memset. Return
8291 NULL_TREE if no simplification can be made. */
8292
8293 static tree
8294 fold_builtin_bzero (location_t loc, tree dest, tree size, bool ignore)
8295 {
8296 if (! validate_arg (dest, POINTER_TYPE)
8297 || ! validate_arg (size, INTEGER_TYPE))
8298 return NULL_TREE;
8299
8300 if (!ignore)
8301 return NULL_TREE;
8302
8303 /* New argument list transforming bzero(ptr x, int y) to
8304 memset(ptr x, int 0, size_t y). This is done this way
8305 so that if it isn't expanded inline, we fallback to
8306 calling bzero instead of memset. */
8307
8308 return fold_builtin_memset (loc, dest, integer_zero_node,
8309 fold_convert_loc (loc, sizetype, size),
8310 void_type_node, ignore);
8311 }
8312
8313 /* Fold function call to builtin mem{{,p}cpy,move}. Return
8314 NULL_TREE if no simplification can be made.
8315 If ENDP is 0, return DEST (like memcpy).
8316 If ENDP is 1, return DEST+LEN (like mempcpy).
8317 If ENDP is 2, return DEST+LEN-1 (like stpcpy).
8318 If ENDP is 3, return DEST, additionally *SRC and *DEST may overlap
8319 (memmove). */
8320
8321 static tree
8322 fold_builtin_memory_op (location_t loc, tree dest, tree src,
8323 tree len, tree type, bool ignore, int endp)
8324 {
8325 tree destvar, srcvar, expr;
8326
8327 if (! validate_arg (dest, POINTER_TYPE)
8328 || ! validate_arg (src, POINTER_TYPE)
8329 || ! validate_arg (len, INTEGER_TYPE))
8330 return NULL_TREE;
8331
8332 /* If the LEN parameter is zero, return DEST. */
8333 if (integer_zerop (len))
8334 return omit_one_operand_loc (loc, type, dest, src);
8335
8336 /* If SRC and DEST are the same (and not volatile), return
8337 DEST{,+LEN,+LEN-1}. */
8338 if (operand_equal_p (src, dest, 0))
8339 expr = len;
8340 else
8341 {
8342 tree srctype, desttype;
8343 int src_align, dest_align;
8344
8345 if (endp == 3)
8346 {
8347 src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
8348 dest_align = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
8349
8350 /* Both DEST and SRC must be pointer types.
8351 ??? This is what old code did. Is the testing for pointer types
8352 really mandatory?
8353
8354 If either SRC is readonly or length is 1, we can use memcpy. */
8355 if (!dest_align || !src_align)
8356 return NULL_TREE;
8357 if (readonly_data_expr (src)
8358 || (host_integerp (len, 1)
8359 && (MIN (src_align, dest_align) / BITS_PER_UNIT
8360 >= tree_low_cst (len, 1))))
8361 {
8362 tree fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8363 if (!fn)
8364 return NULL_TREE;
8365 return build_call_expr_loc (loc, fn, 3, dest, src, len);
8366 }
8367
8368 /* If *src and *dest can't overlap, optimize into memcpy as well. */
8369 srcvar = build_fold_indirect_ref_loc (loc, src);
8370 destvar = build_fold_indirect_ref_loc (loc, dest);
8371 if (srcvar
8372 && !TREE_THIS_VOLATILE (srcvar)
8373 && destvar
8374 && !TREE_THIS_VOLATILE (destvar))
8375 {
8376 tree src_base, dest_base, fn;
8377 HOST_WIDE_INT src_offset = 0, dest_offset = 0;
8378 HOST_WIDE_INT size = -1;
8379 HOST_WIDE_INT maxsize = -1;
8380
8381 src_base = srcvar;
8382 if (handled_component_p (src_base))
8383 src_base = get_ref_base_and_extent (src_base, &src_offset,
8384 &size, &maxsize);
8385 dest_base = destvar;
8386 if (handled_component_p (dest_base))
8387 dest_base = get_ref_base_and_extent (dest_base, &dest_offset,
8388 &size, &maxsize);
8389 if (host_integerp (len, 1))
8390 {
8391 maxsize = tree_low_cst (len, 1);
8392 if (maxsize
8393 > INTTYPE_MAXIMUM (HOST_WIDE_INT) / BITS_PER_UNIT)
8394 maxsize = -1;
8395 else
8396 maxsize *= BITS_PER_UNIT;
8397 }
8398 else
8399 maxsize = -1;
8400 if (SSA_VAR_P (src_base)
8401 && SSA_VAR_P (dest_base))
8402 {
8403 if (operand_equal_p (src_base, dest_base, 0)
8404 && ranges_overlap_p (src_offset, maxsize,
8405 dest_offset, maxsize))
8406 return NULL_TREE;
8407 }
8408 else if (TREE_CODE (src_base) == INDIRECT_REF
8409 && TREE_CODE (dest_base) == INDIRECT_REF)
8410 {
8411 if (! operand_equal_p (TREE_OPERAND (src_base, 0),
8412 TREE_OPERAND (dest_base, 0), 0)
8413 || ranges_overlap_p (src_offset, maxsize,
8414 dest_offset, maxsize))
8415 return NULL_TREE;
8416 }
8417 else
8418 return NULL_TREE;
8419
8420 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8421 if (!fn)
8422 return NULL_TREE;
8423 return build_call_expr_loc (loc, fn, 3, dest, src, len);
8424 }
8425 return NULL_TREE;
8426 }
8427
8428 if (!host_integerp (len, 0))
8429 return NULL_TREE;
8430 /* FIXME:
8431 This logic lose for arguments like (type *)malloc (sizeof (type)),
8432 since we strip the casts of up to VOID return value from malloc.
8433 Perhaps we ought to inherit type from non-VOID argument here? */
8434 STRIP_NOPS (src);
8435 STRIP_NOPS (dest);
8436 /* As we fold (void *)(p + CST) to (void *)p + CST undo this here. */
8437 if (TREE_CODE (src) == POINTER_PLUS_EXPR)
8438 {
8439 tree tem = TREE_OPERAND (src, 0);
8440 STRIP_NOPS (tem);
8441 if (tem != TREE_OPERAND (src, 0))
8442 src = build1 (NOP_EXPR, TREE_TYPE (tem), src);
8443 }
8444 if (TREE_CODE (dest) == POINTER_PLUS_EXPR)
8445 {
8446 tree tem = TREE_OPERAND (dest, 0);
8447 STRIP_NOPS (tem);
8448 if (tem != TREE_OPERAND (dest, 0))
8449 dest = build1 (NOP_EXPR, TREE_TYPE (tem), dest);
8450 }
8451 srctype = TREE_TYPE (TREE_TYPE (src));
8452 if (srctype
8453 && TREE_CODE (srctype) == ARRAY_TYPE
8454 && !tree_int_cst_equal (TYPE_SIZE_UNIT (srctype), len))
8455 {
8456 srctype = TREE_TYPE (srctype);
8457 STRIP_NOPS (src);
8458 src = build1 (NOP_EXPR, build_pointer_type (srctype), src);
8459 }
8460 desttype = TREE_TYPE (TREE_TYPE (dest));
8461 if (desttype
8462 && TREE_CODE (desttype) == ARRAY_TYPE
8463 && !tree_int_cst_equal (TYPE_SIZE_UNIT (desttype), len))
8464 {
8465 desttype = TREE_TYPE (desttype);
8466 STRIP_NOPS (dest);
8467 dest = build1 (NOP_EXPR, build_pointer_type (desttype), dest);
8468 }
8469 if (!srctype || !desttype
8470 || !TYPE_SIZE_UNIT (srctype)
8471 || !TYPE_SIZE_UNIT (desttype)
8472 || TREE_CODE (TYPE_SIZE_UNIT (srctype)) != INTEGER_CST
8473 || TREE_CODE (TYPE_SIZE_UNIT (desttype)) != INTEGER_CST
8474 || TYPE_VOLATILE (srctype)
8475 || TYPE_VOLATILE (desttype))
8476 return NULL_TREE;
8477
8478 src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
8479 dest_align = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
8480 if (dest_align < (int) TYPE_ALIGN (desttype)
8481 || src_align < (int) TYPE_ALIGN (srctype))
8482 return NULL_TREE;
8483
8484 if (!ignore)
8485 dest = builtin_save_expr (dest);
8486
8487 srcvar = NULL_TREE;
8488 if (tree_int_cst_equal (TYPE_SIZE_UNIT (srctype), len))
8489 {
8490 srcvar = build_fold_indirect_ref_loc (loc, src);
8491 if (TREE_THIS_VOLATILE (srcvar))
8492 return NULL_TREE;
8493 else if (!tree_int_cst_equal (tree_expr_size (srcvar), len))
8494 srcvar = NULL_TREE;
8495 /* With memcpy, it is possible to bypass aliasing rules, so without
8496 this check i.e. execute/20060930-2.c would be misoptimized,
8497 because it use conflicting alias set to hold argument for the
8498 memcpy call. This check is probably unnecessary with
8499 -fno-strict-aliasing. Similarly for destvar. See also
8500 PR29286. */
8501 else if (!var_decl_component_p (srcvar))
8502 srcvar = NULL_TREE;
8503 }
8504
8505 destvar = NULL_TREE;
8506 if (tree_int_cst_equal (TYPE_SIZE_UNIT (desttype), len))
8507 {
8508 destvar = build_fold_indirect_ref_loc (loc, dest);
8509 if (TREE_THIS_VOLATILE (destvar))
8510 return NULL_TREE;
8511 else if (!tree_int_cst_equal (tree_expr_size (destvar), len))
8512 destvar = NULL_TREE;
8513 else if (!var_decl_component_p (destvar))
8514 destvar = NULL_TREE;
8515 }
8516
8517 if (srcvar == NULL_TREE && destvar == NULL_TREE)
8518 return NULL_TREE;
8519
8520 if (srcvar == NULL_TREE)
8521 {
8522 tree srcptype;
8523 if (TREE_ADDRESSABLE (TREE_TYPE (destvar)))
8524 return NULL_TREE;
8525
8526 srctype = build_qualified_type (desttype, 0);
8527 if (src_align < (int) TYPE_ALIGN (srctype))
8528 {
8529 if (AGGREGATE_TYPE_P (srctype)
8530 || SLOW_UNALIGNED_ACCESS (TYPE_MODE (srctype), src_align))
8531 return NULL_TREE;
8532
8533 srctype = build_variant_type_copy (srctype);
8534 TYPE_ALIGN (srctype) = src_align;
8535 TYPE_USER_ALIGN (srctype) = 1;
8536 TYPE_PACKED (srctype) = 1;
8537 }
8538 srcptype = build_pointer_type_for_mode (srctype, ptr_mode, true);
8539 src = fold_convert_loc (loc, srcptype, src);
8540 srcvar = build_fold_indirect_ref_loc (loc, src);
8541 }
8542 else if (destvar == NULL_TREE)
8543 {
8544 tree destptype;
8545 if (TREE_ADDRESSABLE (TREE_TYPE (srcvar)))
8546 return NULL_TREE;
8547
8548 desttype = build_qualified_type (srctype, 0);
8549 if (dest_align < (int) TYPE_ALIGN (desttype))
8550 {
8551 if (AGGREGATE_TYPE_P (desttype)
8552 || SLOW_UNALIGNED_ACCESS (TYPE_MODE (desttype), dest_align))
8553 return NULL_TREE;
8554
8555 desttype = build_variant_type_copy (desttype);
8556 TYPE_ALIGN (desttype) = dest_align;
8557 TYPE_USER_ALIGN (desttype) = 1;
8558 TYPE_PACKED (desttype) = 1;
8559 }
8560 destptype = build_pointer_type_for_mode (desttype, ptr_mode, true);
8561 dest = fold_convert_loc (loc, destptype, dest);
8562 destvar = build_fold_indirect_ref_loc (loc, dest);
8563 }
8564
8565 if (srctype == desttype
8566 || (gimple_in_ssa_p (cfun)
8567 && useless_type_conversion_p (desttype, srctype)))
8568 expr = srcvar;
8569 else if ((INTEGRAL_TYPE_P (TREE_TYPE (srcvar))
8570 || POINTER_TYPE_P (TREE_TYPE (srcvar)))
8571 && (INTEGRAL_TYPE_P (TREE_TYPE (destvar))
8572 || POINTER_TYPE_P (TREE_TYPE (destvar))))
8573 expr = fold_convert_loc (loc, TREE_TYPE (destvar), srcvar);
8574 else
8575 expr = fold_build1_loc (loc, VIEW_CONVERT_EXPR,
8576 TREE_TYPE (destvar), srcvar);
8577 expr = build2 (MODIFY_EXPR, TREE_TYPE (destvar), destvar, expr);
8578 }
8579
8580 if (ignore)
8581 return expr;
8582
8583 if (endp == 0 || endp == 3)
8584 return omit_one_operand_loc (loc, type, dest, expr);
8585
8586 if (expr == len)
8587 expr = NULL_TREE;
8588
8589 if (endp == 2)
8590 len = fold_build2_loc (loc, MINUS_EXPR, TREE_TYPE (len), len,
8591 ssize_int (1));
8592
8593 len = fold_convert_loc (loc, sizetype, len);
8594 dest = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
8595 dest = fold_convert_loc (loc, type, dest);
8596 if (expr)
8597 dest = omit_one_operand_loc (loc, type, dest, expr);
8598 return dest;
8599 }
8600
8601 /* Fold function call to builtin strcpy with arguments DEST and SRC.
8602 If LEN is not NULL, it represents the length of the string to be
8603 copied. Return NULL_TREE if no simplification can be made. */
8604
8605 tree
8606 fold_builtin_strcpy (location_t loc, tree fndecl, tree dest, tree src, tree len)
8607 {
8608 tree fn;
8609
8610 if (!validate_arg (dest, POINTER_TYPE)
8611 || !validate_arg (src, POINTER_TYPE))
8612 return NULL_TREE;
8613
8614 /* If SRC and DEST are the same (and not volatile), return DEST. */
8615 if (operand_equal_p (src, dest, 0))
8616 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest);
8617
8618 if (optimize_function_for_size_p (cfun))
8619 return NULL_TREE;
8620
8621 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8622 if (!fn)
8623 return NULL_TREE;
8624
8625 if (!len)
8626 {
8627 len = c_strlen (src, 1);
8628 if (! len || TREE_SIDE_EFFECTS (len))
8629 return NULL_TREE;
8630 }
8631
8632 len = size_binop_loc (loc, PLUS_EXPR, len, ssize_int (1));
8633 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)),
8634 build_call_expr_loc (loc, fn, 3, dest, src, len));
8635 }
8636
8637 /* Fold function call to builtin stpcpy with arguments DEST and SRC.
8638 Return NULL_TREE if no simplification can be made. */
8639
8640 static tree
8641 fold_builtin_stpcpy (location_t loc, tree fndecl, tree dest, tree src)
8642 {
8643 tree fn, len, lenp1, call, type;
8644
8645 if (!validate_arg (dest, POINTER_TYPE)
8646 || !validate_arg (src, POINTER_TYPE))
8647 return NULL_TREE;
8648
8649 len = c_strlen (src, 1);
8650 if (!len
8651 || TREE_CODE (len) != INTEGER_CST)
8652 return NULL_TREE;
8653
8654 if (optimize_function_for_size_p (cfun)
8655 /* If length is zero it's small enough. */
8656 && !integer_zerop (len))
8657 return NULL_TREE;
8658
8659 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8660 if (!fn)
8661 return NULL_TREE;
8662
8663 lenp1 = size_binop_loc (loc, PLUS_EXPR, len, ssize_int (1));
8664 /* We use dest twice in building our expression. Save it from
8665 multiple expansions. */
8666 dest = builtin_save_expr (dest);
8667 call = build_call_expr_loc (loc, fn, 3, dest, src, lenp1);
8668
8669 type = TREE_TYPE (TREE_TYPE (fndecl));
8670 len = fold_convert_loc (loc, sizetype, len);
8671 dest = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
8672 dest = fold_convert_loc (loc, type, dest);
8673 dest = omit_one_operand_loc (loc, type, dest, call);
8674 return dest;
8675 }
8676
8677 /* Fold function call to builtin strncpy with arguments DEST, SRC, and LEN.
8678 If SLEN is not NULL, it represents the length of the source string.
8679 Return NULL_TREE if no simplification can be made. */
8680
8681 tree
8682 fold_builtin_strncpy (location_t loc, tree fndecl, tree dest,
8683 tree src, tree len, tree slen)
8684 {
8685 tree fn;
8686
8687 if (!validate_arg (dest, POINTER_TYPE)
8688 || !validate_arg (src, POINTER_TYPE)
8689 || !validate_arg (len, INTEGER_TYPE))
8690 return NULL_TREE;
8691
8692 /* If the LEN parameter is zero, return DEST. */
8693 if (integer_zerop (len))
8694 return omit_one_operand_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
8695
8696 /* We can't compare slen with len as constants below if len is not a
8697 constant. */
8698 if (len == 0 || TREE_CODE (len) != INTEGER_CST)
8699 return NULL_TREE;
8700
8701 if (!slen)
8702 slen = c_strlen (src, 1);
8703
8704 /* Now, we must be passed a constant src ptr parameter. */
8705 if (slen == 0 || TREE_CODE (slen) != INTEGER_CST)
8706 return NULL_TREE;
8707
8708 slen = size_binop_loc (loc, PLUS_EXPR, slen, ssize_int (1));
8709
8710 /* We do not support simplification of this case, though we do
8711 support it when expanding trees into RTL. */
8712 /* FIXME: generate a call to __builtin_memset. */
8713 if (tree_int_cst_lt (slen, len))
8714 return NULL_TREE;
8715
8716 /* OK transform into builtin memcpy. */
8717 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8718 if (!fn)
8719 return NULL_TREE;
8720 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)),
8721 build_call_expr_loc (loc, fn, 3, dest, src, len));
8722 }
8723
8724 /* Fold function call to builtin memchr. ARG1, ARG2 and LEN are the
8725 arguments to the call, and TYPE is its return type.
8726 Return NULL_TREE if no simplification can be made. */
8727
8728 static tree
8729 fold_builtin_memchr (location_t loc, tree arg1, tree arg2, tree len, tree type)
8730 {
8731 if (!validate_arg (arg1, POINTER_TYPE)
8732 || !validate_arg (arg2, INTEGER_TYPE)
8733 || !validate_arg (len, INTEGER_TYPE))
8734 return NULL_TREE;
8735 else
8736 {
8737 const char *p1;
8738
8739 if (TREE_CODE (arg2) != INTEGER_CST
8740 || !host_integerp (len, 1))
8741 return NULL_TREE;
8742
8743 p1 = c_getstr (arg1);
8744 if (p1 && compare_tree_int (len, strlen (p1) + 1) <= 0)
8745 {
8746 char c;
8747 const char *r;
8748 tree tem;
8749
8750 if (target_char_cast (arg2, &c))
8751 return NULL_TREE;
8752
8753 r = (char *) memchr (p1, c, tree_low_cst (len, 1));
8754
8755 if (r == NULL)
8756 return build_int_cst (TREE_TYPE (arg1), 0);
8757
8758 tem = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (arg1), arg1,
8759 size_int (r - p1));
8760 return fold_convert_loc (loc, type, tem);
8761 }
8762 return NULL_TREE;
8763 }
8764 }
8765
8766 /* Fold function call to builtin memcmp with arguments ARG1 and ARG2.
8767 Return NULL_TREE if no simplification can be made. */
8768
8769 static tree
8770 fold_builtin_memcmp (location_t loc, tree arg1, tree arg2, tree len)
8771 {
8772 const char *p1, *p2;
8773
8774 if (!validate_arg (arg1, POINTER_TYPE)
8775 || !validate_arg (arg2, POINTER_TYPE)
8776 || !validate_arg (len, INTEGER_TYPE))
8777 return NULL_TREE;
8778
8779 /* If the LEN parameter is zero, return zero. */
8780 if (integer_zerop (len))
8781 return omit_two_operands_loc (loc, integer_type_node, integer_zero_node,
8782 arg1, arg2);
8783
8784 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
8785 if (operand_equal_p (arg1, arg2, 0))
8786 return omit_one_operand_loc (loc, integer_type_node, integer_zero_node, len);
8787
8788 p1 = c_getstr (arg1);
8789 p2 = c_getstr (arg2);
8790
8791 /* If all arguments are constant, and the value of len is not greater
8792 than the lengths of arg1 and arg2, evaluate at compile-time. */
8793 if (host_integerp (len, 1) && p1 && p2
8794 && compare_tree_int (len, strlen (p1) + 1) <= 0
8795 && compare_tree_int (len, strlen (p2) + 1) <= 0)
8796 {
8797 const int r = memcmp (p1, p2, tree_low_cst (len, 1));
8798
8799 if (r > 0)
8800 return integer_one_node;
8801 else if (r < 0)
8802 return integer_minus_one_node;
8803 else
8804 return integer_zero_node;
8805 }
8806
8807 /* If len parameter is one, return an expression corresponding to
8808 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
8809 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 1)
8810 {
8811 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8812 tree cst_uchar_ptr_node
8813 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8814
8815 tree ind1
8816 = fold_convert_loc (loc, integer_type_node,
8817 build1 (INDIRECT_REF, cst_uchar_node,
8818 fold_convert_loc (loc,
8819 cst_uchar_ptr_node,
8820 arg1)));
8821 tree ind2
8822 = fold_convert_loc (loc, integer_type_node,
8823 build1 (INDIRECT_REF, cst_uchar_node,
8824 fold_convert_loc (loc,
8825 cst_uchar_ptr_node,
8826 arg2)));
8827 return fold_build2_loc (loc, MINUS_EXPR, integer_type_node, ind1, ind2);
8828 }
8829
8830 return NULL_TREE;
8831 }
8832
8833 /* Fold function call to builtin strcmp with arguments ARG1 and ARG2.
8834 Return NULL_TREE if no simplification can be made. */
8835
8836 static tree
8837 fold_builtin_strcmp (location_t loc, tree arg1, tree arg2)
8838 {
8839 const char *p1, *p2;
8840
8841 if (!validate_arg (arg1, POINTER_TYPE)
8842 || !validate_arg (arg2, POINTER_TYPE))
8843 return NULL_TREE;
8844
8845 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
8846 if (operand_equal_p (arg1, arg2, 0))
8847 return integer_zero_node;
8848
8849 p1 = c_getstr (arg1);
8850 p2 = c_getstr (arg2);
8851
8852 if (p1 && p2)
8853 {
8854 const int i = strcmp (p1, p2);
8855 if (i < 0)
8856 return integer_minus_one_node;
8857 else if (i > 0)
8858 return integer_one_node;
8859 else
8860 return integer_zero_node;
8861 }
8862
8863 /* If the second arg is "", return *(const unsigned char*)arg1. */
8864 if (p2 && *p2 == '\0')
8865 {
8866 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8867 tree cst_uchar_ptr_node
8868 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8869
8870 return fold_convert_loc (loc, integer_type_node,
8871 build1 (INDIRECT_REF, cst_uchar_node,
8872 fold_convert_loc (loc,
8873 cst_uchar_ptr_node,
8874 arg1)));
8875 }
8876
8877 /* If the first arg is "", return -*(const unsigned char*)arg2. */
8878 if (p1 && *p1 == '\0')
8879 {
8880 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8881 tree cst_uchar_ptr_node
8882 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8883
8884 tree temp
8885 = fold_convert_loc (loc, integer_type_node,
8886 build1 (INDIRECT_REF, cst_uchar_node,
8887 fold_convert_loc (loc,
8888 cst_uchar_ptr_node,
8889 arg2)));
8890 return fold_build1_loc (loc, NEGATE_EXPR, integer_type_node, temp);
8891 }
8892
8893 return NULL_TREE;
8894 }
8895
8896 /* Fold function call to builtin strncmp with arguments ARG1, ARG2, and LEN.
8897 Return NULL_TREE if no simplification can be made. */
8898
8899 static tree
8900 fold_builtin_strncmp (location_t loc, tree arg1, tree arg2, tree len)
8901 {
8902 const char *p1, *p2;
8903
8904 if (!validate_arg (arg1, POINTER_TYPE)
8905 || !validate_arg (arg2, POINTER_TYPE)
8906 || !validate_arg (len, INTEGER_TYPE))
8907 return NULL_TREE;
8908
8909 /* If the LEN parameter is zero, return zero. */
8910 if (integer_zerop (len))
8911 return omit_two_operands_loc (loc, integer_type_node, integer_zero_node,
8912 arg1, arg2);
8913
8914 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
8915 if (operand_equal_p (arg1, arg2, 0))
8916 return omit_one_operand_loc (loc, integer_type_node, integer_zero_node, len);
8917
8918 p1 = c_getstr (arg1);
8919 p2 = c_getstr (arg2);
8920
8921 if (host_integerp (len, 1) && p1 && p2)
8922 {
8923 const int i = strncmp (p1, p2, tree_low_cst (len, 1));
8924 if (i > 0)
8925 return integer_one_node;
8926 else if (i < 0)
8927 return integer_minus_one_node;
8928 else
8929 return integer_zero_node;
8930 }
8931
8932 /* If the second arg is "", and the length is greater than zero,
8933 return *(const unsigned char*)arg1. */
8934 if (p2 && *p2 == '\0'
8935 && TREE_CODE (len) == INTEGER_CST
8936 && tree_int_cst_sgn (len) == 1)
8937 {
8938 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8939 tree cst_uchar_ptr_node
8940 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8941
8942 return fold_convert_loc (loc, integer_type_node,
8943 build1 (INDIRECT_REF, cst_uchar_node,
8944 fold_convert_loc (loc,
8945 cst_uchar_ptr_node,
8946 arg1)));
8947 }
8948
8949 /* If the first arg is "", and the length is greater than zero,
8950 return -*(const unsigned char*)arg2. */
8951 if (p1 && *p1 == '\0'
8952 && TREE_CODE (len) == INTEGER_CST
8953 && tree_int_cst_sgn (len) == 1)
8954 {
8955 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8956 tree cst_uchar_ptr_node
8957 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8958
8959 tree temp = fold_convert_loc (loc, integer_type_node,
8960 build1 (INDIRECT_REF, cst_uchar_node,
8961 fold_convert_loc (loc,
8962 cst_uchar_ptr_node,
8963 arg2)));
8964 return fold_build1_loc (loc, NEGATE_EXPR, integer_type_node, temp);
8965 }
8966
8967 /* If len parameter is one, return an expression corresponding to
8968 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
8969 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 1)
8970 {
8971 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8972 tree cst_uchar_ptr_node
8973 = build_pointer_type_for_mode (cst_uchar_node, ptr_mode, true);
8974
8975 tree ind1 = fold_convert_loc (loc, integer_type_node,
8976 build1 (INDIRECT_REF, cst_uchar_node,
8977 fold_convert_loc (loc,
8978 cst_uchar_ptr_node,
8979 arg1)));
8980 tree ind2 = fold_convert_loc (loc, integer_type_node,
8981 build1 (INDIRECT_REF, cst_uchar_node,
8982 fold_convert_loc (loc,
8983 cst_uchar_ptr_node,
8984 arg2)));
8985 return fold_build2_loc (loc, MINUS_EXPR, integer_type_node, ind1, ind2);
8986 }
8987
8988 return NULL_TREE;
8989 }
8990
8991 /* Fold function call to builtin signbit, signbitf or signbitl with argument
8992 ARG. Return NULL_TREE if no simplification can be made. */
8993
8994 static tree
8995 fold_builtin_signbit (location_t loc, tree arg, tree type)
8996 {
8997 tree temp;
8998
8999 if (!validate_arg (arg, REAL_TYPE))
9000 return NULL_TREE;
9001
9002 /* If ARG is a compile-time constant, determine the result. */
9003 if (TREE_CODE (arg) == REAL_CST
9004 && !TREE_OVERFLOW (arg))
9005 {
9006 REAL_VALUE_TYPE c;
9007
9008 c = TREE_REAL_CST (arg);
9009 temp = REAL_VALUE_NEGATIVE (c) ? integer_one_node : integer_zero_node;
9010 return fold_convert_loc (loc, type, temp);
9011 }
9012
9013 /* If ARG is non-negative, the result is always zero. */
9014 if (tree_expr_nonnegative_p (arg))
9015 return omit_one_operand_loc (loc, type, integer_zero_node, arg);
9016
9017 /* If ARG's format doesn't have signed zeros, return "arg < 0.0". */
9018 if (!HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg))))
9019 return fold_build2_loc (loc, LT_EXPR, type, arg,
9020 build_real (TREE_TYPE (arg), dconst0));
9021
9022 return NULL_TREE;
9023 }
9024
9025 /* Fold function call to builtin copysign, copysignf or copysignl with
9026 arguments ARG1 and ARG2. Return NULL_TREE if no simplification can
9027 be made. */
9028
9029 static tree
9030 fold_builtin_copysign (location_t loc, tree fndecl,
9031 tree arg1, tree arg2, tree type)
9032 {
9033 tree tem;
9034
9035 if (!validate_arg (arg1, REAL_TYPE)
9036 || !validate_arg (arg2, REAL_TYPE))
9037 return NULL_TREE;
9038
9039 /* copysign(X,X) is X. */
9040 if (operand_equal_p (arg1, arg2, 0))
9041 return fold_convert_loc (loc, type, arg1);
9042
9043 /* If ARG1 and ARG2 are compile-time constants, determine the result. */
9044 if (TREE_CODE (arg1) == REAL_CST
9045 && TREE_CODE (arg2) == REAL_CST
9046 && !TREE_OVERFLOW (arg1)
9047 && !TREE_OVERFLOW (arg2))
9048 {
9049 REAL_VALUE_TYPE c1, c2;
9050
9051 c1 = TREE_REAL_CST (arg1);
9052 c2 = TREE_REAL_CST (arg2);
9053 /* c1.sign := c2.sign. */
9054 real_copysign (&c1, &c2);
9055 return build_real (type, c1);
9056 }
9057
9058 /* copysign(X, Y) is fabs(X) when Y is always non-negative.
9059 Remember to evaluate Y for side-effects. */
9060 if (tree_expr_nonnegative_p (arg2))
9061 return omit_one_operand_loc (loc, type,
9062 fold_build1_loc (loc, ABS_EXPR, type, arg1),
9063 arg2);
9064
9065 /* Strip sign changing operations for the first argument. */
9066 tem = fold_strip_sign_ops (arg1);
9067 if (tem)
9068 return build_call_expr_loc (loc, fndecl, 2, tem, arg2);
9069
9070 return NULL_TREE;
9071 }
9072
9073 /* Fold a call to builtin isascii with argument ARG. */
9074
9075 static tree
9076 fold_builtin_isascii (location_t loc, tree arg)
9077 {
9078 if (!validate_arg (arg, INTEGER_TYPE))
9079 return NULL_TREE;
9080 else
9081 {
9082 /* Transform isascii(c) -> ((c & ~0x7f) == 0). */
9083 arg = fold_build2 (BIT_AND_EXPR, integer_type_node, arg,
9084 build_int_cst (NULL_TREE,
9085 ~ (unsigned HOST_WIDE_INT) 0x7f));
9086 return fold_build2_loc (loc, EQ_EXPR, integer_type_node,
9087 arg, integer_zero_node);
9088 }
9089 }
9090
9091 /* Fold a call to builtin toascii with argument ARG. */
9092
9093 static tree
9094 fold_builtin_toascii (location_t loc, tree arg)
9095 {
9096 if (!validate_arg (arg, INTEGER_TYPE))
9097 return NULL_TREE;
9098
9099 /* Transform toascii(c) -> (c & 0x7f). */
9100 return fold_build2_loc (loc, BIT_AND_EXPR, integer_type_node, arg,
9101 build_int_cst (NULL_TREE, 0x7f));
9102 }
9103
9104 /* Fold a call to builtin isdigit with argument ARG. */
9105
9106 static tree
9107 fold_builtin_isdigit (location_t loc, tree arg)
9108 {
9109 if (!validate_arg (arg, INTEGER_TYPE))
9110 return NULL_TREE;
9111 else
9112 {
9113 /* Transform isdigit(c) -> (unsigned)(c) - '0' <= 9. */
9114 /* According to the C standard, isdigit is unaffected by locale.
9115 However, it definitely is affected by the target character set. */
9116 unsigned HOST_WIDE_INT target_digit0
9117 = lang_hooks.to_target_charset ('0');
9118
9119 if (target_digit0 == 0)
9120 return NULL_TREE;
9121
9122 arg = fold_convert_loc (loc, unsigned_type_node, arg);
9123 arg = fold_build2 (MINUS_EXPR, unsigned_type_node, arg,
9124 build_int_cst (unsigned_type_node, target_digit0));
9125 return fold_build2_loc (loc, LE_EXPR, integer_type_node, arg,
9126 build_int_cst (unsigned_type_node, 9));
9127 }
9128 }
9129
9130 /* Fold a call to fabs, fabsf or fabsl with argument ARG. */
9131
9132 static tree
9133 fold_builtin_fabs (location_t loc, tree arg, tree type)
9134 {
9135 if (!validate_arg (arg, REAL_TYPE))
9136 return NULL_TREE;
9137
9138 arg = fold_convert_loc (loc, type, arg);
9139 if (TREE_CODE (arg) == REAL_CST)
9140 return fold_abs_const (arg, type);
9141 return fold_build1_loc (loc, ABS_EXPR, type, arg);
9142 }
9143
9144 /* Fold a call to abs, labs, llabs or imaxabs with argument ARG. */
9145
9146 static tree
9147 fold_builtin_abs (location_t loc, tree arg, tree type)
9148 {
9149 if (!validate_arg (arg, INTEGER_TYPE))
9150 return NULL_TREE;
9151
9152 arg = fold_convert_loc (loc, type, arg);
9153 if (TREE_CODE (arg) == INTEGER_CST)
9154 return fold_abs_const (arg, type);
9155 return fold_build1_loc (loc, ABS_EXPR, type, arg);
9156 }
9157
9158 /* Fold a call to builtin fmin or fmax. */
9159
9160 static tree
9161 fold_builtin_fmin_fmax (location_t loc, tree arg0, tree arg1,
9162 tree type, bool max)
9163 {
9164 if (validate_arg (arg0, REAL_TYPE) && validate_arg (arg1, REAL_TYPE))
9165 {
9166 /* Calculate the result when the argument is a constant. */
9167 tree res = do_mpfr_arg2 (arg0, arg1, type, (max ? mpfr_max : mpfr_min));
9168
9169 if (res)
9170 return res;
9171
9172 /* If either argument is NaN, return the other one. Avoid the
9173 transformation if we get (and honor) a signalling NaN. Using
9174 omit_one_operand() ensures we create a non-lvalue. */
9175 if (TREE_CODE (arg0) == REAL_CST
9176 && real_isnan (&TREE_REAL_CST (arg0))
9177 && (! HONOR_SNANS (TYPE_MODE (TREE_TYPE (arg0)))
9178 || ! TREE_REAL_CST (arg0).signalling))
9179 return omit_one_operand_loc (loc, type, arg1, arg0);
9180 if (TREE_CODE (arg1) == REAL_CST
9181 && real_isnan (&TREE_REAL_CST (arg1))
9182 && (! HONOR_SNANS (TYPE_MODE (TREE_TYPE (arg1)))
9183 || ! TREE_REAL_CST (arg1).signalling))
9184 return omit_one_operand_loc (loc, type, arg0, arg1);
9185
9186 /* Transform fmin/fmax(x,x) -> x. */
9187 if (operand_equal_p (arg0, arg1, OEP_PURE_SAME))
9188 return omit_one_operand_loc (loc, type, arg0, arg1);
9189
9190 /* Convert fmin/fmax to MIN_EXPR/MAX_EXPR. C99 requires these
9191 functions to return the numeric arg if the other one is NaN.
9192 These tree codes don't honor that, so only transform if
9193 -ffinite-math-only is set. C99 doesn't require -0.0 to be
9194 handled, so we don't have to worry about it either. */
9195 if (flag_finite_math_only)
9196 return fold_build2_loc (loc, (max ? MAX_EXPR : MIN_EXPR), type,
9197 fold_convert_loc (loc, type, arg0),
9198 fold_convert_loc (loc, type, arg1));
9199 }
9200 return NULL_TREE;
9201 }
9202
9203 /* Fold a call to builtin carg(a+bi) -> atan2(b,a). */
9204
9205 static tree
9206 fold_builtin_carg (location_t loc, tree arg, tree type)
9207 {
9208 if (validate_arg (arg, COMPLEX_TYPE)
9209 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) == REAL_TYPE)
9210 {
9211 tree atan2_fn = mathfn_built_in (type, BUILT_IN_ATAN2);
9212
9213 if (atan2_fn)
9214 {
9215 tree new_arg = builtin_save_expr (arg);
9216 tree r_arg = fold_build1_loc (loc, REALPART_EXPR, type, new_arg);
9217 tree i_arg = fold_build1_loc (loc, IMAGPART_EXPR, type, new_arg);
9218 return build_call_expr_loc (loc, atan2_fn, 2, i_arg, r_arg);
9219 }
9220 }
9221
9222 return NULL_TREE;
9223 }
9224
9225 /* Fold a call to builtin logb/ilogb. */
9226
9227 static tree
9228 fold_builtin_logb (location_t loc, tree arg, tree rettype)
9229 {
9230 if (! validate_arg (arg, REAL_TYPE))
9231 return NULL_TREE;
9232
9233 STRIP_NOPS (arg);
9234
9235 if (TREE_CODE (arg) == REAL_CST && ! TREE_OVERFLOW (arg))
9236 {
9237 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg);
9238
9239 switch (value->cl)
9240 {
9241 case rvc_nan:
9242 case rvc_inf:
9243 /* If arg is Inf or NaN and we're logb, return it. */
9244 if (TREE_CODE (rettype) == REAL_TYPE)
9245 return fold_convert_loc (loc, rettype, arg);
9246 /* Fall through... */
9247 case rvc_zero:
9248 /* Zero may set errno and/or raise an exception for logb, also
9249 for ilogb we don't know FP_ILOGB0. */
9250 return NULL_TREE;
9251 case rvc_normal:
9252 /* For normal numbers, proceed iff radix == 2. In GCC,
9253 normalized significands are in the range [0.5, 1.0). We
9254 want the exponent as if they were [1.0, 2.0) so get the
9255 exponent and subtract 1. */
9256 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (arg)))->b == 2)
9257 return fold_convert_loc (loc, rettype,
9258 build_int_cst (NULL_TREE,
9259 REAL_EXP (value)-1));
9260 break;
9261 }
9262 }
9263
9264 return NULL_TREE;
9265 }
9266
9267 /* Fold a call to builtin significand, if radix == 2. */
9268
9269 static tree
9270 fold_builtin_significand (location_t loc, tree arg, tree rettype)
9271 {
9272 if (! validate_arg (arg, REAL_TYPE))
9273 return NULL_TREE;
9274
9275 STRIP_NOPS (arg);
9276
9277 if (TREE_CODE (arg) == REAL_CST && ! TREE_OVERFLOW (arg))
9278 {
9279 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg);
9280
9281 switch (value->cl)
9282 {
9283 case rvc_zero:
9284 case rvc_nan:
9285 case rvc_inf:
9286 /* If arg is +-0, +-Inf or +-NaN, then return it. */
9287 return fold_convert_loc (loc, rettype, arg);
9288 case rvc_normal:
9289 /* For normal numbers, proceed iff radix == 2. */
9290 if (REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (arg)))->b == 2)
9291 {
9292 REAL_VALUE_TYPE result = *value;
9293 /* In GCC, normalized significands are in the range [0.5,
9294 1.0). We want them to be [1.0, 2.0) so set the
9295 exponent to 1. */
9296 SET_REAL_EXP (&result, 1);
9297 return build_real (rettype, result);
9298 }
9299 break;
9300 }
9301 }
9302
9303 return NULL_TREE;
9304 }
9305
9306 /* Fold a call to builtin frexp, we can assume the base is 2. */
9307
9308 static tree
9309 fold_builtin_frexp (location_t loc, tree arg0, tree arg1, tree rettype)
9310 {
9311 if (! validate_arg (arg0, REAL_TYPE) || ! validate_arg (arg1, POINTER_TYPE))
9312 return NULL_TREE;
9313
9314 STRIP_NOPS (arg0);
9315
9316 if (!(TREE_CODE (arg0) == REAL_CST && ! TREE_OVERFLOW (arg0)))
9317 return NULL_TREE;
9318
9319 arg1 = build_fold_indirect_ref_loc (loc, arg1);
9320
9321 /* Proceed if a valid pointer type was passed in. */
9322 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg1)) == integer_type_node)
9323 {
9324 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg0);
9325 tree frac, exp;
9326
9327 switch (value->cl)
9328 {
9329 case rvc_zero:
9330 /* For +-0, return (*exp = 0, +-0). */
9331 exp = integer_zero_node;
9332 frac = arg0;
9333 break;
9334 case rvc_nan:
9335 case rvc_inf:
9336 /* For +-NaN or +-Inf, *exp is unspecified, return arg0. */
9337 return omit_one_operand_loc (loc, rettype, arg0, arg1);
9338 case rvc_normal:
9339 {
9340 /* Since the frexp function always expects base 2, and in
9341 GCC normalized significands are already in the range
9342 [0.5, 1.0), we have exactly what frexp wants. */
9343 REAL_VALUE_TYPE frac_rvt = *value;
9344 SET_REAL_EXP (&frac_rvt, 0);
9345 frac = build_real (rettype, frac_rvt);
9346 exp = build_int_cst (NULL_TREE, REAL_EXP (value));
9347 }
9348 break;
9349 default:
9350 gcc_unreachable ();
9351 }
9352
9353 /* Create the COMPOUND_EXPR (*arg1 = trunc, frac). */
9354 arg1 = fold_build2_loc (loc, MODIFY_EXPR, rettype, arg1, exp);
9355 TREE_SIDE_EFFECTS (arg1) = 1;
9356 return fold_build2_loc (loc, COMPOUND_EXPR, rettype, arg1, frac);
9357 }
9358
9359 return NULL_TREE;
9360 }
9361
9362 /* Fold a call to builtin ldexp or scalbn/scalbln. If LDEXP is true
9363 then we can assume the base is two. If it's false, then we have to
9364 check the mode of the TYPE parameter in certain cases. */
9365
9366 static tree
9367 fold_builtin_load_exponent (location_t loc, tree arg0, tree arg1,
9368 tree type, bool ldexp)
9369 {
9370 if (validate_arg (arg0, REAL_TYPE) && validate_arg (arg1, INTEGER_TYPE))
9371 {
9372 STRIP_NOPS (arg0);
9373 STRIP_NOPS (arg1);
9374
9375 /* If arg0 is 0, Inf or NaN, or if arg1 is 0, then return arg0. */
9376 if (real_zerop (arg0) || integer_zerop (arg1)
9377 || (TREE_CODE (arg0) == REAL_CST
9378 && !real_isfinite (&TREE_REAL_CST (arg0))))
9379 return omit_one_operand_loc (loc, type, arg0, arg1);
9380
9381 /* If both arguments are constant, then try to evaluate it. */
9382 if ((ldexp || REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2)
9383 && TREE_CODE (arg0) == REAL_CST && !TREE_OVERFLOW (arg0)
9384 && host_integerp (arg1, 0))
9385 {
9386 /* Bound the maximum adjustment to twice the range of the
9387 mode's valid exponents. Use abs to ensure the range is
9388 positive as a sanity check. */
9389 const long max_exp_adj = 2 *
9390 labs (REAL_MODE_FORMAT (TYPE_MODE (type))->emax
9391 - REAL_MODE_FORMAT (TYPE_MODE (type))->emin);
9392
9393 /* Get the user-requested adjustment. */
9394 const HOST_WIDE_INT req_exp_adj = tree_low_cst (arg1, 0);
9395
9396 /* The requested adjustment must be inside this range. This
9397 is a preliminary cap to avoid things like overflow, we
9398 may still fail to compute the result for other reasons. */
9399 if (-max_exp_adj < req_exp_adj && req_exp_adj < max_exp_adj)
9400 {
9401 REAL_VALUE_TYPE initial_result;
9402
9403 real_ldexp (&initial_result, &TREE_REAL_CST (arg0), req_exp_adj);
9404
9405 /* Ensure we didn't overflow. */
9406 if (! real_isinf (&initial_result))
9407 {
9408 const REAL_VALUE_TYPE trunc_result
9409 = real_value_truncate (TYPE_MODE (type), initial_result);
9410
9411 /* Only proceed if the target mode can hold the
9412 resulting value. */
9413 if (REAL_VALUES_EQUAL (initial_result, trunc_result))
9414 return build_real (type, trunc_result);
9415 }
9416 }
9417 }
9418 }
9419
9420 return NULL_TREE;
9421 }
9422
9423 /* Fold a call to builtin modf. */
9424
9425 static tree
9426 fold_builtin_modf (location_t loc, tree arg0, tree arg1, tree rettype)
9427 {
9428 if (! validate_arg (arg0, REAL_TYPE) || ! validate_arg (arg1, POINTER_TYPE))
9429 return NULL_TREE;
9430
9431 STRIP_NOPS (arg0);
9432
9433 if (!(TREE_CODE (arg0) == REAL_CST && ! TREE_OVERFLOW (arg0)))
9434 return NULL_TREE;
9435
9436 arg1 = build_fold_indirect_ref_loc (loc, arg1);
9437
9438 /* Proceed if a valid pointer type was passed in. */
9439 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg1)) == TYPE_MAIN_VARIANT (rettype))
9440 {
9441 const REAL_VALUE_TYPE *const value = TREE_REAL_CST_PTR (arg0);
9442 REAL_VALUE_TYPE trunc, frac;
9443
9444 switch (value->cl)
9445 {
9446 case rvc_nan:
9447 case rvc_zero:
9448 /* For +-NaN or +-0, return (*arg1 = arg0, arg0). */
9449 trunc = frac = *value;
9450 break;
9451 case rvc_inf:
9452 /* For +-Inf, return (*arg1 = arg0, +-0). */
9453 frac = dconst0;
9454 frac.sign = value->sign;
9455 trunc = *value;
9456 break;
9457 case rvc_normal:
9458 /* Return (*arg1 = trunc(arg0), arg0-trunc(arg0)). */
9459 real_trunc (&trunc, VOIDmode, value);
9460 real_arithmetic (&frac, MINUS_EXPR, value, &trunc);
9461 /* If the original number was negative and already
9462 integral, then the fractional part is -0.0. */
9463 if (value->sign && frac.cl == rvc_zero)
9464 frac.sign = value->sign;
9465 break;
9466 }
9467
9468 /* Create the COMPOUND_EXPR (*arg1 = trunc, frac). */
9469 arg1 = fold_build2_loc (loc, MODIFY_EXPR, rettype, arg1,
9470 build_real (rettype, trunc));
9471 TREE_SIDE_EFFECTS (arg1) = 1;
9472 return fold_build2_loc (loc, COMPOUND_EXPR, rettype, arg1,
9473 build_real (rettype, frac));
9474 }
9475
9476 return NULL_TREE;
9477 }
9478
9479 /* Given a location LOC, an interclass builtin function decl FNDECL
9480 and its single argument ARG, return an folded expression computing
9481 the same, or NULL_TREE if we either couldn't or didn't want to fold
9482 (the latter happen if there's an RTL instruction available). */
9483
9484 static tree
9485 fold_builtin_interclass_mathfn (location_t loc, tree fndecl, tree arg)
9486 {
9487 enum machine_mode mode;
9488
9489 if (!validate_arg (arg, REAL_TYPE))
9490 return NULL_TREE;
9491
9492 if (interclass_mathfn_icode (arg, fndecl) != CODE_FOR_nothing)
9493 return NULL_TREE;
9494
9495 mode = TYPE_MODE (TREE_TYPE (arg));
9496
9497 /* If there is no optab, try generic code. */
9498 switch (DECL_FUNCTION_CODE (fndecl))
9499 {
9500 tree result;
9501
9502 CASE_FLT_FN (BUILT_IN_ISINF):
9503 {
9504 /* isinf(x) -> isgreater(fabs(x),DBL_MAX). */
9505 tree const isgr_fn = built_in_decls[BUILT_IN_ISGREATER];
9506 tree const type = TREE_TYPE (arg);
9507 REAL_VALUE_TYPE r;
9508 char buf[128];
9509
9510 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
9511 real_from_string (&r, buf);
9512 result = build_call_expr (isgr_fn, 2,
9513 fold_build1_loc (loc, ABS_EXPR, type, arg),
9514 build_real (type, r));
9515 return result;
9516 }
9517 CASE_FLT_FN (BUILT_IN_FINITE):
9518 case BUILT_IN_ISFINITE:
9519 {
9520 /* isfinite(x) -> islessequal(fabs(x),DBL_MAX). */
9521 tree const isle_fn = built_in_decls[BUILT_IN_ISLESSEQUAL];
9522 tree const type = TREE_TYPE (arg);
9523 REAL_VALUE_TYPE r;
9524 char buf[128];
9525
9526 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
9527 real_from_string (&r, buf);
9528 result = build_call_expr (isle_fn, 2,
9529 fold_build1_loc (loc, ABS_EXPR, type, arg),
9530 build_real (type, r));
9531 /*result = fold_build2_loc (loc, UNGT_EXPR,
9532 TREE_TYPE (TREE_TYPE (fndecl)),
9533 fold_build1_loc (loc, ABS_EXPR, type, arg),
9534 build_real (type, r));
9535 result = fold_build1_loc (loc, TRUTH_NOT_EXPR,
9536 TREE_TYPE (TREE_TYPE (fndecl)),
9537 result);*/
9538 return result;
9539 }
9540 case BUILT_IN_ISNORMAL:
9541 {
9542 /* isnormal(x) -> isgreaterequal(fabs(x),DBL_MIN) &
9543 islessequal(fabs(x),DBL_MAX). */
9544 tree const isle_fn = built_in_decls[BUILT_IN_ISLESSEQUAL];
9545 tree const isge_fn = built_in_decls[BUILT_IN_ISGREATEREQUAL];
9546 tree const type = TREE_TYPE (arg);
9547 REAL_VALUE_TYPE rmax, rmin;
9548 char buf[128];
9549
9550 get_max_float (REAL_MODE_FORMAT (mode), buf, sizeof (buf));
9551 real_from_string (&rmax, buf);
9552 sprintf (buf, "0x1p%d", REAL_MODE_FORMAT (mode)->emin - 1);
9553 real_from_string (&rmin, buf);
9554 arg = builtin_save_expr (fold_build1_loc (loc, ABS_EXPR, type, arg));
9555 result = build_call_expr (isle_fn, 2, arg,
9556 build_real (type, rmax));
9557 result = fold_build2 (BIT_AND_EXPR, integer_type_node, result,
9558 build_call_expr (isge_fn, 2, arg,
9559 build_real (type, rmin)));
9560 return result;
9561 }
9562 default:
9563 break;
9564 }
9565
9566 return NULL_TREE;
9567 }
9568
9569 /* Fold a call to __builtin_isnan(), __builtin_isinf, __builtin_finite.
9570 ARG is the argument for the call. */
9571
9572 static tree
9573 fold_builtin_classify (location_t loc, tree fndecl, tree arg, int builtin_index)
9574 {
9575 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9576 REAL_VALUE_TYPE r;
9577
9578 if (!validate_arg (arg, REAL_TYPE))
9579 return NULL_TREE;
9580
9581 switch (builtin_index)
9582 {
9583 case BUILT_IN_ISINF:
9584 if (!HONOR_INFINITIES (TYPE_MODE (TREE_TYPE (arg))))
9585 return omit_one_operand_loc (loc, type, integer_zero_node, arg);
9586
9587 if (TREE_CODE (arg) == REAL_CST)
9588 {
9589 r = TREE_REAL_CST (arg);
9590 if (real_isinf (&r))
9591 return real_compare (GT_EXPR, &r, &dconst0)
9592 ? integer_one_node : integer_minus_one_node;
9593 else
9594 return integer_zero_node;
9595 }
9596
9597 return NULL_TREE;
9598
9599 case BUILT_IN_ISINF_SIGN:
9600 {
9601 /* isinf_sign(x) -> isinf(x) ? (signbit(x) ? -1 : 1) : 0 */
9602 /* In a boolean context, GCC will fold the inner COND_EXPR to
9603 1. So e.g. "if (isinf_sign(x))" would be folded to just
9604 "if (isinf(x) ? 1 : 0)" which becomes "if (isinf(x))". */
9605 tree signbit_fn = mathfn_built_in_1 (TREE_TYPE (arg), BUILT_IN_SIGNBIT, 0);
9606 tree isinf_fn = built_in_decls[BUILT_IN_ISINF];
9607 tree tmp = NULL_TREE;
9608
9609 arg = builtin_save_expr (arg);
9610
9611 if (signbit_fn && isinf_fn)
9612 {
9613 tree signbit_call = build_call_expr_loc (loc, signbit_fn, 1, arg);
9614 tree isinf_call = build_call_expr_loc (loc, isinf_fn, 1, arg);
9615
9616 signbit_call = fold_build2_loc (loc, NE_EXPR, integer_type_node,
9617 signbit_call, integer_zero_node);
9618 isinf_call = fold_build2_loc (loc, NE_EXPR, integer_type_node,
9619 isinf_call, integer_zero_node);
9620
9621 tmp = fold_build3_loc (loc, COND_EXPR, integer_type_node, signbit_call,
9622 integer_minus_one_node, integer_one_node);
9623 tmp = fold_build3_loc (loc, COND_EXPR, integer_type_node,
9624 isinf_call, tmp,
9625 integer_zero_node);
9626 }
9627
9628 return tmp;
9629 }
9630
9631 case BUILT_IN_ISFINITE:
9632 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg)))
9633 && !HONOR_INFINITIES (TYPE_MODE (TREE_TYPE (arg))))
9634 return omit_one_operand_loc (loc, type, integer_one_node, arg);
9635
9636 if (TREE_CODE (arg) == REAL_CST)
9637 {
9638 r = TREE_REAL_CST (arg);
9639 return real_isfinite (&r) ? integer_one_node : integer_zero_node;
9640 }
9641
9642 return NULL_TREE;
9643
9644 case BUILT_IN_ISNAN:
9645 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg))))
9646 return omit_one_operand_loc (loc, type, integer_zero_node, arg);
9647
9648 if (TREE_CODE (arg) == REAL_CST)
9649 {
9650 r = TREE_REAL_CST (arg);
9651 return real_isnan (&r) ? integer_one_node : integer_zero_node;
9652 }
9653
9654 arg = builtin_save_expr (arg);
9655 return fold_build2_loc (loc, UNORDERED_EXPR, type, arg, arg);
9656
9657 default:
9658 gcc_unreachable ();
9659 }
9660 }
9661
9662 /* Fold a call to __builtin_fpclassify(int, int, int, int, int, ...).
9663 This builtin will generate code to return the appropriate floating
9664 point classification depending on the value of the floating point
9665 number passed in. The possible return values must be supplied as
9666 int arguments to the call in the following order: FP_NAN, FP_INFINITE,
9667 FP_NORMAL, FP_SUBNORMAL and FP_ZERO. The ellipses is for exactly
9668 one floating point argument which is "type generic". */
9669
9670 static tree
9671 fold_builtin_fpclassify (location_t loc, tree exp)
9672 {
9673 tree fp_nan, fp_infinite, fp_normal, fp_subnormal, fp_zero,
9674 arg, type, res, tmp;
9675 enum machine_mode mode;
9676 REAL_VALUE_TYPE r;
9677 char buf[128];
9678
9679 /* Verify the required arguments in the original call. */
9680 if (!validate_arglist (exp, INTEGER_TYPE, INTEGER_TYPE,
9681 INTEGER_TYPE, INTEGER_TYPE,
9682 INTEGER_TYPE, REAL_TYPE, VOID_TYPE))
9683 return NULL_TREE;
9684
9685 fp_nan = CALL_EXPR_ARG (exp, 0);
9686 fp_infinite = CALL_EXPR_ARG (exp, 1);
9687 fp_normal = CALL_EXPR_ARG (exp, 2);
9688 fp_subnormal = CALL_EXPR_ARG (exp, 3);
9689 fp_zero = CALL_EXPR_ARG (exp, 4);
9690 arg = CALL_EXPR_ARG (exp, 5);
9691 type = TREE_TYPE (arg);
9692 mode = TYPE_MODE (type);
9693 arg = builtin_save_expr (fold_build1_loc (loc, ABS_EXPR, type, arg));
9694
9695 /* fpclassify(x) ->
9696 isnan(x) ? FP_NAN :
9697 (fabs(x) == Inf ? FP_INFINITE :
9698 (fabs(x) >= DBL_MIN ? FP_NORMAL :
9699 (x == 0 ? FP_ZERO : FP_SUBNORMAL))). */
9700
9701 tmp = fold_build2_loc (loc, EQ_EXPR, integer_type_node, arg,
9702 build_real (type, dconst0));
9703 res = fold_build3_loc (loc, COND_EXPR, integer_type_node,
9704 tmp, fp_zero, fp_subnormal);
9705
9706 sprintf (buf, "0x1p%d", REAL_MODE_FORMAT (mode)->emin - 1);
9707 real_from_string (&r, buf);
9708 tmp = fold_build2_loc (loc, GE_EXPR, integer_type_node,
9709 arg, build_real (type, r));
9710 res = fold_build3_loc (loc, COND_EXPR, integer_type_node, tmp, fp_normal, res);
9711
9712 if (HONOR_INFINITIES (mode))
9713 {
9714 real_inf (&r);
9715 tmp = fold_build2_loc (loc, EQ_EXPR, integer_type_node, arg,
9716 build_real (type, r));
9717 res = fold_build3_loc (loc, COND_EXPR, integer_type_node, tmp,
9718 fp_infinite, res);
9719 }
9720
9721 if (HONOR_NANS (mode))
9722 {
9723 tmp = fold_build2_loc (loc, ORDERED_EXPR, integer_type_node, arg, arg);
9724 res = fold_build3_loc (loc, COND_EXPR, integer_type_node, tmp, res, fp_nan);
9725 }
9726
9727 return res;
9728 }
9729
9730 /* Fold a call to an unordered comparison function such as
9731 __builtin_isgreater(). FNDECL is the FUNCTION_DECL for the function
9732 being called and ARG0 and ARG1 are the arguments for the call.
9733 UNORDERED_CODE and ORDERED_CODE are comparison codes that give
9734 the opposite of the desired result. UNORDERED_CODE is used
9735 for modes that can hold NaNs and ORDERED_CODE is used for
9736 the rest. */
9737
9738 static tree
9739 fold_builtin_unordered_cmp (location_t loc, tree fndecl, tree arg0, tree arg1,
9740 enum tree_code unordered_code,
9741 enum tree_code ordered_code)
9742 {
9743 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9744 enum tree_code code;
9745 tree type0, type1;
9746 enum tree_code code0, code1;
9747 tree cmp_type = NULL_TREE;
9748
9749 type0 = TREE_TYPE (arg0);
9750 type1 = TREE_TYPE (arg1);
9751
9752 code0 = TREE_CODE (type0);
9753 code1 = TREE_CODE (type1);
9754
9755 if (code0 == REAL_TYPE && code1 == REAL_TYPE)
9756 /* Choose the wider of two real types. */
9757 cmp_type = TYPE_PRECISION (type0) >= TYPE_PRECISION (type1)
9758 ? type0 : type1;
9759 else if (code0 == REAL_TYPE && code1 == INTEGER_TYPE)
9760 cmp_type = type0;
9761 else if (code0 == INTEGER_TYPE && code1 == REAL_TYPE)
9762 cmp_type = type1;
9763
9764 arg0 = fold_convert_loc (loc, cmp_type, arg0);
9765 arg1 = fold_convert_loc (loc, cmp_type, arg1);
9766
9767 if (unordered_code == UNORDERED_EXPR)
9768 {
9769 if (!HONOR_NANS (TYPE_MODE (TREE_TYPE (arg0))))
9770 return omit_two_operands_loc (loc, type, integer_zero_node, arg0, arg1);
9771 return fold_build2_loc (loc, UNORDERED_EXPR, type, arg0, arg1);
9772 }
9773
9774 code = HONOR_NANS (TYPE_MODE (TREE_TYPE (arg0))) ? unordered_code
9775 : ordered_code;
9776 return fold_build1_loc (loc, TRUTH_NOT_EXPR, type,
9777 fold_build2_loc (loc, code, type, arg0, arg1));
9778 }
9779
9780 /* Fold a call to built-in function FNDECL with 0 arguments.
9781 IGNORE is true if the result of the function call is ignored. This
9782 function returns NULL_TREE if no simplification was possible. */
9783
9784 static tree
9785 fold_builtin_0 (location_t loc, tree fndecl, bool ignore ATTRIBUTE_UNUSED)
9786 {
9787 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9788 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
9789 switch (fcode)
9790 {
9791 CASE_FLT_FN (BUILT_IN_INF):
9792 case BUILT_IN_INFD32:
9793 case BUILT_IN_INFD64:
9794 case BUILT_IN_INFD128:
9795 return fold_builtin_inf (loc, type, true);
9796
9797 CASE_FLT_FN (BUILT_IN_HUGE_VAL):
9798 return fold_builtin_inf (loc, type, false);
9799
9800 case BUILT_IN_CLASSIFY_TYPE:
9801 return fold_builtin_classify_type (NULL_TREE);
9802
9803 default:
9804 break;
9805 }
9806 return NULL_TREE;
9807 }
9808
9809 /* Fold a call to built-in function FNDECL with 1 argument, ARG0.
9810 IGNORE is true if the result of the function call is ignored. This
9811 function returns NULL_TREE if no simplification was possible. */
9812
9813 static tree
9814 fold_builtin_1 (location_t loc, tree fndecl, tree arg0, bool ignore)
9815 {
9816 tree type = TREE_TYPE (TREE_TYPE (fndecl));
9817 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
9818 switch (fcode)
9819 {
9820 case BUILT_IN_CONSTANT_P:
9821 {
9822 tree val = fold_builtin_constant_p (arg0);
9823
9824 /* Gimplification will pull the CALL_EXPR for the builtin out of
9825 an if condition. When not optimizing, we'll not CSE it back.
9826 To avoid link error types of regressions, return false now. */
9827 if (!val && !optimize)
9828 val = integer_zero_node;
9829
9830 return val;
9831 }
9832
9833 case BUILT_IN_CLASSIFY_TYPE:
9834 return fold_builtin_classify_type (arg0);
9835
9836 case BUILT_IN_STRLEN:
9837 return fold_builtin_strlen (loc, type, arg0);
9838
9839 CASE_FLT_FN (BUILT_IN_FABS):
9840 return fold_builtin_fabs (loc, arg0, type);
9841
9842 case BUILT_IN_ABS:
9843 case BUILT_IN_LABS:
9844 case BUILT_IN_LLABS:
9845 case BUILT_IN_IMAXABS:
9846 return fold_builtin_abs (loc, arg0, type);
9847
9848 CASE_FLT_FN (BUILT_IN_CONJ):
9849 if (validate_arg (arg0, COMPLEX_TYPE)
9850 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9851 return fold_build1_loc (loc, CONJ_EXPR, type, arg0);
9852 break;
9853
9854 CASE_FLT_FN (BUILT_IN_CREAL):
9855 if (validate_arg (arg0, COMPLEX_TYPE)
9856 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9857 return non_lvalue_loc (loc, fold_build1_loc (loc, REALPART_EXPR, type, arg0));;
9858 break;
9859
9860 CASE_FLT_FN (BUILT_IN_CIMAG):
9861 if (validate_arg (arg0, COMPLEX_TYPE)
9862 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9863 return non_lvalue_loc (loc, fold_build1_loc (loc, IMAGPART_EXPR, type, arg0));
9864 break;
9865
9866 CASE_FLT_FN (BUILT_IN_CCOS):
9867 return fold_builtin_ccos(loc, arg0, type, fndecl, /*hyper=*/ false);
9868
9869 CASE_FLT_FN (BUILT_IN_CCOSH):
9870 return fold_builtin_ccos(loc, arg0, type, fndecl, /*hyper=*/ true);
9871
9872 CASE_FLT_FN (BUILT_IN_CPROJ):
9873 return fold_builtin_cproj(loc, arg0, type);
9874
9875 CASE_FLT_FN (BUILT_IN_CSIN):
9876 if (validate_arg (arg0, COMPLEX_TYPE)
9877 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9878 return do_mpc_arg1 (arg0, type, mpc_sin);
9879 break;
9880
9881 CASE_FLT_FN (BUILT_IN_CSINH):
9882 if (validate_arg (arg0, COMPLEX_TYPE)
9883 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9884 return do_mpc_arg1 (arg0, type, mpc_sinh);
9885 break;
9886
9887 CASE_FLT_FN (BUILT_IN_CTAN):
9888 if (validate_arg (arg0, COMPLEX_TYPE)
9889 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9890 return do_mpc_arg1 (arg0, type, mpc_tan);
9891 break;
9892
9893 CASE_FLT_FN (BUILT_IN_CTANH):
9894 if (validate_arg (arg0, COMPLEX_TYPE)
9895 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9896 return do_mpc_arg1 (arg0, type, mpc_tanh);
9897 break;
9898
9899 CASE_FLT_FN (BUILT_IN_CLOG):
9900 if (validate_arg (arg0, COMPLEX_TYPE)
9901 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9902 return do_mpc_arg1 (arg0, type, mpc_log);
9903 break;
9904
9905 CASE_FLT_FN (BUILT_IN_CSQRT):
9906 if (validate_arg (arg0, COMPLEX_TYPE)
9907 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9908 return do_mpc_arg1 (arg0, type, mpc_sqrt);
9909 break;
9910
9911 CASE_FLT_FN (BUILT_IN_CASIN):
9912 if (validate_arg (arg0, COMPLEX_TYPE)
9913 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9914 return do_mpc_arg1 (arg0, type, mpc_asin);
9915 break;
9916
9917 CASE_FLT_FN (BUILT_IN_CACOS):
9918 if (validate_arg (arg0, COMPLEX_TYPE)
9919 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9920 return do_mpc_arg1 (arg0, type, mpc_acos);
9921 break;
9922
9923 CASE_FLT_FN (BUILT_IN_CATAN):
9924 if (validate_arg (arg0, COMPLEX_TYPE)
9925 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9926 return do_mpc_arg1 (arg0, type, mpc_atan);
9927 break;
9928
9929 CASE_FLT_FN (BUILT_IN_CASINH):
9930 if (validate_arg (arg0, COMPLEX_TYPE)
9931 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9932 return do_mpc_arg1 (arg0, type, mpc_asinh);
9933 break;
9934
9935 CASE_FLT_FN (BUILT_IN_CACOSH):
9936 if (validate_arg (arg0, COMPLEX_TYPE)
9937 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9938 return do_mpc_arg1 (arg0, type, mpc_acosh);
9939 break;
9940
9941 CASE_FLT_FN (BUILT_IN_CATANH):
9942 if (validate_arg (arg0, COMPLEX_TYPE)
9943 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE)
9944 return do_mpc_arg1 (arg0, type, mpc_atanh);
9945 break;
9946
9947 CASE_FLT_FN (BUILT_IN_CABS):
9948 return fold_builtin_cabs (loc, arg0, type, fndecl);
9949
9950 CASE_FLT_FN (BUILT_IN_CARG):
9951 return fold_builtin_carg (loc, arg0, type);
9952
9953 CASE_FLT_FN (BUILT_IN_SQRT):
9954 return fold_builtin_sqrt (loc, arg0, type);
9955
9956 CASE_FLT_FN (BUILT_IN_CBRT):
9957 return fold_builtin_cbrt (loc, arg0, type);
9958
9959 CASE_FLT_FN (BUILT_IN_ASIN):
9960 if (validate_arg (arg0, REAL_TYPE))
9961 return do_mpfr_arg1 (arg0, type, mpfr_asin,
9962 &dconstm1, &dconst1, true);
9963 break;
9964
9965 CASE_FLT_FN (BUILT_IN_ACOS):
9966 if (validate_arg (arg0, REAL_TYPE))
9967 return do_mpfr_arg1 (arg0, type, mpfr_acos,
9968 &dconstm1, &dconst1, true);
9969 break;
9970
9971 CASE_FLT_FN (BUILT_IN_ATAN):
9972 if (validate_arg (arg0, REAL_TYPE))
9973 return do_mpfr_arg1 (arg0, type, mpfr_atan, NULL, NULL, 0);
9974 break;
9975
9976 CASE_FLT_FN (BUILT_IN_ASINH):
9977 if (validate_arg (arg0, REAL_TYPE))
9978 return do_mpfr_arg1 (arg0, type, mpfr_asinh, NULL, NULL, 0);
9979 break;
9980
9981 CASE_FLT_FN (BUILT_IN_ACOSH):
9982 if (validate_arg (arg0, REAL_TYPE))
9983 return do_mpfr_arg1 (arg0, type, mpfr_acosh,
9984 &dconst1, NULL, true);
9985 break;
9986
9987 CASE_FLT_FN (BUILT_IN_ATANH):
9988 if (validate_arg (arg0, REAL_TYPE))
9989 return do_mpfr_arg1 (arg0, type, mpfr_atanh,
9990 &dconstm1, &dconst1, false);
9991 break;
9992
9993 CASE_FLT_FN (BUILT_IN_SIN):
9994 if (validate_arg (arg0, REAL_TYPE))
9995 return do_mpfr_arg1 (arg0, type, mpfr_sin, NULL, NULL, 0);
9996 break;
9997
9998 CASE_FLT_FN (BUILT_IN_COS):
9999 return fold_builtin_cos (loc, arg0, type, fndecl);
10000
10001 CASE_FLT_FN (BUILT_IN_TAN):
10002 return fold_builtin_tan (arg0, type);
10003
10004 CASE_FLT_FN (BUILT_IN_CEXP):
10005 return fold_builtin_cexp (loc, arg0, type);
10006
10007 CASE_FLT_FN (BUILT_IN_CEXPI):
10008 if (validate_arg (arg0, REAL_TYPE))
10009 return do_mpfr_sincos (arg0, NULL_TREE, NULL_TREE);
10010 break;
10011
10012 CASE_FLT_FN (BUILT_IN_SINH):
10013 if (validate_arg (arg0, REAL_TYPE))
10014 return do_mpfr_arg1 (arg0, type, mpfr_sinh, NULL, NULL, 0);
10015 break;
10016
10017 CASE_FLT_FN (BUILT_IN_COSH):
10018 return fold_builtin_cosh (loc, arg0, type, fndecl);
10019
10020 CASE_FLT_FN (BUILT_IN_TANH):
10021 if (validate_arg (arg0, REAL_TYPE))
10022 return do_mpfr_arg1 (arg0, type, mpfr_tanh, NULL, NULL, 0);
10023 break;
10024
10025 CASE_FLT_FN (BUILT_IN_ERF):
10026 if (validate_arg (arg0, REAL_TYPE))
10027 return do_mpfr_arg1 (arg0, type, mpfr_erf, NULL, NULL, 0);
10028 break;
10029
10030 CASE_FLT_FN (BUILT_IN_ERFC):
10031 if (validate_arg (arg0, REAL_TYPE))
10032 return do_mpfr_arg1 (arg0, type, mpfr_erfc, NULL, NULL, 0);
10033 break;
10034
10035 CASE_FLT_FN (BUILT_IN_TGAMMA):
10036 if (validate_arg (arg0, REAL_TYPE))
10037 return do_mpfr_arg1 (arg0, type, mpfr_gamma, NULL, NULL, 0);
10038 break;
10039
10040 CASE_FLT_FN (BUILT_IN_EXP):
10041 return fold_builtin_exponent (loc, fndecl, arg0, mpfr_exp);
10042
10043 CASE_FLT_FN (BUILT_IN_EXP2):
10044 return fold_builtin_exponent (loc, fndecl, arg0, mpfr_exp2);
10045
10046 CASE_FLT_FN (BUILT_IN_EXP10):
10047 CASE_FLT_FN (BUILT_IN_POW10):
10048 return fold_builtin_exponent (loc, fndecl, arg0, mpfr_exp10);
10049
10050 CASE_FLT_FN (BUILT_IN_EXPM1):
10051 if (validate_arg (arg0, REAL_TYPE))
10052 return do_mpfr_arg1 (arg0, type, mpfr_expm1, NULL, NULL, 0);
10053 break;
10054
10055 CASE_FLT_FN (BUILT_IN_LOG):
10056 return fold_builtin_logarithm (loc, fndecl, arg0, mpfr_log);
10057
10058 CASE_FLT_FN (BUILT_IN_LOG2):
10059 return fold_builtin_logarithm (loc, fndecl, arg0, mpfr_log2);
10060
10061 CASE_FLT_FN (BUILT_IN_LOG10):
10062 return fold_builtin_logarithm (loc, fndecl, arg0, mpfr_log10);
10063
10064 CASE_FLT_FN (BUILT_IN_LOG1P):
10065 if (validate_arg (arg0, REAL_TYPE))
10066 return do_mpfr_arg1 (arg0, type, mpfr_log1p,
10067 &dconstm1, NULL, false);
10068 break;
10069
10070 CASE_FLT_FN (BUILT_IN_J0):
10071 if (validate_arg (arg0, REAL_TYPE))
10072 return do_mpfr_arg1 (arg0, type, mpfr_j0,
10073 NULL, NULL, 0);
10074 break;
10075
10076 CASE_FLT_FN (BUILT_IN_J1):
10077 if (validate_arg (arg0, REAL_TYPE))
10078 return do_mpfr_arg1 (arg0, type, mpfr_j1,
10079 NULL, NULL, 0);
10080 break;
10081
10082 CASE_FLT_FN (BUILT_IN_Y0):
10083 if (validate_arg (arg0, REAL_TYPE))
10084 return do_mpfr_arg1 (arg0, type, mpfr_y0,
10085 &dconst0, NULL, false);
10086 break;
10087
10088 CASE_FLT_FN (BUILT_IN_Y1):
10089 if (validate_arg (arg0, REAL_TYPE))
10090 return do_mpfr_arg1 (arg0, type, mpfr_y1,
10091 &dconst0, NULL, false);
10092 break;
10093
10094 CASE_FLT_FN (BUILT_IN_NAN):
10095 case BUILT_IN_NAND32:
10096 case BUILT_IN_NAND64:
10097 case BUILT_IN_NAND128:
10098 return fold_builtin_nan (arg0, type, true);
10099
10100 CASE_FLT_FN (BUILT_IN_NANS):
10101 return fold_builtin_nan (arg0, type, false);
10102
10103 CASE_FLT_FN (BUILT_IN_FLOOR):
10104 return fold_builtin_floor (loc, fndecl, arg0);
10105
10106 CASE_FLT_FN (BUILT_IN_CEIL):
10107 return fold_builtin_ceil (loc, fndecl, arg0);
10108
10109 CASE_FLT_FN (BUILT_IN_TRUNC):
10110 return fold_builtin_trunc (loc, fndecl, arg0);
10111
10112 CASE_FLT_FN (BUILT_IN_ROUND):
10113 return fold_builtin_round (loc, fndecl, arg0);
10114
10115 CASE_FLT_FN (BUILT_IN_NEARBYINT):
10116 CASE_FLT_FN (BUILT_IN_RINT):
10117 return fold_trunc_transparent_mathfn (loc, fndecl, arg0);
10118
10119 CASE_FLT_FN (BUILT_IN_LCEIL):
10120 CASE_FLT_FN (BUILT_IN_LLCEIL):
10121 CASE_FLT_FN (BUILT_IN_LFLOOR):
10122 CASE_FLT_FN (BUILT_IN_LLFLOOR):
10123 CASE_FLT_FN (BUILT_IN_LROUND):
10124 CASE_FLT_FN (BUILT_IN_LLROUND):
10125 return fold_builtin_int_roundingfn (loc, fndecl, arg0);
10126
10127 CASE_FLT_FN (BUILT_IN_LRINT):
10128 CASE_FLT_FN (BUILT_IN_LLRINT):
10129 return fold_fixed_mathfn (loc, fndecl, arg0);
10130
10131 case BUILT_IN_BSWAP32:
10132 case BUILT_IN_BSWAP64:
10133 return fold_builtin_bswap (fndecl, arg0);
10134
10135 CASE_INT_FN (BUILT_IN_FFS):
10136 CASE_INT_FN (BUILT_IN_CLZ):
10137 CASE_INT_FN (BUILT_IN_CTZ):
10138 CASE_INT_FN (BUILT_IN_POPCOUNT):
10139 CASE_INT_FN (BUILT_IN_PARITY):
10140 return fold_builtin_bitop (fndecl, arg0);
10141
10142 CASE_FLT_FN (BUILT_IN_SIGNBIT):
10143 return fold_builtin_signbit (loc, arg0, type);
10144
10145 CASE_FLT_FN (BUILT_IN_SIGNIFICAND):
10146 return fold_builtin_significand (loc, arg0, type);
10147
10148 CASE_FLT_FN (BUILT_IN_ILOGB):
10149 CASE_FLT_FN (BUILT_IN_LOGB):
10150 return fold_builtin_logb (loc, arg0, type);
10151
10152 case BUILT_IN_ISASCII:
10153 return fold_builtin_isascii (loc, arg0);
10154
10155 case BUILT_IN_TOASCII:
10156 return fold_builtin_toascii (loc, arg0);
10157
10158 case BUILT_IN_ISDIGIT:
10159 return fold_builtin_isdigit (loc, arg0);
10160
10161 CASE_FLT_FN (BUILT_IN_FINITE):
10162 case BUILT_IN_FINITED32:
10163 case BUILT_IN_FINITED64:
10164 case BUILT_IN_FINITED128:
10165 case BUILT_IN_ISFINITE:
10166 {
10167 tree ret = fold_builtin_classify (loc, fndecl, arg0, BUILT_IN_ISFINITE);
10168 if (ret)
10169 return ret;
10170 return fold_builtin_interclass_mathfn (loc, fndecl, arg0);
10171 }
10172
10173 CASE_FLT_FN (BUILT_IN_ISINF):
10174 case BUILT_IN_ISINFD32:
10175 case BUILT_IN_ISINFD64:
10176 case BUILT_IN_ISINFD128:
10177 {
10178 tree ret = fold_builtin_classify (loc, fndecl, arg0, BUILT_IN_ISINF);
10179 if (ret)
10180 return ret;
10181 return fold_builtin_interclass_mathfn (loc, fndecl, arg0);
10182 }
10183
10184 case BUILT_IN_ISNORMAL:
10185 return fold_builtin_interclass_mathfn (loc, fndecl, arg0);
10186
10187 case BUILT_IN_ISINF_SIGN:
10188 return fold_builtin_classify (loc, fndecl, arg0, BUILT_IN_ISINF_SIGN);
10189
10190 CASE_FLT_FN (BUILT_IN_ISNAN):
10191 case BUILT_IN_ISNAND32:
10192 case BUILT_IN_ISNAND64:
10193 case BUILT_IN_ISNAND128:
10194 return fold_builtin_classify (loc, fndecl, arg0, BUILT_IN_ISNAN);
10195
10196 case BUILT_IN_PRINTF:
10197 case BUILT_IN_PRINTF_UNLOCKED:
10198 case BUILT_IN_VPRINTF:
10199 return fold_builtin_printf (loc, fndecl, arg0, NULL_TREE, ignore, fcode);
10200
10201 case BUILT_IN_FREE:
10202 if (integer_zerop (arg0))
10203 return build_empty_stmt (loc);
10204 break;
10205
10206 default:
10207 break;
10208 }
10209
10210 return NULL_TREE;
10211
10212 }
10213
10214 /* Fold a call to built-in function FNDECL with 2 arguments, ARG0 and ARG1.
10215 IGNORE is true if the result of the function call is ignored. This
10216 function returns NULL_TREE if no simplification was possible. */
10217
10218 static tree
10219 fold_builtin_2 (location_t loc, tree fndecl, tree arg0, tree arg1, bool ignore)
10220 {
10221 tree type = TREE_TYPE (TREE_TYPE (fndecl));
10222 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10223
10224 switch (fcode)
10225 {
10226 CASE_FLT_FN (BUILT_IN_JN):
10227 if (validate_arg (arg0, INTEGER_TYPE)
10228 && validate_arg (arg1, REAL_TYPE))
10229 return do_mpfr_bessel_n (arg0, arg1, type, mpfr_jn, NULL, 0);
10230 break;
10231
10232 CASE_FLT_FN (BUILT_IN_YN):
10233 if (validate_arg (arg0, INTEGER_TYPE)
10234 && validate_arg (arg1, REAL_TYPE))
10235 return do_mpfr_bessel_n (arg0, arg1, type, mpfr_yn,
10236 &dconst0, false);
10237 break;
10238
10239 CASE_FLT_FN (BUILT_IN_DREM):
10240 CASE_FLT_FN (BUILT_IN_REMAINDER):
10241 if (validate_arg (arg0, REAL_TYPE)
10242 && validate_arg(arg1, REAL_TYPE))
10243 return do_mpfr_arg2 (arg0, arg1, type, mpfr_remainder);
10244 break;
10245
10246 CASE_FLT_FN_REENT (BUILT_IN_GAMMA): /* GAMMA_R */
10247 CASE_FLT_FN_REENT (BUILT_IN_LGAMMA): /* LGAMMA_R */
10248 if (validate_arg (arg0, REAL_TYPE)
10249 && validate_arg(arg1, POINTER_TYPE))
10250 return do_mpfr_lgamma_r (arg0, arg1, type);
10251 break;
10252
10253 CASE_FLT_FN (BUILT_IN_ATAN2):
10254 if (validate_arg (arg0, REAL_TYPE)
10255 && validate_arg(arg1, REAL_TYPE))
10256 return do_mpfr_arg2 (arg0, arg1, type, mpfr_atan2);
10257 break;
10258
10259 CASE_FLT_FN (BUILT_IN_FDIM):
10260 if (validate_arg (arg0, REAL_TYPE)
10261 && validate_arg(arg1, REAL_TYPE))
10262 return do_mpfr_arg2 (arg0, arg1, type, mpfr_dim);
10263 break;
10264
10265 CASE_FLT_FN (BUILT_IN_HYPOT):
10266 return fold_builtin_hypot (loc, fndecl, arg0, arg1, type);
10267
10268 CASE_FLT_FN (BUILT_IN_CPOW):
10269 if (validate_arg (arg0, COMPLEX_TYPE)
10270 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE
10271 && validate_arg (arg1, COMPLEX_TYPE)
10272 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg1))) == REAL_TYPE)
10273 return do_mpc_arg2 (arg0, arg1, type, /*do_nonfinite=*/ 0, mpc_pow);
10274 break;
10275
10276 CASE_FLT_FN (BUILT_IN_LDEXP):
10277 return fold_builtin_load_exponent (loc, arg0, arg1, type, /*ldexp=*/true);
10278 CASE_FLT_FN (BUILT_IN_SCALBN):
10279 CASE_FLT_FN (BUILT_IN_SCALBLN):
10280 return fold_builtin_load_exponent (loc, arg0, arg1,
10281 type, /*ldexp=*/false);
10282
10283 CASE_FLT_FN (BUILT_IN_FREXP):
10284 return fold_builtin_frexp (loc, arg0, arg1, type);
10285
10286 CASE_FLT_FN (BUILT_IN_MODF):
10287 return fold_builtin_modf (loc, arg0, arg1, type);
10288
10289 case BUILT_IN_BZERO:
10290 return fold_builtin_bzero (loc, arg0, arg1, ignore);
10291
10292 case BUILT_IN_FPUTS:
10293 return fold_builtin_fputs (loc, arg0, arg1, ignore, false, NULL_TREE);
10294
10295 case BUILT_IN_FPUTS_UNLOCKED:
10296 return fold_builtin_fputs (loc, arg0, arg1, ignore, true, NULL_TREE);
10297
10298 case BUILT_IN_STRSTR:
10299 return fold_builtin_strstr (loc, arg0, arg1, type);
10300
10301 case BUILT_IN_STRCAT:
10302 return fold_builtin_strcat (loc, arg0, arg1);
10303
10304 case BUILT_IN_STRSPN:
10305 return fold_builtin_strspn (loc, arg0, arg1);
10306
10307 case BUILT_IN_STRCSPN:
10308 return fold_builtin_strcspn (loc, arg0, arg1);
10309
10310 case BUILT_IN_STRCHR:
10311 case BUILT_IN_INDEX:
10312 return fold_builtin_strchr (loc, arg0, arg1, type);
10313
10314 case BUILT_IN_STRRCHR:
10315 case BUILT_IN_RINDEX:
10316 return fold_builtin_strrchr (loc, arg0, arg1, type);
10317
10318 case BUILT_IN_STRCPY:
10319 return fold_builtin_strcpy (loc, fndecl, arg0, arg1, NULL_TREE);
10320
10321 case BUILT_IN_STPCPY:
10322 if (ignore)
10323 {
10324 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
10325 if (!fn)
10326 break;
10327
10328 return build_call_expr_loc (loc, fn, 2, arg0, arg1);
10329 }
10330 else
10331 return fold_builtin_stpcpy (loc, fndecl, arg0, arg1);
10332 break;
10333
10334 case BUILT_IN_STRCMP:
10335 return fold_builtin_strcmp (loc, arg0, arg1);
10336
10337 case BUILT_IN_STRPBRK:
10338 return fold_builtin_strpbrk (loc, arg0, arg1, type);
10339
10340 case BUILT_IN_EXPECT:
10341 return fold_builtin_expect (loc, arg0, arg1);
10342
10343 CASE_FLT_FN (BUILT_IN_POW):
10344 return fold_builtin_pow (loc, fndecl, arg0, arg1, type);
10345
10346 CASE_FLT_FN (BUILT_IN_POWI):
10347 return fold_builtin_powi (loc, fndecl, arg0, arg1, type);
10348
10349 CASE_FLT_FN (BUILT_IN_COPYSIGN):
10350 return fold_builtin_copysign (loc, fndecl, arg0, arg1, type);
10351
10352 CASE_FLT_FN (BUILT_IN_FMIN):
10353 return fold_builtin_fmin_fmax (loc, arg0, arg1, type, /*max=*/false);
10354
10355 CASE_FLT_FN (BUILT_IN_FMAX):
10356 return fold_builtin_fmin_fmax (loc, arg0, arg1, type, /*max=*/true);
10357
10358 case BUILT_IN_ISGREATER:
10359 return fold_builtin_unordered_cmp (loc, fndecl,
10360 arg0, arg1, UNLE_EXPR, LE_EXPR);
10361 case BUILT_IN_ISGREATEREQUAL:
10362 return fold_builtin_unordered_cmp (loc, fndecl,
10363 arg0, arg1, UNLT_EXPR, LT_EXPR);
10364 case BUILT_IN_ISLESS:
10365 return fold_builtin_unordered_cmp (loc, fndecl,
10366 arg0, arg1, UNGE_EXPR, GE_EXPR);
10367 case BUILT_IN_ISLESSEQUAL:
10368 return fold_builtin_unordered_cmp (loc, fndecl,
10369 arg0, arg1, UNGT_EXPR, GT_EXPR);
10370 case BUILT_IN_ISLESSGREATER:
10371 return fold_builtin_unordered_cmp (loc, fndecl,
10372 arg0, arg1, UNEQ_EXPR, EQ_EXPR);
10373 case BUILT_IN_ISUNORDERED:
10374 return fold_builtin_unordered_cmp (loc, fndecl,
10375 arg0, arg1, UNORDERED_EXPR,
10376 NOP_EXPR);
10377
10378 /* We do the folding for va_start in the expander. */
10379 case BUILT_IN_VA_START:
10380 break;
10381
10382 case BUILT_IN_SPRINTF:
10383 return fold_builtin_sprintf (loc, arg0, arg1, NULL_TREE, ignore);
10384
10385 case BUILT_IN_OBJECT_SIZE:
10386 return fold_builtin_object_size (arg0, arg1);
10387
10388 case BUILT_IN_PRINTF:
10389 case BUILT_IN_PRINTF_UNLOCKED:
10390 case BUILT_IN_VPRINTF:
10391 return fold_builtin_printf (loc, fndecl, arg0, arg1, ignore, fcode);
10392
10393 case BUILT_IN_PRINTF_CHK:
10394 case BUILT_IN_VPRINTF_CHK:
10395 if (!validate_arg (arg0, INTEGER_TYPE)
10396 || TREE_SIDE_EFFECTS (arg0))
10397 return NULL_TREE;
10398 else
10399 return fold_builtin_printf (loc, fndecl,
10400 arg1, NULL_TREE, ignore, fcode);
10401 break;
10402
10403 case BUILT_IN_FPRINTF:
10404 case BUILT_IN_FPRINTF_UNLOCKED:
10405 case BUILT_IN_VFPRINTF:
10406 return fold_builtin_fprintf (loc, fndecl, arg0, arg1, NULL_TREE,
10407 ignore, fcode);
10408
10409 default:
10410 break;
10411 }
10412 return NULL_TREE;
10413 }
10414
10415 /* Fold a call to built-in function FNDECL with 3 arguments, ARG0, ARG1,
10416 and ARG2. IGNORE is true if the result of the function call is ignored.
10417 This function returns NULL_TREE if no simplification was possible. */
10418
10419 static tree
10420 fold_builtin_3 (location_t loc, tree fndecl,
10421 tree arg0, tree arg1, tree arg2, bool ignore)
10422 {
10423 tree type = TREE_TYPE (TREE_TYPE (fndecl));
10424 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10425 switch (fcode)
10426 {
10427
10428 CASE_FLT_FN (BUILT_IN_SINCOS):
10429 return fold_builtin_sincos (loc, arg0, arg1, arg2);
10430
10431 CASE_FLT_FN (BUILT_IN_FMA):
10432 if (validate_arg (arg0, REAL_TYPE)
10433 && validate_arg(arg1, REAL_TYPE)
10434 && validate_arg(arg2, REAL_TYPE))
10435 return do_mpfr_arg3 (arg0, arg1, arg2, type, mpfr_fma);
10436 break;
10437
10438 CASE_FLT_FN (BUILT_IN_REMQUO):
10439 if (validate_arg (arg0, REAL_TYPE)
10440 && validate_arg(arg1, REAL_TYPE)
10441 && validate_arg(arg2, POINTER_TYPE))
10442 return do_mpfr_remquo (arg0, arg1, arg2);
10443 break;
10444
10445 case BUILT_IN_MEMSET:
10446 return fold_builtin_memset (loc, arg0, arg1, arg2, type, ignore);
10447
10448 case BUILT_IN_BCOPY:
10449 return fold_builtin_memory_op (loc, arg1, arg0, arg2,
10450 void_type_node, true, /*endp=*/3);
10451
10452 case BUILT_IN_MEMCPY:
10453 return fold_builtin_memory_op (loc, arg0, arg1, arg2,
10454 type, ignore, /*endp=*/0);
10455
10456 case BUILT_IN_MEMPCPY:
10457 return fold_builtin_memory_op (loc, arg0, arg1, arg2,
10458 type, ignore, /*endp=*/1);
10459
10460 case BUILT_IN_MEMMOVE:
10461 return fold_builtin_memory_op (loc, arg0, arg1, arg2,
10462 type, ignore, /*endp=*/3);
10463
10464 case BUILT_IN_STRNCAT:
10465 return fold_builtin_strncat (loc, arg0, arg1, arg2);
10466
10467 case BUILT_IN_STRNCPY:
10468 return fold_builtin_strncpy (loc, fndecl, arg0, arg1, arg2, NULL_TREE);
10469
10470 case BUILT_IN_STRNCMP:
10471 return fold_builtin_strncmp (loc, arg0, arg1, arg2);
10472
10473 case BUILT_IN_MEMCHR:
10474 return fold_builtin_memchr (loc, arg0, arg1, arg2, type);
10475
10476 case BUILT_IN_BCMP:
10477 case BUILT_IN_MEMCMP:
10478 return fold_builtin_memcmp (loc, arg0, arg1, arg2);;
10479
10480 case BUILT_IN_SPRINTF:
10481 return fold_builtin_sprintf (loc, arg0, arg1, arg2, ignore);
10482
10483 case BUILT_IN_STRCPY_CHK:
10484 case BUILT_IN_STPCPY_CHK:
10485 return fold_builtin_stxcpy_chk (loc, fndecl, arg0, arg1, arg2, NULL_TREE,
10486 ignore, fcode);
10487
10488 case BUILT_IN_STRCAT_CHK:
10489 return fold_builtin_strcat_chk (loc, fndecl, arg0, arg1, arg2);
10490
10491 case BUILT_IN_PRINTF_CHK:
10492 case BUILT_IN_VPRINTF_CHK:
10493 if (!validate_arg (arg0, INTEGER_TYPE)
10494 || TREE_SIDE_EFFECTS (arg0))
10495 return NULL_TREE;
10496 else
10497 return fold_builtin_printf (loc, fndecl, arg1, arg2, ignore, fcode);
10498 break;
10499
10500 case BUILT_IN_FPRINTF:
10501 case BUILT_IN_FPRINTF_UNLOCKED:
10502 case BUILT_IN_VFPRINTF:
10503 return fold_builtin_fprintf (loc, fndecl, arg0, arg1, arg2,
10504 ignore, fcode);
10505
10506 case BUILT_IN_FPRINTF_CHK:
10507 case BUILT_IN_VFPRINTF_CHK:
10508 if (!validate_arg (arg1, INTEGER_TYPE)
10509 || TREE_SIDE_EFFECTS (arg1))
10510 return NULL_TREE;
10511 else
10512 return fold_builtin_fprintf (loc, fndecl, arg0, arg2, NULL_TREE,
10513 ignore, fcode);
10514
10515 default:
10516 break;
10517 }
10518 return NULL_TREE;
10519 }
10520
10521 /* Fold a call to built-in function FNDECL with 4 arguments, ARG0, ARG1,
10522 ARG2, and ARG3. IGNORE is true if the result of the function call is
10523 ignored. This function returns NULL_TREE if no simplification was
10524 possible. */
10525
10526 static tree
10527 fold_builtin_4 (location_t loc, tree fndecl,
10528 tree arg0, tree arg1, tree arg2, tree arg3, bool ignore)
10529 {
10530 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10531
10532 switch (fcode)
10533 {
10534 case BUILT_IN_MEMCPY_CHK:
10535 case BUILT_IN_MEMPCPY_CHK:
10536 case BUILT_IN_MEMMOVE_CHK:
10537 case BUILT_IN_MEMSET_CHK:
10538 return fold_builtin_memory_chk (loc, fndecl, arg0, arg1, arg2, arg3,
10539 NULL_TREE, ignore,
10540 DECL_FUNCTION_CODE (fndecl));
10541
10542 case BUILT_IN_STRNCPY_CHK:
10543 return fold_builtin_strncpy_chk (loc, arg0, arg1, arg2, arg3, NULL_TREE);
10544
10545 case BUILT_IN_STRNCAT_CHK:
10546 return fold_builtin_strncat_chk (loc, fndecl, arg0, arg1, arg2, arg3);
10547
10548 case BUILT_IN_FPRINTF_CHK:
10549 case BUILT_IN_VFPRINTF_CHK:
10550 if (!validate_arg (arg1, INTEGER_TYPE)
10551 || TREE_SIDE_EFFECTS (arg1))
10552 return NULL_TREE;
10553 else
10554 return fold_builtin_fprintf (loc, fndecl, arg0, arg2, arg3,
10555 ignore, fcode);
10556 break;
10557
10558 default:
10559 break;
10560 }
10561 return NULL_TREE;
10562 }
10563
10564 /* Fold a call to built-in function FNDECL. ARGS is an array of NARGS
10565 arguments, where NARGS <= 4. IGNORE is true if the result of the
10566 function call is ignored. This function returns NULL_TREE if no
10567 simplification was possible. Note that this only folds builtins with
10568 fixed argument patterns. Foldings that do varargs-to-varargs
10569 transformations, or that match calls with more than 4 arguments,
10570 need to be handled with fold_builtin_varargs instead. */
10571
10572 #define MAX_ARGS_TO_FOLD_BUILTIN 4
10573
10574 static tree
10575 fold_builtin_n (location_t loc, tree fndecl, tree *args, int nargs, bool ignore)
10576 {
10577 tree ret = NULL_TREE;
10578
10579 switch (nargs)
10580 {
10581 case 0:
10582 ret = fold_builtin_0 (loc, fndecl, ignore);
10583 break;
10584 case 1:
10585 ret = fold_builtin_1 (loc, fndecl, args[0], ignore);
10586 break;
10587 case 2:
10588 ret = fold_builtin_2 (loc, fndecl, args[0], args[1], ignore);
10589 break;
10590 case 3:
10591 ret = fold_builtin_3 (loc, fndecl, args[0], args[1], args[2], ignore);
10592 break;
10593 case 4:
10594 ret = fold_builtin_4 (loc, fndecl, args[0], args[1], args[2], args[3],
10595 ignore);
10596 break;
10597 default:
10598 break;
10599 }
10600 if (ret)
10601 {
10602 ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
10603 SET_EXPR_LOCATION (ret, loc);
10604 TREE_NO_WARNING (ret) = 1;
10605 return ret;
10606 }
10607 return NULL_TREE;
10608 }
10609
10610 /* Builtins with folding operations that operate on "..." arguments
10611 need special handling; we need to store the arguments in a convenient
10612 data structure before attempting any folding. Fortunately there are
10613 only a few builtins that fall into this category. FNDECL is the
10614 function, EXP is the CALL_EXPR for the call, and IGNORE is true if the
10615 result of the function call is ignored. */
10616
10617 static tree
10618 fold_builtin_varargs (location_t loc, tree fndecl, tree exp,
10619 bool ignore ATTRIBUTE_UNUSED)
10620 {
10621 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
10622 tree ret = NULL_TREE;
10623
10624 switch (fcode)
10625 {
10626 case BUILT_IN_SPRINTF_CHK:
10627 case BUILT_IN_VSPRINTF_CHK:
10628 ret = fold_builtin_sprintf_chk (loc, exp, fcode);
10629 break;
10630
10631 case BUILT_IN_SNPRINTF_CHK:
10632 case BUILT_IN_VSNPRINTF_CHK:
10633 ret = fold_builtin_snprintf_chk (loc, exp, NULL_TREE, fcode);
10634 break;
10635
10636 case BUILT_IN_FPCLASSIFY:
10637 ret = fold_builtin_fpclassify (loc, exp);
10638 break;
10639
10640 default:
10641 break;
10642 }
10643 if (ret)
10644 {
10645 ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
10646 SET_EXPR_LOCATION (ret, loc);
10647 TREE_NO_WARNING (ret) = 1;
10648 return ret;
10649 }
10650 return NULL_TREE;
10651 }
10652
10653 /* Return true if FNDECL shouldn't be folded right now.
10654 If a built-in function has an inline attribute always_inline
10655 wrapper, defer folding it after always_inline functions have
10656 been inlined, otherwise e.g. -D_FORTIFY_SOURCE checking
10657 might not be performed. */
10658
10659 static bool
10660 avoid_folding_inline_builtin (tree fndecl)
10661 {
10662 return (DECL_DECLARED_INLINE_P (fndecl)
10663 && DECL_DISREGARD_INLINE_LIMITS (fndecl)
10664 && cfun
10665 && !cfun->always_inline_functions_inlined
10666 && lookup_attribute ("always_inline", DECL_ATTRIBUTES (fndecl)));
10667 }
10668
10669 /* A wrapper function for builtin folding that prevents warnings for
10670 "statement without effect" and the like, caused by removing the
10671 call node earlier than the warning is generated. */
10672
10673 tree
10674 fold_call_expr (location_t loc, tree exp, bool ignore)
10675 {
10676 tree ret = NULL_TREE;
10677 tree fndecl = get_callee_fndecl (exp);
10678 if (fndecl
10679 && TREE_CODE (fndecl) == FUNCTION_DECL
10680 && DECL_BUILT_IN (fndecl)
10681 /* If CALL_EXPR_VA_ARG_PACK is set, the arguments aren't finalized
10682 yet. Defer folding until we see all the arguments
10683 (after inlining). */
10684 && !CALL_EXPR_VA_ARG_PACK (exp))
10685 {
10686 int nargs = call_expr_nargs (exp);
10687
10688 /* Before gimplification CALL_EXPR_VA_ARG_PACK is not set, but
10689 instead last argument is __builtin_va_arg_pack (). Defer folding
10690 even in that case, until arguments are finalized. */
10691 if (nargs && TREE_CODE (CALL_EXPR_ARG (exp, nargs - 1)) == CALL_EXPR)
10692 {
10693 tree fndecl2 = get_callee_fndecl (CALL_EXPR_ARG (exp, nargs - 1));
10694 if (fndecl2
10695 && TREE_CODE (fndecl2) == FUNCTION_DECL
10696 && DECL_BUILT_IN_CLASS (fndecl2) == BUILT_IN_NORMAL
10697 && DECL_FUNCTION_CODE (fndecl2) == BUILT_IN_VA_ARG_PACK)
10698 return NULL_TREE;
10699 }
10700
10701 if (avoid_folding_inline_builtin (fndecl))
10702 return NULL_TREE;
10703
10704 /* FIXME: Don't use a list in this interface. */
10705 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
10706 return targetm.fold_builtin (fndecl, CALL_EXPR_ARGS (exp), ignore);
10707 else
10708 {
10709 if (nargs <= MAX_ARGS_TO_FOLD_BUILTIN)
10710 {
10711 tree *args = CALL_EXPR_ARGP (exp);
10712 ret = fold_builtin_n (loc, fndecl, args, nargs, ignore);
10713 }
10714 if (!ret)
10715 ret = fold_builtin_varargs (loc, fndecl, exp, ignore);
10716 if (ret)
10717 return ret;
10718 }
10719 }
10720 return NULL_TREE;
10721 }
10722
10723 /* Conveniently construct a function call expression. FNDECL names the
10724 function to be called and ARGLIST is a TREE_LIST of arguments. */
10725
10726 tree
10727 build_function_call_expr (location_t loc, tree fndecl, tree arglist)
10728 {
10729 tree fntype = TREE_TYPE (fndecl);
10730 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10731 int n = list_length (arglist);
10732 tree *argarray = (tree *) alloca (n * sizeof (tree));
10733 int i;
10734
10735 for (i = 0; i < n; i++, arglist = TREE_CHAIN (arglist))
10736 argarray[i] = TREE_VALUE (arglist);
10737 return fold_builtin_call_array (loc, TREE_TYPE (fntype), fn, n, argarray);
10738 }
10739
10740 /* Conveniently construct a function call expression. FNDECL names the
10741 function to be called, N is the number of arguments, and the "..."
10742 parameters are the argument expressions. */
10743
10744 tree
10745 build_call_expr_loc (location_t loc, tree fndecl, int n, ...)
10746 {
10747 va_list ap;
10748 tree fntype = TREE_TYPE (fndecl);
10749 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10750 tree *argarray = (tree *) alloca (n * sizeof (tree));
10751 int i;
10752
10753 va_start (ap, n);
10754 for (i = 0; i < n; i++)
10755 argarray[i] = va_arg (ap, tree);
10756 va_end (ap);
10757 return fold_builtin_call_array (loc, TREE_TYPE (fntype), fn, n, argarray);
10758 }
10759
10760 /* Construct a CALL_EXPR with type TYPE with FN as the function expression.
10761 N arguments are passed in the array ARGARRAY. */
10762
10763 tree
10764 fold_builtin_call_array (location_t loc, tree type,
10765 tree fn,
10766 int n,
10767 tree *argarray)
10768 {
10769 tree ret = NULL_TREE;
10770 int i;
10771 tree exp;
10772
10773 if (TREE_CODE (fn) == ADDR_EXPR)
10774 {
10775 tree fndecl = TREE_OPERAND (fn, 0);
10776 if (TREE_CODE (fndecl) == FUNCTION_DECL
10777 && DECL_BUILT_IN (fndecl))
10778 {
10779 /* If last argument is __builtin_va_arg_pack (), arguments to this
10780 function are not finalized yet. Defer folding until they are. */
10781 if (n && TREE_CODE (argarray[n - 1]) == CALL_EXPR)
10782 {
10783 tree fndecl2 = get_callee_fndecl (argarray[n - 1]);
10784 if (fndecl2
10785 && TREE_CODE (fndecl2) == FUNCTION_DECL
10786 && DECL_BUILT_IN_CLASS (fndecl2) == BUILT_IN_NORMAL
10787 && DECL_FUNCTION_CODE (fndecl2) == BUILT_IN_VA_ARG_PACK)
10788 return build_call_array_loc (loc, type, fn, n, argarray);
10789 }
10790 if (avoid_folding_inline_builtin (fndecl))
10791 return build_call_array_loc (loc, type, fn, n, argarray);
10792 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
10793 {
10794 tree arglist = NULL_TREE;
10795 for (i = n - 1; i >= 0; i--)
10796 arglist = tree_cons (NULL_TREE, argarray[i], arglist);
10797 ret = targetm.fold_builtin (fndecl, arglist, false);
10798 if (ret)
10799 return ret;
10800 return build_call_array_loc (loc, type, fn, n, argarray);
10801 }
10802 else if (n <= MAX_ARGS_TO_FOLD_BUILTIN)
10803 {
10804 /* First try the transformations that don't require consing up
10805 an exp. */
10806 ret = fold_builtin_n (loc, fndecl, argarray, n, false);
10807 if (ret)
10808 return ret;
10809 }
10810
10811 /* If we got this far, we need to build an exp. */
10812 exp = build_call_array_loc (loc, type, fn, n, argarray);
10813 ret = fold_builtin_varargs (loc, fndecl, exp, false);
10814 return ret ? ret : exp;
10815 }
10816 }
10817
10818 return build_call_array_loc (loc, type, fn, n, argarray);
10819 }
10820
10821 /* Construct a new CALL_EXPR using the tail of the argument list of EXP
10822 along with N new arguments specified as the "..." parameters. SKIP
10823 is the number of arguments in EXP to be omitted. This function is used
10824 to do varargs-to-varargs transformations. */
10825
10826 static tree
10827 rewrite_call_expr (location_t loc, tree exp, int skip, tree fndecl, int n, ...)
10828 {
10829 int oldnargs = call_expr_nargs (exp);
10830 int nargs = oldnargs - skip + n;
10831 tree fntype = TREE_TYPE (fndecl);
10832 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
10833 tree *buffer;
10834
10835 if (n > 0)
10836 {
10837 int i, j;
10838 va_list ap;
10839
10840 buffer = XALLOCAVEC (tree, nargs);
10841 va_start (ap, n);
10842 for (i = 0; i < n; i++)
10843 buffer[i] = va_arg (ap, tree);
10844 va_end (ap);
10845 for (j = skip; j < oldnargs; j++, i++)
10846 buffer[i] = CALL_EXPR_ARG (exp, j);
10847 }
10848 else
10849 buffer = CALL_EXPR_ARGP (exp) + skip;
10850
10851 return fold (build_call_array_loc (loc, TREE_TYPE (exp), fn, nargs, buffer));
10852 }
10853
10854 /* Validate a single argument ARG against a tree code CODE representing
10855 a type. */
10856
10857 static bool
10858 validate_arg (const_tree arg, enum tree_code code)
10859 {
10860 if (!arg)
10861 return false;
10862 else if (code == POINTER_TYPE)
10863 return POINTER_TYPE_P (TREE_TYPE (arg));
10864 else if (code == INTEGER_TYPE)
10865 return INTEGRAL_TYPE_P (TREE_TYPE (arg));
10866 return code == TREE_CODE (TREE_TYPE (arg));
10867 }
10868
10869 /* This function validates the types of a function call argument list
10870 against a specified list of tree_codes. If the last specifier is a 0,
10871 that represents an ellipses, otherwise the last specifier must be a
10872 VOID_TYPE.
10873
10874 This is the GIMPLE version of validate_arglist. Eventually we want to
10875 completely convert builtins.c to work from GIMPLEs and the tree based
10876 validate_arglist will then be removed. */
10877
10878 bool
10879 validate_gimple_arglist (const_gimple call, ...)
10880 {
10881 enum tree_code code;
10882 bool res = 0;
10883 va_list ap;
10884 const_tree arg;
10885 size_t i;
10886
10887 va_start (ap, call);
10888 i = 0;
10889
10890 do
10891 {
10892 code = (enum tree_code) va_arg (ap, int);
10893 switch (code)
10894 {
10895 case 0:
10896 /* This signifies an ellipses, any further arguments are all ok. */
10897 res = true;
10898 goto end;
10899 case VOID_TYPE:
10900 /* This signifies an endlink, if no arguments remain, return
10901 true, otherwise return false. */
10902 res = (i == gimple_call_num_args (call));
10903 goto end;
10904 default:
10905 /* If no parameters remain or the parameter's code does not
10906 match the specified code, return false. Otherwise continue
10907 checking any remaining arguments. */
10908 arg = gimple_call_arg (call, i++);
10909 if (!validate_arg (arg, code))
10910 goto end;
10911 break;
10912 }
10913 }
10914 while (1);
10915
10916 /* We need gotos here since we can only have one VA_CLOSE in a
10917 function. */
10918 end: ;
10919 va_end (ap);
10920
10921 return res;
10922 }
10923
10924 /* This function validates the types of a function call argument list
10925 against a specified list of tree_codes. If the last specifier is a 0,
10926 that represents an ellipses, otherwise the last specifier must be a
10927 VOID_TYPE. */
10928
10929 bool
10930 validate_arglist (const_tree callexpr, ...)
10931 {
10932 enum tree_code code;
10933 bool res = 0;
10934 va_list ap;
10935 const_call_expr_arg_iterator iter;
10936 const_tree arg;
10937
10938 va_start (ap, callexpr);
10939 init_const_call_expr_arg_iterator (callexpr, &iter);
10940
10941 do
10942 {
10943 code = (enum tree_code) va_arg (ap, int);
10944 switch (code)
10945 {
10946 case 0:
10947 /* This signifies an ellipses, any further arguments are all ok. */
10948 res = true;
10949 goto end;
10950 case VOID_TYPE:
10951 /* This signifies an endlink, if no arguments remain, return
10952 true, otherwise return false. */
10953 res = !more_const_call_expr_args_p (&iter);
10954 goto end;
10955 default:
10956 /* If no parameters remain or the parameter's code does not
10957 match the specified code, return false. Otherwise continue
10958 checking any remaining arguments. */
10959 arg = next_const_call_expr_arg (&iter);
10960 if (!validate_arg (arg, code))
10961 goto end;
10962 break;
10963 }
10964 }
10965 while (1);
10966
10967 /* We need gotos here since we can only have one VA_CLOSE in a
10968 function. */
10969 end: ;
10970 va_end (ap);
10971
10972 return res;
10973 }
10974
10975 /* Default target-specific builtin expander that does nothing. */
10976
10977 rtx
10978 default_expand_builtin (tree exp ATTRIBUTE_UNUSED,
10979 rtx target ATTRIBUTE_UNUSED,
10980 rtx subtarget ATTRIBUTE_UNUSED,
10981 enum machine_mode mode ATTRIBUTE_UNUSED,
10982 int ignore ATTRIBUTE_UNUSED)
10983 {
10984 return NULL_RTX;
10985 }
10986
10987 /* Returns true is EXP represents data that would potentially reside
10988 in a readonly section. */
10989
10990 static bool
10991 readonly_data_expr (tree exp)
10992 {
10993 STRIP_NOPS (exp);
10994
10995 if (TREE_CODE (exp) != ADDR_EXPR)
10996 return false;
10997
10998 exp = get_base_address (TREE_OPERAND (exp, 0));
10999 if (!exp)
11000 return false;
11001
11002 /* Make sure we call decl_readonly_section only for trees it
11003 can handle (since it returns true for everything it doesn't
11004 understand). */
11005 if (TREE_CODE (exp) == STRING_CST
11006 || TREE_CODE (exp) == CONSTRUCTOR
11007 || (TREE_CODE (exp) == VAR_DECL && TREE_STATIC (exp)))
11008 return decl_readonly_section (exp, 0);
11009 else
11010 return false;
11011 }
11012
11013 /* Simplify a call to the strstr builtin. S1 and S2 are the arguments
11014 to the call, and TYPE is its return type.
11015
11016 Return NULL_TREE if no simplification was possible, otherwise return the
11017 simplified form of the call as a tree.
11018
11019 The simplified form may be a constant or other expression which
11020 computes the same value, but in a more efficient manner (including
11021 calls to other builtin functions).
11022
11023 The call may contain arguments which need to be evaluated, but
11024 which are not useful to determine the result of the call. In
11025 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11026 COMPOUND_EXPR will be an argument which must be evaluated.
11027 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11028 COMPOUND_EXPR in the chain will contain the tree for the simplified
11029 form of the builtin function call. */
11030
11031 static tree
11032 fold_builtin_strstr (location_t loc, tree s1, tree s2, tree type)
11033 {
11034 if (!validate_arg (s1, POINTER_TYPE)
11035 || !validate_arg (s2, POINTER_TYPE))
11036 return NULL_TREE;
11037 else
11038 {
11039 tree fn;
11040 const char *p1, *p2;
11041
11042 p2 = c_getstr (s2);
11043 if (p2 == NULL)
11044 return NULL_TREE;
11045
11046 p1 = c_getstr (s1);
11047 if (p1 != NULL)
11048 {
11049 const char *r = strstr (p1, p2);
11050 tree tem;
11051
11052 if (r == NULL)
11053 return build_int_cst (TREE_TYPE (s1), 0);
11054
11055 /* Return an offset into the constant string argument. */
11056 tem = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (s1),
11057 s1, size_int (r - p1));
11058 return fold_convert_loc (loc, type, tem);
11059 }
11060
11061 /* The argument is const char *, and the result is char *, so we need
11062 a type conversion here to avoid a warning. */
11063 if (p2[0] == '\0')
11064 return fold_convert_loc (loc, type, s1);
11065
11066 if (p2[1] != '\0')
11067 return NULL_TREE;
11068
11069 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
11070 if (!fn)
11071 return NULL_TREE;
11072
11073 /* New argument list transforming strstr(s1, s2) to
11074 strchr(s1, s2[0]). */
11075 return build_call_expr_loc (loc, fn, 2, s1, build_int_cst (NULL_TREE, p2[0]));
11076 }
11077 }
11078
11079 /* Simplify a call to the strchr builtin. S1 and S2 are the arguments to
11080 the call, and TYPE is its return type.
11081
11082 Return NULL_TREE if no simplification was possible, otherwise return the
11083 simplified form of the call as a tree.
11084
11085 The simplified form may be a constant or other expression which
11086 computes the same value, but in a more efficient manner (including
11087 calls to other builtin functions).
11088
11089 The call may contain arguments which need to be evaluated, but
11090 which are not useful to determine the result of the call. In
11091 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11092 COMPOUND_EXPR will be an argument which must be evaluated.
11093 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11094 COMPOUND_EXPR in the chain will contain the tree for the simplified
11095 form of the builtin function call. */
11096
11097 static tree
11098 fold_builtin_strchr (location_t loc, tree s1, tree s2, tree type)
11099 {
11100 if (!validate_arg (s1, POINTER_TYPE)
11101 || !validate_arg (s2, INTEGER_TYPE))
11102 return NULL_TREE;
11103 else
11104 {
11105 const char *p1;
11106
11107 if (TREE_CODE (s2) != INTEGER_CST)
11108 return NULL_TREE;
11109
11110 p1 = c_getstr (s1);
11111 if (p1 != NULL)
11112 {
11113 char c;
11114 const char *r;
11115 tree tem;
11116
11117 if (target_char_cast (s2, &c))
11118 return NULL_TREE;
11119
11120 r = strchr (p1, c);
11121
11122 if (r == NULL)
11123 return build_int_cst (TREE_TYPE (s1), 0);
11124
11125 /* Return an offset into the constant string argument. */
11126 tem = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (s1),
11127 s1, size_int (r - p1));
11128 return fold_convert_loc (loc, type, tem);
11129 }
11130 return NULL_TREE;
11131 }
11132 }
11133
11134 /* Simplify a call to the strrchr builtin. S1 and S2 are the arguments to
11135 the call, and TYPE is its return type.
11136
11137 Return NULL_TREE if no simplification was possible, otherwise return the
11138 simplified form of the call as a tree.
11139
11140 The simplified form may be a constant or other expression which
11141 computes the same value, but in a more efficient manner (including
11142 calls to other builtin functions).
11143
11144 The call may contain arguments which need to be evaluated, but
11145 which are not useful to determine the result of the call. In
11146 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11147 COMPOUND_EXPR will be an argument which must be evaluated.
11148 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11149 COMPOUND_EXPR in the chain will contain the tree for the simplified
11150 form of the builtin function call. */
11151
11152 static tree
11153 fold_builtin_strrchr (location_t loc, tree s1, tree s2, tree type)
11154 {
11155 if (!validate_arg (s1, POINTER_TYPE)
11156 || !validate_arg (s2, INTEGER_TYPE))
11157 return NULL_TREE;
11158 else
11159 {
11160 tree fn;
11161 const char *p1;
11162
11163 if (TREE_CODE (s2) != INTEGER_CST)
11164 return NULL_TREE;
11165
11166 p1 = c_getstr (s1);
11167 if (p1 != NULL)
11168 {
11169 char c;
11170 const char *r;
11171 tree tem;
11172
11173 if (target_char_cast (s2, &c))
11174 return NULL_TREE;
11175
11176 r = strrchr (p1, c);
11177
11178 if (r == NULL)
11179 return build_int_cst (TREE_TYPE (s1), 0);
11180
11181 /* Return an offset into the constant string argument. */
11182 tem = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (s1),
11183 s1, size_int (r - p1));
11184 return fold_convert_loc (loc, type, tem);
11185 }
11186
11187 if (! integer_zerop (s2))
11188 return NULL_TREE;
11189
11190 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
11191 if (!fn)
11192 return NULL_TREE;
11193
11194 /* Transform strrchr(s1, '\0') to strchr(s1, '\0'). */
11195 return build_call_expr_loc (loc, fn, 2, s1, s2);
11196 }
11197 }
11198
11199 /* Simplify a call to the strpbrk builtin. S1 and S2 are the arguments
11200 to the call, and TYPE is its return type.
11201
11202 Return NULL_TREE if no simplification was possible, otherwise return the
11203 simplified form of the call as a tree.
11204
11205 The simplified form may be a constant or other expression which
11206 computes the same value, but in a more efficient manner (including
11207 calls to other builtin functions).
11208
11209 The call may contain arguments which need to be evaluated, but
11210 which are not useful to determine the result of the call. In
11211 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11212 COMPOUND_EXPR will be an argument which must be evaluated.
11213 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11214 COMPOUND_EXPR in the chain will contain the tree for the simplified
11215 form of the builtin function call. */
11216
11217 static tree
11218 fold_builtin_strpbrk (location_t loc, tree s1, tree s2, tree type)
11219 {
11220 if (!validate_arg (s1, POINTER_TYPE)
11221 || !validate_arg (s2, POINTER_TYPE))
11222 return NULL_TREE;
11223 else
11224 {
11225 tree fn;
11226 const char *p1, *p2;
11227
11228 p2 = c_getstr (s2);
11229 if (p2 == NULL)
11230 return NULL_TREE;
11231
11232 p1 = c_getstr (s1);
11233 if (p1 != NULL)
11234 {
11235 const char *r = strpbrk (p1, p2);
11236 tree tem;
11237
11238 if (r == NULL)
11239 return build_int_cst (TREE_TYPE (s1), 0);
11240
11241 /* Return an offset into the constant string argument. */
11242 tem = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (s1),
11243 s1, size_int (r - p1));
11244 return fold_convert_loc (loc, type, tem);
11245 }
11246
11247 if (p2[0] == '\0')
11248 /* strpbrk(x, "") == NULL.
11249 Evaluate and ignore s1 in case it had side-effects. */
11250 return omit_one_operand_loc (loc, TREE_TYPE (s1), integer_zero_node, s1);
11251
11252 if (p2[1] != '\0')
11253 return NULL_TREE; /* Really call strpbrk. */
11254
11255 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
11256 if (!fn)
11257 return NULL_TREE;
11258
11259 /* New argument list transforming strpbrk(s1, s2) to
11260 strchr(s1, s2[0]). */
11261 return build_call_expr_loc (loc, fn, 2, s1, build_int_cst (NULL_TREE, p2[0]));
11262 }
11263 }
11264
11265 /* Simplify a call to the strcat builtin. DST and SRC are the arguments
11266 to the call.
11267
11268 Return NULL_TREE if no simplification was possible, otherwise return the
11269 simplified form of the call as a tree.
11270
11271 The simplified form may be a constant or other expression which
11272 computes the same value, but in a more efficient manner (including
11273 calls to other builtin functions).
11274
11275 The call may contain arguments which need to be evaluated, but
11276 which are not useful to determine the result of the call. In
11277 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11278 COMPOUND_EXPR will be an argument which must be evaluated.
11279 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11280 COMPOUND_EXPR in the chain will contain the tree for the simplified
11281 form of the builtin function call. */
11282
11283 static tree
11284 fold_builtin_strcat (location_t loc ATTRIBUTE_UNUSED, tree dst, tree src)
11285 {
11286 if (!validate_arg (dst, POINTER_TYPE)
11287 || !validate_arg (src, POINTER_TYPE))
11288 return NULL_TREE;
11289 else
11290 {
11291 const char *p = c_getstr (src);
11292
11293 /* If the string length is zero, return the dst parameter. */
11294 if (p && *p == '\0')
11295 return dst;
11296
11297 if (optimize_insn_for_speed_p ())
11298 {
11299 /* See if we can store by pieces into (dst + strlen(dst)). */
11300 tree newdst, call;
11301 tree strlen_fn = implicit_built_in_decls[BUILT_IN_STRLEN];
11302 tree strcpy_fn = implicit_built_in_decls[BUILT_IN_STRCPY];
11303
11304 if (!strlen_fn || !strcpy_fn)
11305 return NULL_TREE;
11306
11307 /* If we don't have a movstr we don't want to emit an strcpy
11308 call. We have to do that if the length of the source string
11309 isn't computable (in that case we can use memcpy probably
11310 later expanding to a sequence of mov instructions). If we
11311 have movstr instructions we can emit strcpy calls. */
11312 if (!HAVE_movstr)
11313 {
11314 tree len = c_strlen (src, 1);
11315 if (! len || TREE_SIDE_EFFECTS (len))
11316 return NULL_TREE;
11317 }
11318
11319 /* Stabilize the argument list. */
11320 dst = builtin_save_expr (dst);
11321
11322 /* Create strlen (dst). */
11323 newdst = build_call_expr_loc (loc, strlen_fn, 1, dst);
11324 /* Create (dst p+ strlen (dst)). */
11325
11326 newdst = fold_build2_loc (loc, POINTER_PLUS_EXPR,
11327 TREE_TYPE (dst), dst, newdst);
11328 newdst = builtin_save_expr (newdst);
11329
11330 call = build_call_expr_loc (loc, strcpy_fn, 2, newdst, src);
11331 return build2 (COMPOUND_EXPR, TREE_TYPE (dst), call, dst);
11332 }
11333 return NULL_TREE;
11334 }
11335 }
11336
11337 /* Simplify a call to the strncat builtin. DST, SRC, and LEN are the
11338 arguments to the call.
11339
11340 Return NULL_TREE if no simplification was possible, otherwise return the
11341 simplified form of the call as a tree.
11342
11343 The simplified form may be a constant or other expression which
11344 computes the same value, but in a more efficient manner (including
11345 calls to other builtin functions).
11346
11347 The call may contain arguments which need to be evaluated, but
11348 which are not useful to determine the result of the call. In
11349 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11350 COMPOUND_EXPR will be an argument which must be evaluated.
11351 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11352 COMPOUND_EXPR in the chain will contain the tree for the simplified
11353 form of the builtin function call. */
11354
11355 static tree
11356 fold_builtin_strncat (location_t loc, tree dst, tree src, tree len)
11357 {
11358 if (!validate_arg (dst, POINTER_TYPE)
11359 || !validate_arg (src, POINTER_TYPE)
11360 || !validate_arg (len, INTEGER_TYPE))
11361 return NULL_TREE;
11362 else
11363 {
11364 const char *p = c_getstr (src);
11365
11366 /* If the requested length is zero, or the src parameter string
11367 length is zero, return the dst parameter. */
11368 if (integer_zerop (len) || (p && *p == '\0'))
11369 return omit_two_operands_loc (loc, TREE_TYPE (dst), dst, src, len);
11370
11371 /* If the requested len is greater than or equal to the string
11372 length, call strcat. */
11373 if (TREE_CODE (len) == INTEGER_CST && p
11374 && compare_tree_int (len, strlen (p)) >= 0)
11375 {
11376 tree fn = implicit_built_in_decls[BUILT_IN_STRCAT];
11377
11378 /* If the replacement _DECL isn't initialized, don't do the
11379 transformation. */
11380 if (!fn)
11381 return NULL_TREE;
11382
11383 return build_call_expr_loc (loc, fn, 2, dst, src);
11384 }
11385 return NULL_TREE;
11386 }
11387 }
11388
11389 /* Simplify a call to the strspn builtin. S1 and S2 are the arguments
11390 to the call.
11391
11392 Return NULL_TREE if no simplification was possible, otherwise return the
11393 simplified form of the call as a tree.
11394
11395 The simplified form may be a constant or other expression which
11396 computes the same value, but in a more efficient manner (including
11397 calls to other builtin functions).
11398
11399 The call may contain arguments which need to be evaluated, but
11400 which are not useful to determine the result of the call. In
11401 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11402 COMPOUND_EXPR will be an argument which must be evaluated.
11403 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11404 COMPOUND_EXPR in the chain will contain the tree for the simplified
11405 form of the builtin function call. */
11406
11407 static tree
11408 fold_builtin_strspn (location_t loc, tree s1, tree s2)
11409 {
11410 if (!validate_arg (s1, POINTER_TYPE)
11411 || !validate_arg (s2, POINTER_TYPE))
11412 return NULL_TREE;
11413 else
11414 {
11415 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
11416
11417 /* If both arguments are constants, evaluate at compile-time. */
11418 if (p1 && p2)
11419 {
11420 const size_t r = strspn (p1, p2);
11421 return size_int (r);
11422 }
11423
11424 /* If either argument is "", return NULL_TREE. */
11425 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
11426 /* Evaluate and ignore both arguments in case either one has
11427 side-effects. */
11428 return omit_two_operands_loc (loc, size_type_node, size_zero_node,
11429 s1, s2);
11430 return NULL_TREE;
11431 }
11432 }
11433
11434 /* Simplify a call to the strcspn builtin. S1 and S2 are the arguments
11435 to the call.
11436
11437 Return NULL_TREE if no simplification was possible, otherwise return the
11438 simplified form of the call as a tree.
11439
11440 The simplified form may be a constant or other expression which
11441 computes the same value, but in a more efficient manner (including
11442 calls to other builtin functions).
11443
11444 The call may contain arguments which need to be evaluated, but
11445 which are not useful to determine the result of the call. In
11446 this case we return a chain of COMPOUND_EXPRs. The LHS of each
11447 COMPOUND_EXPR will be an argument which must be evaluated.
11448 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
11449 COMPOUND_EXPR in the chain will contain the tree for the simplified
11450 form of the builtin function call. */
11451
11452 static tree
11453 fold_builtin_strcspn (location_t loc, tree s1, tree s2)
11454 {
11455 if (!validate_arg (s1, POINTER_TYPE)
11456 || !validate_arg (s2, POINTER_TYPE))
11457 return NULL_TREE;
11458 else
11459 {
11460 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
11461
11462 /* If both arguments are constants, evaluate at compile-time. */
11463 if (p1 && p2)
11464 {
11465 const size_t r = strcspn (p1, p2);
11466 return size_int (r);
11467 }
11468
11469 /* If the first argument is "", return NULL_TREE. */
11470 if (p1 && *p1 == '\0')
11471 {
11472 /* Evaluate and ignore argument s2 in case it has
11473 side-effects. */
11474 return omit_one_operand_loc (loc, size_type_node,
11475 size_zero_node, s2);
11476 }
11477
11478 /* If the second argument is "", return __builtin_strlen(s1). */
11479 if (p2 && *p2 == '\0')
11480 {
11481 tree fn = implicit_built_in_decls[BUILT_IN_STRLEN];
11482
11483 /* If the replacement _DECL isn't initialized, don't do the
11484 transformation. */
11485 if (!fn)
11486 return NULL_TREE;
11487
11488 return build_call_expr_loc (loc, fn, 1, s1);
11489 }
11490 return NULL_TREE;
11491 }
11492 }
11493
11494 /* Fold a call to the fputs builtin. ARG0 and ARG1 are the arguments
11495 to the call. IGNORE is true if the value returned
11496 by the builtin will be ignored. UNLOCKED is true is true if this
11497 actually a call to fputs_unlocked. If LEN in non-NULL, it represents
11498 the known length of the string. Return NULL_TREE if no simplification
11499 was possible. */
11500
11501 tree
11502 fold_builtin_fputs (location_t loc, tree arg0, tree arg1,
11503 bool ignore, bool unlocked, tree len)
11504 {
11505 /* If we're using an unlocked function, assume the other unlocked
11506 functions exist explicitly. */
11507 tree const fn_fputc = unlocked ? built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
11508 : implicit_built_in_decls[BUILT_IN_FPUTC];
11509 tree const fn_fwrite = unlocked ? built_in_decls[BUILT_IN_FWRITE_UNLOCKED]
11510 : implicit_built_in_decls[BUILT_IN_FWRITE];
11511
11512 /* If the return value is used, don't do the transformation. */
11513 if (!ignore)
11514 return NULL_TREE;
11515
11516 /* Verify the arguments in the original call. */
11517 if (!validate_arg (arg0, POINTER_TYPE)
11518 || !validate_arg (arg1, POINTER_TYPE))
11519 return NULL_TREE;
11520
11521 if (! len)
11522 len = c_strlen (arg0, 0);
11523
11524 /* Get the length of the string passed to fputs. If the length
11525 can't be determined, punt. */
11526 if (!len
11527 || TREE_CODE (len) != INTEGER_CST)
11528 return NULL_TREE;
11529
11530 switch (compare_tree_int (len, 1))
11531 {
11532 case -1: /* length is 0, delete the call entirely . */
11533 return omit_one_operand_loc (loc, integer_type_node,
11534 integer_zero_node, arg1);;
11535
11536 case 0: /* length is 1, call fputc. */
11537 {
11538 const char *p = c_getstr (arg0);
11539
11540 if (p != NULL)
11541 {
11542 if (fn_fputc)
11543 return build_call_expr_loc (loc, fn_fputc, 2,
11544 build_int_cst (NULL_TREE, p[0]), arg1);
11545 else
11546 return NULL_TREE;
11547 }
11548 }
11549 /* FALLTHROUGH */
11550 case 1: /* length is greater than 1, call fwrite. */
11551 {
11552 /* If optimizing for size keep fputs. */
11553 if (optimize_function_for_size_p (cfun))
11554 return NULL_TREE;
11555 /* New argument list transforming fputs(string, stream) to
11556 fwrite(string, 1, len, stream). */
11557 if (fn_fwrite)
11558 return build_call_expr_loc (loc, fn_fwrite, 4, arg0,
11559 size_one_node, len, arg1);
11560 else
11561 return NULL_TREE;
11562 }
11563 default:
11564 gcc_unreachable ();
11565 }
11566 return NULL_TREE;
11567 }
11568
11569 /* Fold the next_arg or va_start call EXP. Returns true if there was an error
11570 produced. False otherwise. This is done so that we don't output the error
11571 or warning twice or three times. */
11572
11573 bool
11574 fold_builtin_next_arg (tree exp, bool va_start_p)
11575 {
11576 tree fntype = TREE_TYPE (current_function_decl);
11577 int nargs = call_expr_nargs (exp);
11578 tree arg;
11579
11580 if (TYPE_ARG_TYPES (fntype) == 0
11581 || (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
11582 == void_type_node))
11583 {
11584 error ("%<va_start%> used in function with fixed args");
11585 return true;
11586 }
11587
11588 if (va_start_p)
11589 {
11590 if (va_start_p && (nargs != 2))
11591 {
11592 error ("wrong number of arguments to function %<va_start%>");
11593 return true;
11594 }
11595 arg = CALL_EXPR_ARG (exp, 1);
11596 }
11597 /* We use __builtin_va_start (ap, 0, 0) or __builtin_next_arg (0, 0)
11598 when we checked the arguments and if needed issued a warning. */
11599 else
11600 {
11601 if (nargs == 0)
11602 {
11603 /* Evidently an out of date version of <stdarg.h>; can't validate
11604 va_start's second argument, but can still work as intended. */
11605 warning (0, "%<__builtin_next_arg%> called without an argument");
11606 return true;
11607 }
11608 else if (nargs > 1)
11609 {
11610 error ("wrong number of arguments to function %<__builtin_next_arg%>");
11611 return true;
11612 }
11613 arg = CALL_EXPR_ARG (exp, 0);
11614 }
11615
11616 if (TREE_CODE (arg) == SSA_NAME)
11617 arg = SSA_NAME_VAR (arg);
11618
11619 /* We destructively modify the call to be __builtin_va_start (ap, 0)
11620 or __builtin_next_arg (0) the first time we see it, after checking
11621 the arguments and if needed issuing a warning. */
11622 if (!integer_zerop (arg))
11623 {
11624 tree last_parm = tree_last (DECL_ARGUMENTS (current_function_decl));
11625
11626 /* Strip off all nops for the sake of the comparison. This
11627 is not quite the same as STRIP_NOPS. It does more.
11628 We must also strip off INDIRECT_EXPR for C++ reference
11629 parameters. */
11630 while (CONVERT_EXPR_P (arg)
11631 || TREE_CODE (arg) == INDIRECT_REF)
11632 arg = TREE_OPERAND (arg, 0);
11633 if (arg != last_parm)
11634 {
11635 /* FIXME: Sometimes with the tree optimizers we can get the
11636 not the last argument even though the user used the last
11637 argument. We just warn and set the arg to be the last
11638 argument so that we will get wrong-code because of
11639 it. */
11640 warning (0, "second parameter of %<va_start%> not last named argument");
11641 }
11642
11643 /* Undefined by C99 7.15.1.4p4 (va_start):
11644 "If the parameter parmN is declared with the register storage
11645 class, with a function or array type, or with a type that is
11646 not compatible with the type that results after application of
11647 the default argument promotions, the behavior is undefined."
11648 */
11649 else if (DECL_REGISTER (arg))
11650 warning (0, "undefined behaviour when second parameter of "
11651 "%<va_start%> is declared with %<register%> storage");
11652
11653 /* We want to verify the second parameter just once before the tree
11654 optimizers are run and then avoid keeping it in the tree,
11655 as otherwise we could warn even for correct code like:
11656 void foo (int i, ...)
11657 { va_list ap; i++; va_start (ap, i); va_end (ap); } */
11658 if (va_start_p)
11659 CALL_EXPR_ARG (exp, 1) = integer_zero_node;
11660 else
11661 CALL_EXPR_ARG (exp, 0) = integer_zero_node;
11662 }
11663 return false;
11664 }
11665
11666
11667 /* Simplify a call to the sprintf builtin with arguments DEST, FMT, and ORIG.
11668 ORIG may be null if this is a 2-argument call. We don't attempt to
11669 simplify calls with more than 3 arguments.
11670
11671 Return NULL_TREE if no simplification was possible, otherwise return the
11672 simplified form of the call as a tree. If IGNORED is true, it means that
11673 the caller does not use the returned value of the function. */
11674
11675 static tree
11676 fold_builtin_sprintf (location_t loc, tree dest, tree fmt,
11677 tree orig, int ignored)
11678 {
11679 tree call, retval;
11680 const char *fmt_str = NULL;
11681
11682 /* Verify the required arguments in the original call. We deal with two
11683 types of sprintf() calls: 'sprintf (str, fmt)' and
11684 'sprintf (dest, "%s", orig)'. */
11685 if (!validate_arg (dest, POINTER_TYPE)
11686 || !validate_arg (fmt, POINTER_TYPE))
11687 return NULL_TREE;
11688 if (orig && !validate_arg (orig, POINTER_TYPE))
11689 return NULL_TREE;
11690
11691 /* Check whether the format is a literal string constant. */
11692 fmt_str = c_getstr (fmt);
11693 if (fmt_str == NULL)
11694 return NULL_TREE;
11695
11696 call = NULL_TREE;
11697 retval = NULL_TREE;
11698
11699 if (!init_target_chars ())
11700 return NULL_TREE;
11701
11702 /* If the format doesn't contain % args or %%, use strcpy. */
11703 if (strchr (fmt_str, target_percent) == NULL)
11704 {
11705 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
11706
11707 if (!fn)
11708 return NULL_TREE;
11709
11710 /* Don't optimize sprintf (buf, "abc", ptr++). */
11711 if (orig)
11712 return NULL_TREE;
11713
11714 /* Convert sprintf (str, fmt) into strcpy (str, fmt) when
11715 'format' is known to contain no % formats. */
11716 call = build_call_expr_loc (loc, fn, 2, dest, fmt);
11717 if (!ignored)
11718 retval = build_int_cst (NULL_TREE, strlen (fmt_str));
11719 }
11720
11721 /* If the format is "%s", use strcpy if the result isn't used. */
11722 else if (fmt_str && strcmp (fmt_str, target_percent_s) == 0)
11723 {
11724 tree fn;
11725 fn = implicit_built_in_decls[BUILT_IN_STRCPY];
11726
11727 if (!fn)
11728 return NULL_TREE;
11729
11730 /* Don't crash on sprintf (str1, "%s"). */
11731 if (!orig)
11732 return NULL_TREE;
11733
11734 /* Convert sprintf (str1, "%s", str2) into strcpy (str1, str2). */
11735 if (!ignored)
11736 {
11737 retval = c_strlen (orig, 1);
11738 if (!retval || TREE_CODE (retval) != INTEGER_CST)
11739 return NULL_TREE;
11740 }
11741 call = build_call_expr_loc (loc, fn, 2, dest, orig);
11742 }
11743
11744 if (call && retval)
11745 {
11746 retval = fold_convert_loc
11747 (loc, TREE_TYPE (TREE_TYPE (implicit_built_in_decls[BUILT_IN_SPRINTF])),
11748 retval);
11749 return build2 (COMPOUND_EXPR, TREE_TYPE (retval), call, retval);
11750 }
11751 else
11752 return call;
11753 }
11754
11755 /* Expand a call EXP to __builtin_object_size. */
11756
11757 rtx
11758 expand_builtin_object_size (tree exp)
11759 {
11760 tree ost;
11761 int object_size_type;
11762 tree fndecl = get_callee_fndecl (exp);
11763
11764 if (!validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
11765 {
11766 error ("%Kfirst argument of %D must be a pointer, second integer constant",
11767 exp, fndecl);
11768 expand_builtin_trap ();
11769 return const0_rtx;
11770 }
11771
11772 ost = CALL_EXPR_ARG (exp, 1);
11773 STRIP_NOPS (ost);
11774
11775 if (TREE_CODE (ost) != INTEGER_CST
11776 || tree_int_cst_sgn (ost) < 0
11777 || compare_tree_int (ost, 3) > 0)
11778 {
11779 error ("%Klast argument of %D is not integer constant between 0 and 3",
11780 exp, fndecl);
11781 expand_builtin_trap ();
11782 return const0_rtx;
11783 }
11784
11785 object_size_type = tree_low_cst (ost, 0);
11786
11787 return object_size_type < 2 ? constm1_rtx : const0_rtx;
11788 }
11789
11790 /* Expand EXP, a call to the __mem{cpy,pcpy,move,set}_chk builtin.
11791 FCODE is the BUILT_IN_* to use.
11792 Return NULL_RTX if we failed; the caller should emit a normal call,
11793 otherwise try to get the result in TARGET, if convenient (and in
11794 mode MODE if that's convenient). */
11795
11796 static rtx
11797 expand_builtin_memory_chk (tree exp, rtx target, enum machine_mode mode,
11798 enum built_in_function fcode)
11799 {
11800 tree dest, src, len, size;
11801
11802 if (!validate_arglist (exp,
11803 POINTER_TYPE,
11804 fcode == BUILT_IN_MEMSET_CHK
11805 ? INTEGER_TYPE : POINTER_TYPE,
11806 INTEGER_TYPE, INTEGER_TYPE, VOID_TYPE))
11807 return NULL_RTX;
11808
11809 dest = CALL_EXPR_ARG (exp, 0);
11810 src = CALL_EXPR_ARG (exp, 1);
11811 len = CALL_EXPR_ARG (exp, 2);
11812 size = CALL_EXPR_ARG (exp, 3);
11813
11814 if (! host_integerp (size, 1))
11815 return NULL_RTX;
11816
11817 if (host_integerp (len, 1) || integer_all_onesp (size))
11818 {
11819 tree fn;
11820
11821 if (! integer_all_onesp (size) && tree_int_cst_lt (size, len))
11822 {
11823 warning_at (tree_nonartificial_location (exp),
11824 0, "%Kcall to %D will always overflow destination buffer",
11825 exp, get_callee_fndecl (exp));
11826 return NULL_RTX;
11827 }
11828
11829 fn = NULL_TREE;
11830 /* If __builtin_mem{cpy,pcpy,move,set}_chk is used, assume
11831 mem{cpy,pcpy,move,set} is available. */
11832 switch (fcode)
11833 {
11834 case BUILT_IN_MEMCPY_CHK:
11835 fn = built_in_decls[BUILT_IN_MEMCPY];
11836 break;
11837 case BUILT_IN_MEMPCPY_CHK:
11838 fn = built_in_decls[BUILT_IN_MEMPCPY];
11839 break;
11840 case BUILT_IN_MEMMOVE_CHK:
11841 fn = built_in_decls[BUILT_IN_MEMMOVE];
11842 break;
11843 case BUILT_IN_MEMSET_CHK:
11844 fn = built_in_decls[BUILT_IN_MEMSET];
11845 break;
11846 default:
11847 break;
11848 }
11849
11850 if (! fn)
11851 return NULL_RTX;
11852
11853 fn = build_call_nofold (fn, 3, dest, src, len);
11854 gcc_assert (TREE_CODE (fn) == CALL_EXPR);
11855 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
11856 return expand_expr (fn, target, mode, EXPAND_NORMAL);
11857 }
11858 else if (fcode == BUILT_IN_MEMSET_CHK)
11859 return NULL_RTX;
11860 else
11861 {
11862 unsigned int dest_align
11863 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
11864
11865 /* If DEST is not a pointer type, call the normal function. */
11866 if (dest_align == 0)
11867 return NULL_RTX;
11868
11869 /* If SRC and DEST are the same (and not volatile), do nothing. */
11870 if (operand_equal_p (src, dest, 0))
11871 {
11872 tree expr;
11873
11874 if (fcode != BUILT_IN_MEMPCPY_CHK)
11875 {
11876 /* Evaluate and ignore LEN in case it has side-effects. */
11877 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
11878 return expand_expr (dest, target, mode, EXPAND_NORMAL);
11879 }
11880
11881 expr = fold_build2 (POINTER_PLUS_EXPR, TREE_TYPE (dest), dest, len);
11882 return expand_expr (expr, target, mode, EXPAND_NORMAL);
11883 }
11884
11885 /* __memmove_chk special case. */
11886 if (fcode == BUILT_IN_MEMMOVE_CHK)
11887 {
11888 unsigned int src_align
11889 = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
11890
11891 if (src_align == 0)
11892 return NULL_RTX;
11893
11894 /* If src is categorized for a readonly section we can use
11895 normal __memcpy_chk. */
11896 if (readonly_data_expr (src))
11897 {
11898 tree fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
11899 if (!fn)
11900 return NULL_RTX;
11901 fn = build_call_nofold (fn, 4, dest, src, len, size);
11902 gcc_assert (TREE_CODE (fn) == CALL_EXPR);
11903 CALL_EXPR_TAILCALL (fn) = CALL_EXPR_TAILCALL (exp);
11904 return expand_expr (fn, target, mode, EXPAND_NORMAL);
11905 }
11906 }
11907 return NULL_RTX;
11908 }
11909 }
11910
11911 /* Emit warning if a buffer overflow is detected at compile time. */
11912
11913 static void
11914 maybe_emit_chk_warning (tree exp, enum built_in_function fcode)
11915 {
11916 int is_strlen = 0;
11917 tree len, size;
11918 location_t loc = tree_nonartificial_location (exp);
11919
11920 switch (fcode)
11921 {
11922 case BUILT_IN_STRCPY_CHK:
11923 case BUILT_IN_STPCPY_CHK:
11924 /* For __strcat_chk the warning will be emitted only if overflowing
11925 by at least strlen (dest) + 1 bytes. */
11926 case BUILT_IN_STRCAT_CHK:
11927 len = CALL_EXPR_ARG (exp, 1);
11928 size = CALL_EXPR_ARG (exp, 2);
11929 is_strlen = 1;
11930 break;
11931 case BUILT_IN_STRNCAT_CHK:
11932 case BUILT_IN_STRNCPY_CHK:
11933 len = CALL_EXPR_ARG (exp, 2);
11934 size = CALL_EXPR_ARG (exp, 3);
11935 break;
11936 case BUILT_IN_SNPRINTF_CHK:
11937 case BUILT_IN_VSNPRINTF_CHK:
11938 len = CALL_EXPR_ARG (exp, 1);
11939 size = CALL_EXPR_ARG (exp, 3);
11940 break;
11941 default:
11942 gcc_unreachable ();
11943 }
11944
11945 if (!len || !size)
11946 return;
11947
11948 if (! host_integerp (size, 1) || integer_all_onesp (size))
11949 return;
11950
11951 if (is_strlen)
11952 {
11953 len = c_strlen (len, 1);
11954 if (! len || ! host_integerp (len, 1) || tree_int_cst_lt (len, size))
11955 return;
11956 }
11957 else if (fcode == BUILT_IN_STRNCAT_CHK)
11958 {
11959 tree src = CALL_EXPR_ARG (exp, 1);
11960 if (! src || ! host_integerp (len, 1) || tree_int_cst_lt (len, size))
11961 return;
11962 src = c_strlen (src, 1);
11963 if (! src || ! host_integerp (src, 1))
11964 {
11965 warning_at (loc, 0, "%Kcall to %D might overflow destination buffer",
11966 exp, get_callee_fndecl (exp));
11967 return;
11968 }
11969 else if (tree_int_cst_lt (src, size))
11970 return;
11971 }
11972 else if (! host_integerp (len, 1) || ! tree_int_cst_lt (size, len))
11973 return;
11974
11975 warning_at (loc, 0, "%Kcall to %D will always overflow destination buffer",
11976 exp, get_callee_fndecl (exp));
11977 }
11978
11979 /* Emit warning if a buffer overflow is detected at compile time
11980 in __sprintf_chk/__vsprintf_chk calls. */
11981
11982 static void
11983 maybe_emit_sprintf_chk_warning (tree exp, enum built_in_function fcode)
11984 {
11985 tree size, len, fmt;
11986 const char *fmt_str;
11987 int nargs = call_expr_nargs (exp);
11988
11989 /* Verify the required arguments in the original call. */
11990
11991 if (nargs < 4)
11992 return;
11993 size = CALL_EXPR_ARG (exp, 2);
11994 fmt = CALL_EXPR_ARG (exp, 3);
11995
11996 if (! host_integerp (size, 1) || integer_all_onesp (size))
11997 return;
11998
11999 /* Check whether the format is a literal string constant. */
12000 fmt_str = c_getstr (fmt);
12001 if (fmt_str == NULL)
12002 return;
12003
12004 if (!init_target_chars ())
12005 return;
12006
12007 /* If the format doesn't contain % args or %%, we know its size. */
12008 if (strchr (fmt_str, target_percent) == 0)
12009 len = build_int_cstu (size_type_node, strlen (fmt_str));
12010 /* If the format is "%s" and first ... argument is a string literal,
12011 we know it too. */
12012 else if (fcode == BUILT_IN_SPRINTF_CHK
12013 && strcmp (fmt_str, target_percent_s) == 0)
12014 {
12015 tree arg;
12016
12017 if (nargs < 5)
12018 return;
12019 arg = CALL_EXPR_ARG (exp, 4);
12020 if (! POINTER_TYPE_P (TREE_TYPE (arg)))
12021 return;
12022
12023 len = c_strlen (arg, 1);
12024 if (!len || ! host_integerp (len, 1))
12025 return;
12026 }
12027 else
12028 return;
12029
12030 if (! tree_int_cst_lt (len, size))
12031 warning_at (tree_nonartificial_location (exp),
12032 0, "%Kcall to %D will always overflow destination buffer",
12033 exp, get_callee_fndecl (exp));
12034 }
12035
12036 /* Emit warning if a free is called with address of a variable. */
12037
12038 static void
12039 maybe_emit_free_warning (tree exp)
12040 {
12041 tree arg = CALL_EXPR_ARG (exp, 0);
12042
12043 STRIP_NOPS (arg);
12044 if (TREE_CODE (arg) != ADDR_EXPR)
12045 return;
12046
12047 arg = get_base_address (TREE_OPERAND (arg, 0));
12048 if (arg == NULL || INDIRECT_REF_P (arg))
12049 return;
12050
12051 if (SSA_VAR_P (arg))
12052 warning_at (tree_nonartificial_location (exp),
12053 0, "%Kattempt to free a non-heap object %qD", exp, arg);
12054 else
12055 warning_at (tree_nonartificial_location (exp),
12056 0, "%Kattempt to free a non-heap object", exp);
12057 }
12058
12059 /* Fold a call to __builtin_object_size with arguments PTR and OST,
12060 if possible. */
12061
12062 tree
12063 fold_builtin_object_size (tree ptr, tree ost)
12064 {
12065 tree ret = NULL_TREE;
12066 int object_size_type;
12067
12068 if (!validate_arg (ptr, POINTER_TYPE)
12069 || !validate_arg (ost, INTEGER_TYPE))
12070 return NULL_TREE;
12071
12072 STRIP_NOPS (ost);
12073
12074 if (TREE_CODE (ost) != INTEGER_CST
12075 || tree_int_cst_sgn (ost) < 0
12076 || compare_tree_int (ost, 3) > 0)
12077 return NULL_TREE;
12078
12079 object_size_type = tree_low_cst (ost, 0);
12080
12081 /* __builtin_object_size doesn't evaluate side-effects in its arguments;
12082 if there are any side-effects, it returns (size_t) -1 for types 0 and 1
12083 and (size_t) 0 for types 2 and 3. */
12084 if (TREE_SIDE_EFFECTS (ptr))
12085 return build_int_cst_type (size_type_node, object_size_type < 2 ? -1 : 0);
12086
12087 if (TREE_CODE (ptr) == ADDR_EXPR)
12088 ret = build_int_cstu (size_type_node,
12089 compute_builtin_object_size (ptr, object_size_type));
12090
12091 else if (TREE_CODE (ptr) == SSA_NAME)
12092 {
12093 unsigned HOST_WIDE_INT bytes;
12094
12095 /* If object size is not known yet, delay folding until
12096 later. Maybe subsequent passes will help determining
12097 it. */
12098 bytes = compute_builtin_object_size (ptr, object_size_type);
12099 if (bytes != (unsigned HOST_WIDE_INT) (object_size_type < 2
12100 ? -1 : 0))
12101 ret = build_int_cstu (size_type_node, bytes);
12102 }
12103
12104 if (ret)
12105 {
12106 unsigned HOST_WIDE_INT low = TREE_INT_CST_LOW (ret);
12107 HOST_WIDE_INT high = TREE_INT_CST_HIGH (ret);
12108 if (fit_double_type (low, high, &low, &high, TREE_TYPE (ret)))
12109 ret = NULL_TREE;
12110 }
12111
12112 return ret;
12113 }
12114
12115 /* Fold a call to the __mem{cpy,pcpy,move,set}_chk builtin.
12116 DEST, SRC, LEN, and SIZE are the arguments to the call.
12117 IGNORE is true, if return value can be ignored. FCODE is the BUILT_IN_*
12118 code of the builtin. If MAXLEN is not NULL, it is maximum length
12119 passed as third argument. */
12120
12121 tree
12122 fold_builtin_memory_chk (location_t loc, tree fndecl,
12123 tree dest, tree src, tree len, tree size,
12124 tree maxlen, bool ignore,
12125 enum built_in_function fcode)
12126 {
12127 tree fn;
12128
12129 if (!validate_arg (dest, POINTER_TYPE)
12130 || !validate_arg (src,
12131 (fcode == BUILT_IN_MEMSET_CHK
12132 ? INTEGER_TYPE : POINTER_TYPE))
12133 || !validate_arg (len, INTEGER_TYPE)
12134 || !validate_arg (size, INTEGER_TYPE))
12135 return NULL_TREE;
12136
12137 /* If SRC and DEST are the same (and not volatile), return DEST
12138 (resp. DEST+LEN for __mempcpy_chk). */
12139 if (fcode != BUILT_IN_MEMSET_CHK && operand_equal_p (src, dest, 0))
12140 {
12141 if (fcode != BUILT_IN_MEMPCPY_CHK)
12142 return omit_one_operand_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)),
12143 dest, len);
12144 else
12145 {
12146 tree temp = fold_build2_loc (loc, POINTER_PLUS_EXPR, TREE_TYPE (dest),
12147 dest, len);
12148 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), temp);
12149 }
12150 }
12151
12152 if (! host_integerp (size, 1))
12153 return NULL_TREE;
12154
12155 if (! integer_all_onesp (size))
12156 {
12157 if (! host_integerp (len, 1))
12158 {
12159 /* If LEN is not constant, try MAXLEN too.
12160 For MAXLEN only allow optimizing into non-_ocs function
12161 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12162 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12163 {
12164 if (fcode == BUILT_IN_MEMPCPY_CHK && ignore)
12165 {
12166 /* (void) __mempcpy_chk () can be optimized into
12167 (void) __memcpy_chk (). */
12168 fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
12169 if (!fn)
12170 return NULL_TREE;
12171
12172 return build_call_expr_loc (loc, fn, 4, dest, src, len, size);
12173 }
12174 return NULL_TREE;
12175 }
12176 }
12177 else
12178 maxlen = len;
12179
12180 if (tree_int_cst_lt (size, maxlen))
12181 return NULL_TREE;
12182 }
12183
12184 fn = NULL_TREE;
12185 /* If __builtin_mem{cpy,pcpy,move,set}_chk is used, assume
12186 mem{cpy,pcpy,move,set} is available. */
12187 switch (fcode)
12188 {
12189 case BUILT_IN_MEMCPY_CHK:
12190 fn = built_in_decls[BUILT_IN_MEMCPY];
12191 break;
12192 case BUILT_IN_MEMPCPY_CHK:
12193 fn = built_in_decls[BUILT_IN_MEMPCPY];
12194 break;
12195 case BUILT_IN_MEMMOVE_CHK:
12196 fn = built_in_decls[BUILT_IN_MEMMOVE];
12197 break;
12198 case BUILT_IN_MEMSET_CHK:
12199 fn = built_in_decls[BUILT_IN_MEMSET];
12200 break;
12201 default:
12202 break;
12203 }
12204
12205 if (!fn)
12206 return NULL_TREE;
12207
12208 return build_call_expr_loc (loc, fn, 3, dest, src, len);
12209 }
12210
12211 /* Fold a call to the __st[rp]cpy_chk builtin.
12212 DEST, SRC, and SIZE are the arguments to the call.
12213 IGNORE is true if return value can be ignored. FCODE is the BUILT_IN_*
12214 code of the builtin. If MAXLEN is not NULL, it is maximum length of
12215 strings passed as second argument. */
12216
12217 tree
12218 fold_builtin_stxcpy_chk (location_t loc, tree fndecl, tree dest,
12219 tree src, tree size,
12220 tree maxlen, bool ignore,
12221 enum built_in_function fcode)
12222 {
12223 tree len, fn;
12224
12225 if (!validate_arg (dest, POINTER_TYPE)
12226 || !validate_arg (src, POINTER_TYPE)
12227 || !validate_arg (size, INTEGER_TYPE))
12228 return NULL_TREE;
12229
12230 /* If SRC and DEST are the same (and not volatile), return DEST. */
12231 if (fcode == BUILT_IN_STRCPY_CHK && operand_equal_p (src, dest, 0))
12232 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest);
12233
12234 if (! host_integerp (size, 1))
12235 return NULL_TREE;
12236
12237 if (! integer_all_onesp (size))
12238 {
12239 len = c_strlen (src, 1);
12240 if (! len || ! host_integerp (len, 1))
12241 {
12242 /* If LEN is not constant, try MAXLEN too.
12243 For MAXLEN only allow optimizing into non-_ocs function
12244 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12245 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12246 {
12247 if (fcode == BUILT_IN_STPCPY_CHK)
12248 {
12249 if (! ignore)
12250 return NULL_TREE;
12251
12252 /* If return value of __stpcpy_chk is ignored,
12253 optimize into __strcpy_chk. */
12254 fn = built_in_decls[BUILT_IN_STRCPY_CHK];
12255 if (!fn)
12256 return NULL_TREE;
12257
12258 return build_call_expr_loc (loc, fn, 3, dest, src, size);
12259 }
12260
12261 if (! len || TREE_SIDE_EFFECTS (len))
12262 return NULL_TREE;
12263
12264 /* If c_strlen returned something, but not a constant,
12265 transform __strcpy_chk into __memcpy_chk. */
12266 fn = built_in_decls[BUILT_IN_MEMCPY_CHK];
12267 if (!fn)
12268 return NULL_TREE;
12269
12270 len = size_binop_loc (loc, PLUS_EXPR, len, ssize_int (1));
12271 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)),
12272 build_call_expr_loc (loc, fn, 4,
12273 dest, src, len, size));
12274 }
12275 }
12276 else
12277 maxlen = len;
12278
12279 if (! tree_int_cst_lt (maxlen, size))
12280 return NULL_TREE;
12281 }
12282
12283 /* If __builtin_st{r,p}cpy_chk is used, assume st{r,p}cpy is available. */
12284 fn = built_in_decls[fcode == BUILT_IN_STPCPY_CHK
12285 ? BUILT_IN_STPCPY : BUILT_IN_STRCPY];
12286 if (!fn)
12287 return NULL_TREE;
12288
12289 return build_call_expr_loc (loc, fn, 2, dest, src);
12290 }
12291
12292 /* Fold a call to the __strncpy_chk builtin. DEST, SRC, LEN, and SIZE
12293 are the arguments to the call. If MAXLEN is not NULL, it is maximum
12294 length passed as third argument. */
12295
12296 tree
12297 fold_builtin_strncpy_chk (location_t loc, tree dest, tree src,
12298 tree len, tree size, tree maxlen)
12299 {
12300 tree fn;
12301
12302 if (!validate_arg (dest, POINTER_TYPE)
12303 || !validate_arg (src, POINTER_TYPE)
12304 || !validate_arg (len, INTEGER_TYPE)
12305 || !validate_arg (size, INTEGER_TYPE))
12306 return NULL_TREE;
12307
12308 if (! host_integerp (size, 1))
12309 return NULL_TREE;
12310
12311 if (! integer_all_onesp (size))
12312 {
12313 if (! host_integerp (len, 1))
12314 {
12315 /* If LEN is not constant, try MAXLEN too.
12316 For MAXLEN only allow optimizing into non-_ocs function
12317 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12318 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12319 return NULL_TREE;
12320 }
12321 else
12322 maxlen = len;
12323
12324 if (tree_int_cst_lt (size, maxlen))
12325 return NULL_TREE;
12326 }
12327
12328 /* If __builtin_strncpy_chk is used, assume strncpy is available. */
12329 fn = built_in_decls[BUILT_IN_STRNCPY];
12330 if (!fn)
12331 return NULL_TREE;
12332
12333 return build_call_expr_loc (loc, fn, 3, dest, src, len);
12334 }
12335
12336 /* Fold a call to the __strcat_chk builtin FNDECL. DEST, SRC, and SIZE
12337 are the arguments to the call. */
12338
12339 static tree
12340 fold_builtin_strcat_chk (location_t loc, tree fndecl, tree dest,
12341 tree src, tree size)
12342 {
12343 tree fn;
12344 const char *p;
12345
12346 if (!validate_arg (dest, POINTER_TYPE)
12347 || !validate_arg (src, POINTER_TYPE)
12348 || !validate_arg (size, INTEGER_TYPE))
12349 return NULL_TREE;
12350
12351 p = c_getstr (src);
12352 /* If the SRC parameter is "", return DEST. */
12353 if (p && *p == '\0')
12354 return omit_one_operand_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
12355
12356 if (! host_integerp (size, 1) || ! integer_all_onesp (size))
12357 return NULL_TREE;
12358
12359 /* If __builtin_strcat_chk is used, assume strcat is available. */
12360 fn = built_in_decls[BUILT_IN_STRCAT];
12361 if (!fn)
12362 return NULL_TREE;
12363
12364 return build_call_expr_loc (loc, fn, 2, dest, src);
12365 }
12366
12367 /* Fold a call to the __strncat_chk builtin with arguments DEST, SRC,
12368 LEN, and SIZE. */
12369
12370 static tree
12371 fold_builtin_strncat_chk (location_t loc, tree fndecl,
12372 tree dest, tree src, tree len, tree size)
12373 {
12374 tree fn;
12375 const char *p;
12376
12377 if (!validate_arg (dest, POINTER_TYPE)
12378 || !validate_arg (src, POINTER_TYPE)
12379 || !validate_arg (size, INTEGER_TYPE)
12380 || !validate_arg (size, INTEGER_TYPE))
12381 return NULL_TREE;
12382
12383 p = c_getstr (src);
12384 /* If the SRC parameter is "" or if LEN is 0, return DEST. */
12385 if (p && *p == '\0')
12386 return omit_one_operand_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest, len);
12387 else if (integer_zerop (len))
12388 return omit_one_operand_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), dest, src);
12389
12390 if (! host_integerp (size, 1))
12391 return NULL_TREE;
12392
12393 if (! integer_all_onesp (size))
12394 {
12395 tree src_len = c_strlen (src, 1);
12396 if (src_len
12397 && host_integerp (src_len, 1)
12398 && host_integerp (len, 1)
12399 && ! tree_int_cst_lt (len, src_len))
12400 {
12401 /* If LEN >= strlen (SRC), optimize into __strcat_chk. */
12402 fn = built_in_decls[BUILT_IN_STRCAT_CHK];
12403 if (!fn)
12404 return NULL_TREE;
12405
12406 return build_call_expr_loc (loc, fn, 3, dest, src, size);
12407 }
12408 return NULL_TREE;
12409 }
12410
12411 /* If __builtin_strncat_chk is used, assume strncat is available. */
12412 fn = built_in_decls[BUILT_IN_STRNCAT];
12413 if (!fn)
12414 return NULL_TREE;
12415
12416 return build_call_expr_loc (loc, fn, 3, dest, src, len);
12417 }
12418
12419 /* Fold a call EXP to __{,v}sprintf_chk. Return NULL_TREE if
12420 a normal call should be emitted rather than expanding the function
12421 inline. FCODE is either BUILT_IN_SPRINTF_CHK or BUILT_IN_VSPRINTF_CHK. */
12422
12423 static tree
12424 fold_builtin_sprintf_chk (location_t loc, tree exp,
12425 enum built_in_function fcode)
12426 {
12427 tree dest, size, len, fn, fmt, flag;
12428 const char *fmt_str;
12429 int nargs = call_expr_nargs (exp);
12430
12431 /* Verify the required arguments in the original call. */
12432 if (nargs < 4)
12433 return NULL_TREE;
12434 dest = CALL_EXPR_ARG (exp, 0);
12435 if (!validate_arg (dest, POINTER_TYPE))
12436 return NULL_TREE;
12437 flag = CALL_EXPR_ARG (exp, 1);
12438 if (!validate_arg (flag, INTEGER_TYPE))
12439 return NULL_TREE;
12440 size = CALL_EXPR_ARG (exp, 2);
12441 if (!validate_arg (size, INTEGER_TYPE))
12442 return NULL_TREE;
12443 fmt = CALL_EXPR_ARG (exp, 3);
12444 if (!validate_arg (fmt, POINTER_TYPE))
12445 return NULL_TREE;
12446
12447 if (! host_integerp (size, 1))
12448 return NULL_TREE;
12449
12450 len = NULL_TREE;
12451
12452 if (!init_target_chars ())
12453 return NULL_TREE;
12454
12455 /* Check whether the format is a literal string constant. */
12456 fmt_str = c_getstr (fmt);
12457 if (fmt_str != NULL)
12458 {
12459 /* If the format doesn't contain % args or %%, we know the size. */
12460 if (strchr (fmt_str, target_percent) == 0)
12461 {
12462 if (fcode != BUILT_IN_SPRINTF_CHK || nargs == 4)
12463 len = build_int_cstu (size_type_node, strlen (fmt_str));
12464 }
12465 /* If the format is "%s" and first ... argument is a string literal,
12466 we know the size too. */
12467 else if (fcode == BUILT_IN_SPRINTF_CHK
12468 && strcmp (fmt_str, target_percent_s) == 0)
12469 {
12470 tree arg;
12471
12472 if (nargs == 5)
12473 {
12474 arg = CALL_EXPR_ARG (exp, 4);
12475 if (validate_arg (arg, POINTER_TYPE))
12476 {
12477 len = c_strlen (arg, 1);
12478 if (! len || ! host_integerp (len, 1))
12479 len = NULL_TREE;
12480 }
12481 }
12482 }
12483 }
12484
12485 if (! integer_all_onesp (size))
12486 {
12487 if (! len || ! tree_int_cst_lt (len, size))
12488 return NULL_TREE;
12489 }
12490
12491 /* Only convert __{,v}sprintf_chk to {,v}sprintf if flag is 0
12492 or if format doesn't contain % chars or is "%s". */
12493 if (! integer_zerop (flag))
12494 {
12495 if (fmt_str == NULL)
12496 return NULL_TREE;
12497 if (strchr (fmt_str, target_percent) != NULL
12498 && strcmp (fmt_str, target_percent_s))
12499 return NULL_TREE;
12500 }
12501
12502 /* If __builtin_{,v}sprintf_chk is used, assume {,v}sprintf is available. */
12503 fn = built_in_decls[fcode == BUILT_IN_VSPRINTF_CHK
12504 ? BUILT_IN_VSPRINTF : BUILT_IN_SPRINTF];
12505 if (!fn)
12506 return NULL_TREE;
12507
12508 return rewrite_call_expr (loc, exp, 4, fn, 2, dest, fmt);
12509 }
12510
12511 /* Fold a call EXP to {,v}snprintf. Return NULL_TREE if
12512 a normal call should be emitted rather than expanding the function
12513 inline. FCODE is either BUILT_IN_SNPRINTF_CHK or
12514 BUILT_IN_VSNPRINTF_CHK. If MAXLEN is not NULL, it is maximum length
12515 passed as second argument. */
12516
12517 tree
12518 fold_builtin_snprintf_chk (location_t loc, tree exp, tree maxlen,
12519 enum built_in_function fcode)
12520 {
12521 tree dest, size, len, fn, fmt, flag;
12522 const char *fmt_str;
12523
12524 /* Verify the required arguments in the original call. */
12525 if (call_expr_nargs (exp) < 5)
12526 return NULL_TREE;
12527 dest = CALL_EXPR_ARG (exp, 0);
12528 if (!validate_arg (dest, POINTER_TYPE))
12529 return NULL_TREE;
12530 len = CALL_EXPR_ARG (exp, 1);
12531 if (!validate_arg (len, INTEGER_TYPE))
12532 return NULL_TREE;
12533 flag = CALL_EXPR_ARG (exp, 2);
12534 if (!validate_arg (flag, INTEGER_TYPE))
12535 return NULL_TREE;
12536 size = CALL_EXPR_ARG (exp, 3);
12537 if (!validate_arg (size, INTEGER_TYPE))
12538 return NULL_TREE;
12539 fmt = CALL_EXPR_ARG (exp, 4);
12540 if (!validate_arg (fmt, POINTER_TYPE))
12541 return NULL_TREE;
12542
12543 if (! host_integerp (size, 1))
12544 return NULL_TREE;
12545
12546 if (! integer_all_onesp (size))
12547 {
12548 if (! host_integerp (len, 1))
12549 {
12550 /* If LEN is not constant, try MAXLEN too.
12551 For MAXLEN only allow optimizing into non-_ocs function
12552 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
12553 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
12554 return NULL_TREE;
12555 }
12556 else
12557 maxlen = len;
12558
12559 if (tree_int_cst_lt (size, maxlen))
12560 return NULL_TREE;
12561 }
12562
12563 if (!init_target_chars ())
12564 return NULL_TREE;
12565
12566 /* Only convert __{,v}snprintf_chk to {,v}snprintf if flag is 0
12567 or if format doesn't contain % chars or is "%s". */
12568 if (! integer_zerop (flag))
12569 {
12570 fmt_str = c_getstr (fmt);
12571 if (fmt_str == NULL)
12572 return NULL_TREE;
12573 if (strchr (fmt_str, target_percent) != NULL
12574 && strcmp (fmt_str, target_percent_s))
12575 return NULL_TREE;
12576 }
12577
12578 /* If __builtin_{,v}snprintf_chk is used, assume {,v}snprintf is
12579 available. */
12580 fn = built_in_decls[fcode == BUILT_IN_VSNPRINTF_CHK
12581 ? BUILT_IN_VSNPRINTF : BUILT_IN_SNPRINTF];
12582 if (!fn)
12583 return NULL_TREE;
12584
12585 return rewrite_call_expr (loc, exp, 5, fn, 3, dest, len, fmt);
12586 }
12587
12588 /* Fold a call to the {,v}printf{,_unlocked} and __{,v}printf_chk builtins.
12589 FMT and ARG are the arguments to the call; we don't fold cases with
12590 more than 2 arguments, and ARG may be null if this is a 1-argument case.
12591
12592 Return NULL_TREE if no simplification was possible, otherwise return the
12593 simplified form of the call as a tree. FCODE is the BUILT_IN_*
12594 code of the function to be simplified. */
12595
12596 static tree
12597 fold_builtin_printf (location_t loc, tree fndecl, tree fmt,
12598 tree arg, bool ignore,
12599 enum built_in_function fcode)
12600 {
12601 tree fn_putchar, fn_puts, newarg, call = NULL_TREE;
12602 const char *fmt_str = NULL;
12603
12604 /* If the return value is used, don't do the transformation. */
12605 if (! ignore)
12606 return NULL_TREE;
12607
12608 /* Verify the required arguments in the original call. */
12609 if (!validate_arg (fmt, POINTER_TYPE))
12610 return NULL_TREE;
12611
12612 /* Check whether the format is a literal string constant. */
12613 fmt_str = c_getstr (fmt);
12614 if (fmt_str == NULL)
12615 return NULL_TREE;
12616
12617 if (fcode == BUILT_IN_PRINTF_UNLOCKED)
12618 {
12619 /* If we're using an unlocked function, assume the other
12620 unlocked functions exist explicitly. */
12621 fn_putchar = built_in_decls[BUILT_IN_PUTCHAR_UNLOCKED];
12622 fn_puts = built_in_decls[BUILT_IN_PUTS_UNLOCKED];
12623 }
12624 else
12625 {
12626 fn_putchar = implicit_built_in_decls[BUILT_IN_PUTCHAR];
12627 fn_puts = implicit_built_in_decls[BUILT_IN_PUTS];
12628 }
12629
12630 if (!init_target_chars ())
12631 return NULL_TREE;
12632
12633 if (strcmp (fmt_str, target_percent_s) == 0
12634 || strchr (fmt_str, target_percent) == NULL)
12635 {
12636 const char *str;
12637
12638 if (strcmp (fmt_str, target_percent_s) == 0)
12639 {
12640 if (fcode == BUILT_IN_VPRINTF || fcode == BUILT_IN_VPRINTF_CHK)
12641 return NULL_TREE;
12642
12643 if (!arg || !validate_arg (arg, POINTER_TYPE))
12644 return NULL_TREE;
12645
12646 str = c_getstr (arg);
12647 if (str == NULL)
12648 return NULL_TREE;
12649 }
12650 else
12651 {
12652 /* The format specifier doesn't contain any '%' characters. */
12653 if (fcode != BUILT_IN_VPRINTF && fcode != BUILT_IN_VPRINTF_CHK
12654 && arg)
12655 return NULL_TREE;
12656 str = fmt_str;
12657 }
12658
12659 /* If the string was "", printf does nothing. */
12660 if (str[0] == '\0')
12661 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), 0);
12662
12663 /* If the string has length of 1, call putchar. */
12664 if (str[1] == '\0')
12665 {
12666 /* Given printf("c"), (where c is any one character,)
12667 convert "c"[0] to an int and pass that to the replacement
12668 function. */
12669 newarg = build_int_cst (NULL_TREE, str[0]);
12670 if (fn_putchar)
12671 call = build_call_expr_loc (loc, fn_putchar, 1, newarg);
12672 }
12673 else
12674 {
12675 /* If the string was "string\n", call puts("string"). */
12676 size_t len = strlen (str);
12677 if ((unsigned char)str[len - 1] == target_newline)
12678 {
12679 /* Create a NUL-terminated string that's one char shorter
12680 than the original, stripping off the trailing '\n'. */
12681 char *newstr = XALLOCAVEC (char, len);
12682 memcpy (newstr, str, len - 1);
12683 newstr[len - 1] = 0;
12684
12685 newarg = build_string_literal (len, newstr);
12686 if (fn_puts)
12687 call = build_call_expr_loc (loc, fn_puts, 1, newarg);
12688 }
12689 else
12690 /* We'd like to arrange to call fputs(string,stdout) here,
12691 but we need stdout and don't have a way to get it yet. */
12692 return NULL_TREE;
12693 }
12694 }
12695
12696 /* The other optimizations can be done only on the non-va_list variants. */
12697 else if (fcode == BUILT_IN_VPRINTF || fcode == BUILT_IN_VPRINTF_CHK)
12698 return NULL_TREE;
12699
12700 /* If the format specifier was "%s\n", call __builtin_puts(arg). */
12701 else if (strcmp (fmt_str, target_percent_s_newline) == 0)
12702 {
12703 if (!arg || !validate_arg (arg, POINTER_TYPE))
12704 return NULL_TREE;
12705 if (fn_puts)
12706 call = build_call_expr_loc (loc, fn_puts, 1, arg);
12707 }
12708
12709 /* If the format specifier was "%c", call __builtin_putchar(arg). */
12710 else if (strcmp (fmt_str, target_percent_c) == 0)
12711 {
12712 if (!arg || !validate_arg (arg, INTEGER_TYPE))
12713 return NULL_TREE;
12714 if (fn_putchar)
12715 call = build_call_expr_loc (loc, fn_putchar, 1, arg);
12716 }
12717
12718 if (!call)
12719 return NULL_TREE;
12720
12721 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), call);
12722 }
12723
12724 /* Fold a call to the {,v}fprintf{,_unlocked} and __{,v}printf_chk builtins.
12725 FP, FMT, and ARG are the arguments to the call. We don't fold calls with
12726 more than 3 arguments, and ARG may be null in the 2-argument case.
12727
12728 Return NULL_TREE if no simplification was possible, otherwise return the
12729 simplified form of the call as a tree. FCODE is the BUILT_IN_*
12730 code of the function to be simplified. */
12731
12732 static tree
12733 fold_builtin_fprintf (location_t loc, tree fndecl, tree fp,
12734 tree fmt, tree arg, bool ignore,
12735 enum built_in_function fcode)
12736 {
12737 tree fn_fputc, fn_fputs, call = NULL_TREE;
12738 const char *fmt_str = NULL;
12739
12740 /* If the return value is used, don't do the transformation. */
12741 if (! ignore)
12742 return NULL_TREE;
12743
12744 /* Verify the required arguments in the original call. */
12745 if (!validate_arg (fp, POINTER_TYPE))
12746 return NULL_TREE;
12747 if (!validate_arg (fmt, POINTER_TYPE))
12748 return NULL_TREE;
12749
12750 /* Check whether the format is a literal string constant. */
12751 fmt_str = c_getstr (fmt);
12752 if (fmt_str == NULL)
12753 return NULL_TREE;
12754
12755 if (fcode == BUILT_IN_FPRINTF_UNLOCKED)
12756 {
12757 /* If we're using an unlocked function, assume the other
12758 unlocked functions exist explicitly. */
12759 fn_fputc = built_in_decls[BUILT_IN_FPUTC_UNLOCKED];
12760 fn_fputs = built_in_decls[BUILT_IN_FPUTS_UNLOCKED];
12761 }
12762 else
12763 {
12764 fn_fputc = implicit_built_in_decls[BUILT_IN_FPUTC];
12765 fn_fputs = implicit_built_in_decls[BUILT_IN_FPUTS];
12766 }
12767
12768 if (!init_target_chars ())
12769 return NULL_TREE;
12770
12771 /* If the format doesn't contain % args or %%, use strcpy. */
12772 if (strchr (fmt_str, target_percent) == NULL)
12773 {
12774 if (fcode != BUILT_IN_VFPRINTF && fcode != BUILT_IN_VFPRINTF_CHK
12775 && arg)
12776 return NULL_TREE;
12777
12778 /* If the format specifier was "", fprintf does nothing. */
12779 if (fmt_str[0] == '\0')
12780 {
12781 /* If FP has side-effects, just wait until gimplification is
12782 done. */
12783 if (TREE_SIDE_EFFECTS (fp))
12784 return NULL_TREE;
12785
12786 return build_int_cst (TREE_TYPE (TREE_TYPE (fndecl)), 0);
12787 }
12788
12789 /* When "string" doesn't contain %, replace all cases of
12790 fprintf (fp, string) with fputs (string, fp). The fputs
12791 builtin will take care of special cases like length == 1. */
12792 if (fn_fputs)
12793 call = build_call_expr_loc (loc, fn_fputs, 2, fmt, fp);
12794 }
12795
12796 /* The other optimizations can be done only on the non-va_list variants. */
12797 else if (fcode == BUILT_IN_VFPRINTF || fcode == BUILT_IN_VFPRINTF_CHK)
12798 return NULL_TREE;
12799
12800 /* If the format specifier was "%s", call __builtin_fputs (arg, fp). */
12801 else if (strcmp (fmt_str, target_percent_s) == 0)
12802 {
12803 if (!arg || !validate_arg (arg, POINTER_TYPE))
12804 return NULL_TREE;
12805 if (fn_fputs)
12806 call = build_call_expr_loc (loc, fn_fputs, 2, arg, fp);
12807 }
12808
12809 /* If the format specifier was "%c", call __builtin_fputc (arg, fp). */
12810 else if (strcmp (fmt_str, target_percent_c) == 0)
12811 {
12812 if (!arg || !validate_arg (arg, INTEGER_TYPE))
12813 return NULL_TREE;
12814 if (fn_fputc)
12815 call = build_call_expr_loc (loc, fn_fputc, 2, arg, fp);
12816 }
12817
12818 if (!call)
12819 return NULL_TREE;
12820 return fold_convert_loc (loc, TREE_TYPE (TREE_TYPE (fndecl)), call);
12821 }
12822
12823 /* Initialize format string characters in the target charset. */
12824
12825 static bool
12826 init_target_chars (void)
12827 {
12828 static bool init;
12829 if (!init)
12830 {
12831 target_newline = lang_hooks.to_target_charset ('\n');
12832 target_percent = lang_hooks.to_target_charset ('%');
12833 target_c = lang_hooks.to_target_charset ('c');
12834 target_s = lang_hooks.to_target_charset ('s');
12835 if (target_newline == 0 || target_percent == 0 || target_c == 0
12836 || target_s == 0)
12837 return false;
12838
12839 target_percent_c[0] = target_percent;
12840 target_percent_c[1] = target_c;
12841 target_percent_c[2] = '\0';
12842
12843 target_percent_s[0] = target_percent;
12844 target_percent_s[1] = target_s;
12845 target_percent_s[2] = '\0';
12846
12847 target_percent_s_newline[0] = target_percent;
12848 target_percent_s_newline[1] = target_s;
12849 target_percent_s_newline[2] = target_newline;
12850 target_percent_s_newline[3] = '\0';
12851
12852 init = true;
12853 }
12854 return true;
12855 }
12856
12857 /* Helper function for do_mpfr_arg*(). Ensure M is a normal number
12858 and no overflow/underflow occurred. INEXACT is true if M was not
12859 exactly calculated. TYPE is the tree type for the result. This
12860 function assumes that you cleared the MPFR flags and then
12861 calculated M to see if anything subsequently set a flag prior to
12862 entering this function. Return NULL_TREE if any checks fail. */
12863
12864 static tree
12865 do_mpfr_ckconv (mpfr_srcptr m, tree type, int inexact)
12866 {
12867 /* Proceed iff we get a normal number, i.e. not NaN or Inf and no
12868 overflow/underflow occurred. If -frounding-math, proceed iff the
12869 result of calling FUNC was exact. */
12870 if (mpfr_number_p (m) && !mpfr_overflow_p () && !mpfr_underflow_p ()
12871 && (!flag_rounding_math || !inexact))
12872 {
12873 REAL_VALUE_TYPE rr;
12874
12875 real_from_mpfr (&rr, m, type, GMP_RNDN);
12876 /* Proceed iff GCC's REAL_VALUE_TYPE can hold the MPFR value,
12877 check for overflow/underflow. If the REAL_VALUE_TYPE is zero
12878 but the mpft_t is not, then we underflowed in the
12879 conversion. */
12880 if (real_isfinite (&rr)
12881 && (rr.cl == rvc_zero) == (mpfr_zero_p (m) != 0))
12882 {
12883 REAL_VALUE_TYPE rmode;
12884
12885 real_convert (&rmode, TYPE_MODE (type), &rr);
12886 /* Proceed iff the specified mode can hold the value. */
12887 if (real_identical (&rmode, &rr))
12888 return build_real (type, rmode);
12889 }
12890 }
12891 return NULL_TREE;
12892 }
12893
12894 /* Helper function for do_mpc_arg*(). Ensure M is a normal complex
12895 number and no overflow/underflow occurred. INEXACT is true if M
12896 was not exactly calculated. TYPE is the tree type for the result.
12897 This function assumes that you cleared the MPFR flags and then
12898 calculated M to see if anything subsequently set a flag prior to
12899 entering this function. Return NULL_TREE if any checks fail, if
12900 FORCE_CONVERT is true, then bypass the checks. */
12901
12902 static tree
12903 do_mpc_ckconv (mpc_srcptr m, tree type, int inexact, int force_convert)
12904 {
12905 /* Proceed iff we get a normal number, i.e. not NaN or Inf and no
12906 overflow/underflow occurred. If -frounding-math, proceed iff the
12907 result of calling FUNC was exact. */
12908 if (force_convert
12909 || (mpfr_number_p (mpc_realref (m)) && mpfr_number_p (mpc_imagref (m))
12910 && !mpfr_overflow_p () && !mpfr_underflow_p ()
12911 && (!flag_rounding_math || !inexact)))
12912 {
12913 REAL_VALUE_TYPE re, im;
12914
12915 real_from_mpfr (&re, mpc_realref (m), TREE_TYPE (type), GMP_RNDN);
12916 real_from_mpfr (&im, mpc_imagref (m), TREE_TYPE (type), GMP_RNDN);
12917 /* Proceed iff GCC's REAL_VALUE_TYPE can hold the MPFR values,
12918 check for overflow/underflow. If the REAL_VALUE_TYPE is zero
12919 but the mpft_t is not, then we underflowed in the
12920 conversion. */
12921 if (force_convert
12922 || (real_isfinite (&re) && real_isfinite (&im)
12923 && (re.cl == rvc_zero) == (mpfr_zero_p (mpc_realref (m)) != 0)
12924 && (im.cl == rvc_zero) == (mpfr_zero_p (mpc_imagref (m)) != 0)))
12925 {
12926 REAL_VALUE_TYPE re_mode, im_mode;
12927
12928 real_convert (&re_mode, TYPE_MODE (TREE_TYPE (type)), &re);
12929 real_convert (&im_mode, TYPE_MODE (TREE_TYPE (type)), &im);
12930 /* Proceed iff the specified mode can hold the value. */
12931 if (force_convert
12932 || (real_identical (&re_mode, &re)
12933 && real_identical (&im_mode, &im)))
12934 return build_complex (type, build_real (TREE_TYPE (type), re_mode),
12935 build_real (TREE_TYPE (type), im_mode));
12936 }
12937 }
12938 return NULL_TREE;
12939 }
12940
12941 /* If argument ARG is a REAL_CST, call the one-argument mpfr function
12942 FUNC on it and return the resulting value as a tree with type TYPE.
12943 If MIN and/or MAX are not NULL, then the supplied ARG must be
12944 within those bounds. If INCLUSIVE is true, then MIN/MAX are
12945 acceptable values, otherwise they are not. The mpfr precision is
12946 set to the precision of TYPE. We assume that function FUNC returns
12947 zero if the result could be calculated exactly within the requested
12948 precision. */
12949
12950 static tree
12951 do_mpfr_arg1 (tree arg, tree type, int (*func)(mpfr_ptr, mpfr_srcptr, mp_rnd_t),
12952 const REAL_VALUE_TYPE *min, const REAL_VALUE_TYPE *max,
12953 bool inclusive)
12954 {
12955 tree result = NULL_TREE;
12956
12957 STRIP_NOPS (arg);
12958
12959 /* To proceed, MPFR must exactly represent the target floating point
12960 format, which only happens when the target base equals two. */
12961 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
12962 && TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg))
12963 {
12964 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg);
12965
12966 if (real_isfinite (ra)
12967 && (!min || real_compare (inclusive ? GE_EXPR: GT_EXPR , ra, min))
12968 && (!max || real_compare (inclusive ? LE_EXPR: LT_EXPR , ra, max)))
12969 {
12970 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
12971 const int prec = fmt->p;
12972 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
12973 int inexact;
12974 mpfr_t m;
12975
12976 mpfr_init2 (m, prec);
12977 mpfr_from_real (m, ra, GMP_RNDN);
12978 mpfr_clear_flags ();
12979 inexact = func (m, m, rnd);
12980 result = do_mpfr_ckconv (m, type, inexact);
12981 mpfr_clear (m);
12982 }
12983 }
12984
12985 return result;
12986 }
12987
12988 /* If argument ARG is a REAL_CST, call the two-argument mpfr function
12989 FUNC on it and return the resulting value as a tree with type TYPE.
12990 The mpfr precision is set to the precision of TYPE. We assume that
12991 function FUNC returns zero if the result could be calculated
12992 exactly within the requested precision. */
12993
12994 static tree
12995 do_mpfr_arg2 (tree arg1, tree arg2, tree type,
12996 int (*func)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t))
12997 {
12998 tree result = NULL_TREE;
12999
13000 STRIP_NOPS (arg1);
13001 STRIP_NOPS (arg2);
13002
13003 /* To proceed, MPFR must exactly represent the target floating point
13004 format, which only happens when the target base equals two. */
13005 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13006 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1)
13007 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2))
13008 {
13009 const REAL_VALUE_TYPE *const ra1 = &TREE_REAL_CST (arg1);
13010 const REAL_VALUE_TYPE *const ra2 = &TREE_REAL_CST (arg2);
13011
13012 if (real_isfinite (ra1) && real_isfinite (ra2))
13013 {
13014 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13015 const int prec = fmt->p;
13016 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13017 int inexact;
13018 mpfr_t m1, m2;
13019
13020 mpfr_inits2 (prec, m1, m2, NULL);
13021 mpfr_from_real (m1, ra1, GMP_RNDN);
13022 mpfr_from_real (m2, ra2, GMP_RNDN);
13023 mpfr_clear_flags ();
13024 inexact = func (m1, m1, m2, rnd);
13025 result = do_mpfr_ckconv (m1, type, inexact);
13026 mpfr_clears (m1, m2, NULL);
13027 }
13028 }
13029
13030 return result;
13031 }
13032
13033 /* If argument ARG is a REAL_CST, call the three-argument mpfr function
13034 FUNC on it and return the resulting value as a tree with type TYPE.
13035 The mpfr precision is set to the precision of TYPE. We assume that
13036 function FUNC returns zero if the result could be calculated
13037 exactly within the requested precision. */
13038
13039 static tree
13040 do_mpfr_arg3 (tree arg1, tree arg2, tree arg3, tree type,
13041 int (*func)(mpfr_ptr, mpfr_srcptr, mpfr_srcptr, mpfr_srcptr, mp_rnd_t))
13042 {
13043 tree result = NULL_TREE;
13044
13045 STRIP_NOPS (arg1);
13046 STRIP_NOPS (arg2);
13047 STRIP_NOPS (arg3);
13048
13049 /* To proceed, MPFR must exactly represent the target floating point
13050 format, which only happens when the target base equals two. */
13051 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13052 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1)
13053 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2)
13054 && TREE_CODE (arg3) == REAL_CST && !TREE_OVERFLOW (arg3))
13055 {
13056 const REAL_VALUE_TYPE *const ra1 = &TREE_REAL_CST (arg1);
13057 const REAL_VALUE_TYPE *const ra2 = &TREE_REAL_CST (arg2);
13058 const REAL_VALUE_TYPE *const ra3 = &TREE_REAL_CST (arg3);
13059
13060 if (real_isfinite (ra1) && real_isfinite (ra2) && real_isfinite (ra3))
13061 {
13062 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13063 const int prec = fmt->p;
13064 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13065 int inexact;
13066 mpfr_t m1, m2, m3;
13067
13068 mpfr_inits2 (prec, m1, m2, m3, NULL);
13069 mpfr_from_real (m1, ra1, GMP_RNDN);
13070 mpfr_from_real (m2, ra2, GMP_RNDN);
13071 mpfr_from_real (m3, ra3, GMP_RNDN);
13072 mpfr_clear_flags ();
13073 inexact = func (m1, m1, m2, m3, rnd);
13074 result = do_mpfr_ckconv (m1, type, inexact);
13075 mpfr_clears (m1, m2, m3, NULL);
13076 }
13077 }
13078
13079 return result;
13080 }
13081
13082 /* If argument ARG is a REAL_CST, call mpfr_sin_cos() on it and set
13083 the pointers *(ARG_SINP) and *(ARG_COSP) to the resulting values.
13084 If ARG_SINP and ARG_COSP are NULL then the result is returned
13085 as a complex value.
13086 The type is taken from the type of ARG and is used for setting the
13087 precision of the calculation and results. */
13088
13089 static tree
13090 do_mpfr_sincos (tree arg, tree arg_sinp, tree arg_cosp)
13091 {
13092 tree const type = TREE_TYPE (arg);
13093 tree result = NULL_TREE;
13094
13095 STRIP_NOPS (arg);
13096
13097 /* To proceed, MPFR must exactly represent the target floating point
13098 format, which only happens when the target base equals two. */
13099 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13100 && TREE_CODE (arg) == REAL_CST
13101 && !TREE_OVERFLOW (arg))
13102 {
13103 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg);
13104
13105 if (real_isfinite (ra))
13106 {
13107 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13108 const int prec = fmt->p;
13109 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13110 tree result_s, result_c;
13111 int inexact;
13112 mpfr_t m, ms, mc;
13113
13114 mpfr_inits2 (prec, m, ms, mc, NULL);
13115 mpfr_from_real (m, ra, GMP_RNDN);
13116 mpfr_clear_flags ();
13117 inexact = mpfr_sin_cos (ms, mc, m, rnd);
13118 result_s = do_mpfr_ckconv (ms, type, inexact);
13119 result_c = do_mpfr_ckconv (mc, type, inexact);
13120 mpfr_clears (m, ms, mc, NULL);
13121 if (result_s && result_c)
13122 {
13123 /* If we are to return in a complex value do so. */
13124 if (!arg_sinp && !arg_cosp)
13125 return build_complex (build_complex_type (type),
13126 result_c, result_s);
13127
13128 /* Dereference the sin/cos pointer arguments. */
13129 arg_sinp = build_fold_indirect_ref (arg_sinp);
13130 arg_cosp = build_fold_indirect_ref (arg_cosp);
13131 /* Proceed if valid pointer type were passed in. */
13132 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg_sinp)) == TYPE_MAIN_VARIANT (type)
13133 && TYPE_MAIN_VARIANT (TREE_TYPE (arg_cosp)) == TYPE_MAIN_VARIANT (type))
13134 {
13135 /* Set the values. */
13136 result_s = fold_build2 (MODIFY_EXPR, type, arg_sinp,
13137 result_s);
13138 TREE_SIDE_EFFECTS (result_s) = 1;
13139 result_c = fold_build2 (MODIFY_EXPR, type, arg_cosp,
13140 result_c);
13141 TREE_SIDE_EFFECTS (result_c) = 1;
13142 /* Combine the assignments into a compound expr. */
13143 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
13144 result_s, result_c));
13145 }
13146 }
13147 }
13148 }
13149 return result;
13150 }
13151
13152 /* If argument ARG1 is an INTEGER_CST and ARG2 is a REAL_CST, call the
13153 two-argument mpfr order N Bessel function FUNC on them and return
13154 the resulting value as a tree with type TYPE. The mpfr precision
13155 is set to the precision of TYPE. We assume that function FUNC
13156 returns zero if the result could be calculated exactly within the
13157 requested precision. */
13158 static tree
13159 do_mpfr_bessel_n (tree arg1, tree arg2, tree type,
13160 int (*func)(mpfr_ptr, long, mpfr_srcptr, mp_rnd_t),
13161 const REAL_VALUE_TYPE *min, bool inclusive)
13162 {
13163 tree result = NULL_TREE;
13164
13165 STRIP_NOPS (arg1);
13166 STRIP_NOPS (arg2);
13167
13168 /* To proceed, MPFR must exactly represent the target floating point
13169 format, which only happens when the target base equals two. */
13170 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13171 && host_integerp (arg1, 0)
13172 && TREE_CODE (arg2) == REAL_CST && !TREE_OVERFLOW (arg2))
13173 {
13174 const HOST_WIDE_INT n = tree_low_cst(arg1, 0);
13175 const REAL_VALUE_TYPE *const ra = &TREE_REAL_CST (arg2);
13176
13177 if (n == (long)n
13178 && real_isfinite (ra)
13179 && (!min || real_compare (inclusive ? GE_EXPR: GT_EXPR , ra, min)))
13180 {
13181 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13182 const int prec = fmt->p;
13183 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13184 int inexact;
13185 mpfr_t m;
13186
13187 mpfr_init2 (m, prec);
13188 mpfr_from_real (m, ra, GMP_RNDN);
13189 mpfr_clear_flags ();
13190 inexact = func (m, n, m, rnd);
13191 result = do_mpfr_ckconv (m, type, inexact);
13192 mpfr_clear (m);
13193 }
13194 }
13195
13196 return result;
13197 }
13198
13199 /* If arguments ARG0 and ARG1 are REAL_CSTs, call mpfr_remquo() to set
13200 the pointer *(ARG_QUO) and return the result. The type is taken
13201 from the type of ARG0 and is used for setting the precision of the
13202 calculation and results. */
13203
13204 static tree
13205 do_mpfr_remquo (tree arg0, tree arg1, tree arg_quo)
13206 {
13207 tree const type = TREE_TYPE (arg0);
13208 tree result = NULL_TREE;
13209
13210 STRIP_NOPS (arg0);
13211 STRIP_NOPS (arg1);
13212
13213 /* To proceed, MPFR must exactly represent the target floating point
13214 format, which only happens when the target base equals two. */
13215 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13216 && TREE_CODE (arg0) == REAL_CST && !TREE_OVERFLOW (arg0)
13217 && TREE_CODE (arg1) == REAL_CST && !TREE_OVERFLOW (arg1))
13218 {
13219 const REAL_VALUE_TYPE *const ra0 = TREE_REAL_CST_PTR (arg0);
13220 const REAL_VALUE_TYPE *const ra1 = TREE_REAL_CST_PTR (arg1);
13221
13222 if (real_isfinite (ra0) && real_isfinite (ra1))
13223 {
13224 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13225 const int prec = fmt->p;
13226 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13227 tree result_rem;
13228 long integer_quo;
13229 mpfr_t m0, m1;
13230
13231 mpfr_inits2 (prec, m0, m1, NULL);
13232 mpfr_from_real (m0, ra0, GMP_RNDN);
13233 mpfr_from_real (m1, ra1, GMP_RNDN);
13234 mpfr_clear_flags ();
13235 mpfr_remquo (m0, &integer_quo, m0, m1, rnd);
13236 /* Remquo is independent of the rounding mode, so pass
13237 inexact=0 to do_mpfr_ckconv(). */
13238 result_rem = do_mpfr_ckconv (m0, type, /*inexact=*/ 0);
13239 mpfr_clears (m0, m1, NULL);
13240 if (result_rem)
13241 {
13242 /* MPFR calculates quo in the host's long so it may
13243 return more bits in quo than the target int can hold
13244 if sizeof(host long) > sizeof(target int). This can
13245 happen even for native compilers in LP64 mode. In
13246 these cases, modulo the quo value with the largest
13247 number that the target int can hold while leaving one
13248 bit for the sign. */
13249 if (sizeof (integer_quo) * CHAR_BIT > INT_TYPE_SIZE)
13250 integer_quo %= (long)(1UL << (INT_TYPE_SIZE - 1));
13251
13252 /* Dereference the quo pointer argument. */
13253 arg_quo = build_fold_indirect_ref (arg_quo);
13254 /* Proceed iff a valid pointer type was passed in. */
13255 if (TYPE_MAIN_VARIANT (TREE_TYPE (arg_quo)) == integer_type_node)
13256 {
13257 /* Set the value. */
13258 tree result_quo = fold_build2 (MODIFY_EXPR,
13259 TREE_TYPE (arg_quo), arg_quo,
13260 build_int_cst (NULL, integer_quo));
13261 TREE_SIDE_EFFECTS (result_quo) = 1;
13262 /* Combine the quo assignment with the rem. */
13263 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
13264 result_quo, result_rem));
13265 }
13266 }
13267 }
13268 }
13269 return result;
13270 }
13271
13272 /* If ARG is a REAL_CST, call mpfr_lgamma() on it and return the
13273 resulting value as a tree with type TYPE. The mpfr precision is
13274 set to the precision of TYPE. We assume that this mpfr function
13275 returns zero if the result could be calculated exactly within the
13276 requested precision. In addition, the integer pointer represented
13277 by ARG_SG will be dereferenced and set to the appropriate signgam
13278 (-1,1) value. */
13279
13280 static tree
13281 do_mpfr_lgamma_r (tree arg, tree arg_sg, tree type)
13282 {
13283 tree result = NULL_TREE;
13284
13285 STRIP_NOPS (arg);
13286
13287 /* To proceed, MPFR must exactly represent the target floating point
13288 format, which only happens when the target base equals two. Also
13289 verify ARG is a constant and that ARG_SG is an int pointer. */
13290 if (REAL_MODE_FORMAT (TYPE_MODE (type))->b == 2
13291 && TREE_CODE (arg) == REAL_CST && !TREE_OVERFLOW (arg)
13292 && TREE_CODE (TREE_TYPE (arg_sg)) == POINTER_TYPE
13293 && TYPE_MAIN_VARIANT (TREE_TYPE (TREE_TYPE (arg_sg))) == integer_type_node)
13294 {
13295 const REAL_VALUE_TYPE *const ra = TREE_REAL_CST_PTR (arg);
13296
13297 /* In addition to NaN and Inf, the argument cannot be zero or a
13298 negative integer. */
13299 if (real_isfinite (ra)
13300 && ra->cl != rvc_zero
13301 && !(real_isneg(ra) && real_isinteger(ra, TYPE_MODE (type))))
13302 {
13303 const struct real_format *fmt = REAL_MODE_FORMAT (TYPE_MODE (type));
13304 const int prec = fmt->p;
13305 const mp_rnd_t rnd = fmt->round_towards_zero? GMP_RNDZ : GMP_RNDN;
13306 int inexact, sg;
13307 mpfr_t m;
13308 tree result_lg;
13309
13310 mpfr_init2 (m, prec);
13311 mpfr_from_real (m, ra, GMP_RNDN);
13312 mpfr_clear_flags ();
13313 inexact = mpfr_lgamma (m, &sg, m, rnd);
13314 result_lg = do_mpfr_ckconv (m, type, inexact);
13315 mpfr_clear (m);
13316 if (result_lg)
13317 {
13318 tree result_sg;
13319
13320 /* Dereference the arg_sg pointer argument. */
13321 arg_sg = build_fold_indirect_ref (arg_sg);
13322 /* Assign the signgam value into *arg_sg. */
13323 result_sg = fold_build2 (MODIFY_EXPR,
13324 TREE_TYPE (arg_sg), arg_sg,
13325 build_int_cst (NULL, sg));
13326 TREE_SIDE_EFFECTS (result_sg) = 1;
13327 /* Combine the signgam assignment with the lgamma result. */
13328 result = non_lvalue (fold_build2 (COMPOUND_EXPR, type,
13329 result_sg, result_lg));
13330 }
13331 }
13332 }
13333
13334 return result;
13335 }
13336
13337 /* If argument ARG is a COMPLEX_CST, call the one-argument mpc
13338 function FUNC on it and return the resulting value as a tree with
13339 type TYPE. The mpfr precision is set to the precision of TYPE. We
13340 assume that function FUNC returns zero if the result could be
13341 calculated exactly within the requested precision. */
13342
13343 static tree
13344 do_mpc_arg1 (tree arg, tree type, int (*func)(mpc_ptr, mpc_srcptr, mpc_rnd_t))
13345 {
13346 tree result = NULL_TREE;
13347
13348 STRIP_NOPS (arg);
13349
13350 /* To proceed, MPFR must exactly represent the target floating point
13351 format, which only happens when the target base equals two. */
13352 if (TREE_CODE (arg) == COMPLEX_CST && !TREE_OVERFLOW (arg)
13353 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) == REAL_TYPE
13354 && REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (TREE_TYPE (arg))))->b == 2)
13355 {
13356 const REAL_VALUE_TYPE *const re = TREE_REAL_CST_PTR (TREE_REALPART (arg));
13357 const REAL_VALUE_TYPE *const im = TREE_REAL_CST_PTR (TREE_IMAGPART (arg));
13358
13359 if (real_isfinite (re) && real_isfinite (im))
13360 {
13361 const struct real_format *const fmt =
13362 REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (type)));
13363 const int prec = fmt->p;
13364 const mp_rnd_t rnd = fmt->round_towards_zero ? GMP_RNDZ : GMP_RNDN;
13365 const mpc_rnd_t crnd = fmt->round_towards_zero ? MPC_RNDZZ : MPC_RNDNN;
13366 int inexact;
13367 mpc_t m;
13368
13369 mpc_init2 (m, prec);
13370 mpfr_from_real (mpc_realref(m), re, rnd);
13371 mpfr_from_real (mpc_imagref(m), im, rnd);
13372 mpfr_clear_flags ();
13373 inexact = func (m, m, crnd);
13374 result = do_mpc_ckconv (m, type, inexact, /*force_convert=*/ 0);
13375 mpc_clear (m);
13376 }
13377 }
13378
13379 return result;
13380 }
13381
13382 /* If arguments ARG0 and ARG1 are a COMPLEX_CST, call the two-argument
13383 mpc function FUNC on it and return the resulting value as a tree
13384 with type TYPE. The mpfr precision is set to the precision of
13385 TYPE. We assume that function FUNC returns zero if the result
13386 could be calculated exactly within the requested precision. If
13387 DO_NONFINITE is true, then fold expressions containing Inf or NaN
13388 in the arguments and/or results. */
13389
13390 tree
13391 do_mpc_arg2 (tree arg0, tree arg1, tree type, int do_nonfinite,
13392 int (*func)(mpc_ptr, mpc_srcptr, mpc_srcptr, mpc_rnd_t))
13393 {
13394 tree result = NULL_TREE;
13395
13396 STRIP_NOPS (arg0);
13397 STRIP_NOPS (arg1);
13398
13399 /* To proceed, MPFR must exactly represent the target floating point
13400 format, which only happens when the target base equals two. */
13401 if (TREE_CODE (arg0) == COMPLEX_CST && !TREE_OVERFLOW (arg0)
13402 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg0))) == REAL_TYPE
13403 && TREE_CODE (arg1) == COMPLEX_CST && !TREE_OVERFLOW (arg1)
13404 && TREE_CODE (TREE_TYPE (TREE_TYPE (arg1))) == REAL_TYPE
13405 && REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (TREE_TYPE (arg0))))->b == 2)
13406 {
13407 const REAL_VALUE_TYPE *const re0 = TREE_REAL_CST_PTR (TREE_REALPART (arg0));
13408 const REAL_VALUE_TYPE *const im0 = TREE_REAL_CST_PTR (TREE_IMAGPART (arg0));
13409 const REAL_VALUE_TYPE *const re1 = TREE_REAL_CST_PTR (TREE_REALPART (arg1));
13410 const REAL_VALUE_TYPE *const im1 = TREE_REAL_CST_PTR (TREE_IMAGPART (arg1));
13411
13412 if (do_nonfinite
13413 || (real_isfinite (re0) && real_isfinite (im0)
13414 && real_isfinite (re1) && real_isfinite (im1)))
13415 {
13416 const struct real_format *const fmt =
13417 REAL_MODE_FORMAT (TYPE_MODE (TREE_TYPE (type)));
13418 const int prec = fmt->p;
13419 const mp_rnd_t rnd = fmt->round_towards_zero ? GMP_RNDZ : GMP_RNDN;
13420 const mpc_rnd_t crnd = fmt->round_towards_zero ? MPC_RNDZZ : MPC_RNDNN;
13421 int inexact;
13422 mpc_t m0, m1;
13423
13424 mpc_init2 (m0, prec);
13425 mpc_init2 (m1, prec);
13426 mpfr_from_real (mpc_realref(m0), re0, rnd);
13427 mpfr_from_real (mpc_imagref(m0), im0, rnd);
13428 mpfr_from_real (mpc_realref(m1), re1, rnd);
13429 mpfr_from_real (mpc_imagref(m1), im1, rnd);
13430 mpfr_clear_flags ();
13431 inexact = func (m0, m0, m1, crnd);
13432 result = do_mpc_ckconv (m0, type, inexact, do_nonfinite);
13433 mpc_clear (m0);
13434 mpc_clear (m1);
13435 }
13436 }
13437
13438 return result;
13439 }
13440
13441 /* FIXME tuples.
13442 The functions below provide an alternate interface for folding
13443 builtin function calls presented as GIMPLE_CALL statements rather
13444 than as CALL_EXPRs. The folded result is still expressed as a
13445 tree. There is too much code duplication in the handling of
13446 varargs functions, and a more intrusive re-factoring would permit
13447 better sharing of code between the tree and statement-based
13448 versions of these functions. */
13449
13450 /* Construct a new CALL_EXPR using the tail of the argument list of STMT
13451 along with N new arguments specified as the "..." parameters. SKIP
13452 is the number of arguments in STMT to be omitted. This function is used
13453 to do varargs-to-varargs transformations. */
13454
13455 static tree
13456 gimple_rewrite_call_expr (gimple stmt, int skip, tree fndecl, int n, ...)
13457 {
13458 int oldnargs = gimple_call_num_args (stmt);
13459 int nargs = oldnargs - skip + n;
13460 tree fntype = TREE_TYPE (fndecl);
13461 tree fn = build1 (ADDR_EXPR, build_pointer_type (fntype), fndecl);
13462 tree *buffer;
13463 int i, j;
13464 va_list ap;
13465 location_t loc = gimple_location (stmt);
13466
13467 buffer = XALLOCAVEC (tree, nargs);
13468 va_start (ap, n);
13469 for (i = 0; i < n; i++)
13470 buffer[i] = va_arg (ap, tree);
13471 va_end (ap);
13472 for (j = skip; j < oldnargs; j++, i++)
13473 buffer[i] = gimple_call_arg (stmt, j);
13474
13475 return fold (build_call_array_loc (loc, TREE_TYPE (fntype), fn, nargs, buffer));
13476 }
13477
13478 /* Fold a call STMT to __{,v}sprintf_chk. Return NULL_TREE if
13479 a normal call should be emitted rather than expanding the function
13480 inline. FCODE is either BUILT_IN_SPRINTF_CHK or BUILT_IN_VSPRINTF_CHK. */
13481
13482 static tree
13483 gimple_fold_builtin_sprintf_chk (gimple stmt, enum built_in_function fcode)
13484 {
13485 tree dest, size, len, fn, fmt, flag;
13486 const char *fmt_str;
13487 int nargs = gimple_call_num_args (stmt);
13488
13489 /* Verify the required arguments in the original call. */
13490 if (nargs < 4)
13491 return NULL_TREE;
13492 dest = gimple_call_arg (stmt, 0);
13493 if (!validate_arg (dest, POINTER_TYPE))
13494 return NULL_TREE;
13495 flag = gimple_call_arg (stmt, 1);
13496 if (!validate_arg (flag, INTEGER_TYPE))
13497 return NULL_TREE;
13498 size = gimple_call_arg (stmt, 2);
13499 if (!validate_arg (size, INTEGER_TYPE))
13500 return NULL_TREE;
13501 fmt = gimple_call_arg (stmt, 3);
13502 if (!validate_arg (fmt, POINTER_TYPE))
13503 return NULL_TREE;
13504
13505 if (! host_integerp (size, 1))
13506 return NULL_TREE;
13507
13508 len = NULL_TREE;
13509
13510 if (!init_target_chars ())
13511 return NULL_TREE;
13512
13513 /* Check whether the format is a literal string constant. */
13514 fmt_str = c_getstr (fmt);
13515 if (fmt_str != NULL)
13516 {
13517 /* If the format doesn't contain % args or %%, we know the size. */
13518 if (strchr (fmt_str, target_percent) == 0)
13519 {
13520 if (fcode != BUILT_IN_SPRINTF_CHK || nargs == 4)
13521 len = build_int_cstu (size_type_node, strlen (fmt_str));
13522 }
13523 /* If the format is "%s" and first ... argument is a string literal,
13524 we know the size too. */
13525 else if (fcode == BUILT_IN_SPRINTF_CHK
13526 && strcmp (fmt_str, target_percent_s) == 0)
13527 {
13528 tree arg;
13529
13530 if (nargs == 5)
13531 {
13532 arg = gimple_call_arg (stmt, 4);
13533 if (validate_arg (arg, POINTER_TYPE))
13534 {
13535 len = c_strlen (arg, 1);
13536 if (! len || ! host_integerp (len, 1))
13537 len = NULL_TREE;
13538 }
13539 }
13540 }
13541 }
13542
13543 if (! integer_all_onesp (size))
13544 {
13545 if (! len || ! tree_int_cst_lt (len, size))
13546 return NULL_TREE;
13547 }
13548
13549 /* Only convert __{,v}sprintf_chk to {,v}sprintf if flag is 0
13550 or if format doesn't contain % chars or is "%s". */
13551 if (! integer_zerop (flag))
13552 {
13553 if (fmt_str == NULL)
13554 return NULL_TREE;
13555 if (strchr (fmt_str, target_percent) != NULL
13556 && strcmp (fmt_str, target_percent_s))
13557 return NULL_TREE;
13558 }
13559
13560 /* If __builtin_{,v}sprintf_chk is used, assume {,v}sprintf is available. */
13561 fn = built_in_decls[fcode == BUILT_IN_VSPRINTF_CHK
13562 ? BUILT_IN_VSPRINTF : BUILT_IN_SPRINTF];
13563 if (!fn)
13564 return NULL_TREE;
13565
13566 return gimple_rewrite_call_expr (stmt, 4, fn, 2, dest, fmt);
13567 }
13568
13569 /* Fold a call STMT to {,v}snprintf. Return NULL_TREE if
13570 a normal call should be emitted rather than expanding the function
13571 inline. FCODE is either BUILT_IN_SNPRINTF_CHK or
13572 BUILT_IN_VSNPRINTF_CHK. If MAXLEN is not NULL, it is maximum length
13573 passed as second argument. */
13574
13575 tree
13576 gimple_fold_builtin_snprintf_chk (gimple stmt, tree maxlen,
13577 enum built_in_function fcode)
13578 {
13579 tree dest, size, len, fn, fmt, flag;
13580 const char *fmt_str;
13581
13582 /* Verify the required arguments in the original call. */
13583 if (gimple_call_num_args (stmt) < 5)
13584 return NULL_TREE;
13585 dest = gimple_call_arg (stmt, 0);
13586 if (!validate_arg (dest, POINTER_TYPE))
13587 return NULL_TREE;
13588 len = gimple_call_arg (stmt, 1);
13589 if (!validate_arg (len, INTEGER_TYPE))
13590 return NULL_TREE;
13591 flag = gimple_call_arg (stmt, 2);
13592 if (!validate_arg (flag, INTEGER_TYPE))
13593 return NULL_TREE;
13594 size = gimple_call_arg (stmt, 3);
13595 if (!validate_arg (size, INTEGER_TYPE))
13596 return NULL_TREE;
13597 fmt = gimple_call_arg (stmt, 4);
13598 if (!validate_arg (fmt, POINTER_TYPE))
13599 return NULL_TREE;
13600
13601 if (! host_integerp (size, 1))
13602 return NULL_TREE;
13603
13604 if (! integer_all_onesp (size))
13605 {
13606 if (! host_integerp (len, 1))
13607 {
13608 /* If LEN is not constant, try MAXLEN too.
13609 For MAXLEN only allow optimizing into non-_ocs function
13610 if SIZE is >= MAXLEN, never convert to __ocs_fail (). */
13611 if (maxlen == NULL_TREE || ! host_integerp (maxlen, 1))
13612 return NULL_TREE;
13613 }
13614 else
13615 maxlen = len;
13616
13617 if (tree_int_cst_lt (size, maxlen))
13618 return NULL_TREE;
13619 }
13620
13621 if (!init_target_chars ())
13622 return NULL_TREE;
13623
13624 /* Only convert __{,v}snprintf_chk to {,v}snprintf if flag is 0
13625 or if format doesn't contain % chars or is "%s". */
13626 if (! integer_zerop (flag))
13627 {
13628 fmt_str = c_getstr (fmt);
13629 if (fmt_str == NULL)
13630 return NULL_TREE;
13631 if (strchr (fmt_str, target_percent) != NULL
13632 && strcmp (fmt_str, target_percent_s))
13633 return NULL_TREE;
13634 }
13635
13636 /* If __builtin_{,v}snprintf_chk is used, assume {,v}snprintf is
13637 available. */
13638 fn = built_in_decls[fcode == BUILT_IN_VSNPRINTF_CHK
13639 ? BUILT_IN_VSNPRINTF : BUILT_IN_SNPRINTF];
13640 if (!fn)
13641 return NULL_TREE;
13642
13643 return gimple_rewrite_call_expr (stmt, 5, fn, 3, dest, len, fmt);
13644 }
13645
13646 /* Builtins with folding operations that operate on "..." arguments
13647 need special handling; we need to store the arguments in a convenient
13648 data structure before attempting any folding. Fortunately there are
13649 only a few builtins that fall into this category. FNDECL is the
13650 function, EXP is the CALL_EXPR for the call, and IGNORE is true if the
13651 result of the function call is ignored. */
13652
13653 static tree
13654 gimple_fold_builtin_varargs (tree fndecl, gimple stmt,
13655 bool ignore ATTRIBUTE_UNUSED)
13656 {
13657 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
13658 tree ret = NULL_TREE;
13659
13660 switch (fcode)
13661 {
13662 case BUILT_IN_SPRINTF_CHK:
13663 case BUILT_IN_VSPRINTF_CHK:
13664 ret = gimple_fold_builtin_sprintf_chk (stmt, fcode);
13665 break;
13666
13667 case BUILT_IN_SNPRINTF_CHK:
13668 case BUILT_IN_VSNPRINTF_CHK:
13669 ret = gimple_fold_builtin_snprintf_chk (stmt, NULL_TREE, fcode);
13670
13671 default:
13672 break;
13673 }
13674 if (ret)
13675 {
13676 ret = build1 (NOP_EXPR, TREE_TYPE (ret), ret);
13677 TREE_NO_WARNING (ret) = 1;
13678 return ret;
13679 }
13680 return NULL_TREE;
13681 }
13682
13683 /* A wrapper function for builtin folding that prevents warnings for
13684 "statement without effect" and the like, caused by removing the
13685 call node earlier than the warning is generated. */
13686
13687 tree
13688 fold_call_stmt (gimple stmt, bool ignore)
13689 {
13690 tree ret = NULL_TREE;
13691 tree fndecl = gimple_call_fndecl (stmt);
13692 location_t loc = gimple_location (stmt);
13693 if (fndecl
13694 && TREE_CODE (fndecl) == FUNCTION_DECL
13695 && DECL_BUILT_IN (fndecl)
13696 && !gimple_call_va_arg_pack_p (stmt))
13697 {
13698 int nargs = gimple_call_num_args (stmt);
13699
13700 if (avoid_folding_inline_builtin (fndecl))
13701 return NULL_TREE;
13702 /* FIXME: Don't use a list in this interface. */
13703 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
13704 {
13705 tree arglist = NULL_TREE;
13706 int i;
13707 for (i = nargs - 1; i >= 0; i--)
13708 arglist = tree_cons (NULL_TREE, gimple_call_arg (stmt, i), arglist);
13709 return targetm.fold_builtin (fndecl, arglist, ignore);
13710 }
13711 else
13712 {
13713 if (nargs <= MAX_ARGS_TO_FOLD_BUILTIN)
13714 {
13715 tree args[MAX_ARGS_TO_FOLD_BUILTIN];
13716 int i;
13717 for (i = 0; i < nargs; i++)
13718 args[i] = gimple_call_arg (stmt, i);
13719 ret = fold_builtin_n (loc, fndecl, args, nargs, ignore);
13720 }
13721 if (!ret)
13722 ret = gimple_fold_builtin_varargs (fndecl, stmt, ignore);
13723 if (ret)
13724 {
13725 /* Propagate location information from original call to
13726 expansion of builtin. Otherwise things like
13727 maybe_emit_chk_warning, that operate on the expansion
13728 of a builtin, will use the wrong location information. */
13729 if (gimple_has_location (stmt))
13730 {
13731 tree realret = ret;
13732 if (TREE_CODE (ret) == NOP_EXPR)
13733 realret = TREE_OPERAND (ret, 0);
13734 if (CAN_HAVE_LOCATION_P (realret)
13735 && !EXPR_HAS_LOCATION (realret))
13736 SET_EXPR_LOCATION (realret, loc);
13737 return realret;
13738 }
13739 return ret;
13740 }
13741 }
13742 }
13743 return NULL_TREE;
13744 }
13745
13746 /* Look up the function in built_in_decls that corresponds to DECL
13747 and set ASMSPEC as its user assembler name. DECL must be a
13748 function decl that declares a builtin. */
13749
13750 void
13751 set_builtin_user_assembler_name (tree decl, const char *asmspec)
13752 {
13753 tree builtin;
13754 gcc_assert (TREE_CODE (decl) == FUNCTION_DECL
13755 && DECL_BUILT_IN_CLASS (decl) == BUILT_IN_NORMAL
13756 && asmspec != 0);
13757
13758 builtin = built_in_decls [DECL_FUNCTION_CODE (decl)];
13759 set_user_assembler_name (builtin, asmspec);
13760 switch (DECL_FUNCTION_CODE (decl))
13761 {
13762 case BUILT_IN_MEMCPY:
13763 init_block_move_fn (asmspec);
13764 memcpy_libfunc = set_user_assembler_libfunc ("memcpy", asmspec);
13765 break;
13766 case BUILT_IN_MEMSET:
13767 init_block_clear_fn (asmspec);
13768 memset_libfunc = set_user_assembler_libfunc ("memset", asmspec);
13769 break;
13770 case BUILT_IN_MEMMOVE:
13771 memmove_libfunc = set_user_assembler_libfunc ("memmove", asmspec);
13772 break;
13773 case BUILT_IN_MEMCMP:
13774 memcmp_libfunc = set_user_assembler_libfunc ("memcmp", asmspec);
13775 break;
13776 case BUILT_IN_ABORT:
13777 abort_libfunc = set_user_assembler_libfunc ("abort", asmspec);
13778 break;
13779 case BUILT_IN_FFS:
13780 if (INT_TYPE_SIZE < BITS_PER_WORD)
13781 {
13782 set_user_assembler_libfunc ("ffs", asmspec);
13783 set_optab_libfunc (ffs_optab, mode_for_size (INT_TYPE_SIZE,
13784 MODE_INT, 0), "ffs");
13785 }
13786 break;
13787 default:
13788 break;
13789 }
13790 }