* random.c (random_seed): Use correct variable.
[official-gcc.git] / gcc / builtins.c
blob2457d66142110d05b5bc5a4006b96a776a3c856b
1 /* Expand builtin functions.
2 Copyright (C) 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
5 This file is part of GCC.
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 2, or (at your option) any later
10 version.
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15 for more details.
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING. If not, write to the Free
19 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20 02111-1307, USA. */
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 "flags.h"
31 #include "regs.h"
32 #include "hard-reg-set.h"
33 #include "except.h"
34 #include "function.h"
35 #include "insn-config.h"
36 #include "expr.h"
37 #include "optabs.h"
38 #include "libfuncs.h"
39 #include "recog.h"
40 #include "output.h"
41 #include "typeclass.h"
42 #include "toplev.h"
43 #include "predict.h"
44 #include "tm_p.h"
45 #include "target.h"
46 #include "langhooks.h"
48 #define CALLED_AS_BUILT_IN(NODE) \
49 (!strncmp (IDENTIFIER_POINTER (DECL_NAME (NODE)), "__builtin_", 10))
51 #ifndef PAD_VARARGS_DOWN
52 #define PAD_VARARGS_DOWN BYTES_BIG_ENDIAN
53 #endif
55 /* Define the names of the builtin function types and codes. */
56 const char *const built_in_class_names[4]
57 = {"NOT_BUILT_IN", "BUILT_IN_FRONTEND", "BUILT_IN_MD", "BUILT_IN_NORMAL"};
59 #define DEF_BUILTIN(X, N, C, T, LT, B, F, NA, AT, IM) #X,
60 const char *const built_in_names[(int) END_BUILTINS] =
62 #include "builtins.def"
64 #undef DEF_BUILTIN
66 /* Setup an array of _DECL trees, make sure each element is
67 initialized to NULL_TREE. */
68 tree built_in_decls[(int) END_BUILTINS];
69 /* Declarations used when constructing the builtin implicitly in the compiler.
70 It may be NULL_TREE when this is invalid (for instance runtime is not
71 required to implement the function call in all cases). */
72 tree implicit_built_in_decls[(int) END_BUILTINS];
74 static int get_pointer_alignment (tree, unsigned int);
75 static const char *c_getstr (tree);
76 static rtx c_readstr (const char *, enum machine_mode);
77 static int target_char_cast (tree, char *);
78 static rtx get_memory_rtx (tree);
79 static tree build_string_literal (int, const char *);
80 static int apply_args_size (void);
81 static int apply_result_size (void);
82 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
83 static rtx result_vector (int, rtx);
84 #endif
85 static rtx expand_builtin_setjmp (tree, rtx);
86 static void expand_builtin_update_setjmp_buf (rtx);
87 static void expand_builtin_prefetch (tree);
88 static rtx expand_builtin_apply_args (void);
89 static rtx expand_builtin_apply_args_1 (void);
90 static rtx expand_builtin_apply (rtx, rtx, rtx);
91 static void expand_builtin_return (rtx);
92 static enum type_class type_to_class (tree);
93 static rtx expand_builtin_classify_type (tree);
94 static void expand_errno_check (tree, rtx);
95 static rtx expand_builtin_mathfn (tree, rtx, rtx);
96 static rtx expand_builtin_mathfn_2 (tree, rtx, rtx);
97 static rtx expand_builtin_mathfn_3 (tree, rtx, rtx);
98 static rtx expand_builtin_args_info (tree);
99 static rtx expand_builtin_next_arg (tree);
100 static rtx expand_builtin_va_start (tree);
101 static rtx expand_builtin_va_end (tree);
102 static rtx expand_builtin_va_copy (tree);
103 static rtx expand_builtin_memcmp (tree, tree, rtx, enum machine_mode);
104 static rtx expand_builtin_strcmp (tree, rtx, enum machine_mode);
105 static rtx expand_builtin_strncmp (tree, rtx, enum machine_mode);
106 static rtx builtin_memcpy_read_str (void *, HOST_WIDE_INT, enum machine_mode);
107 static rtx expand_builtin_strcat (tree, rtx, enum machine_mode);
108 static rtx expand_builtin_strncat (tree, rtx, enum machine_mode);
109 static rtx expand_builtin_strspn (tree, rtx, enum machine_mode);
110 static rtx expand_builtin_strcspn (tree, rtx, enum machine_mode);
111 static rtx expand_builtin_memcpy (tree, rtx, enum machine_mode);
112 static rtx expand_builtin_mempcpy (tree, rtx, enum machine_mode, int);
113 static rtx expand_builtin_memmove (tree, rtx, enum machine_mode);
114 static rtx expand_builtin_bcopy (tree);
115 static rtx expand_builtin_strcpy (tree, rtx, enum machine_mode);
116 static rtx expand_builtin_stpcpy (tree, rtx, enum machine_mode);
117 static rtx builtin_strncpy_read_str (void *, HOST_WIDE_INT, enum machine_mode);
118 static rtx expand_builtin_strncpy (tree, rtx, enum machine_mode);
119 static rtx builtin_memset_read_str (void *, HOST_WIDE_INT, enum machine_mode);
120 static rtx builtin_memset_gen_str (void *, HOST_WIDE_INT, enum machine_mode);
121 static rtx expand_builtin_memset (tree, rtx, enum machine_mode);
122 static rtx expand_builtin_bzero (tree);
123 static rtx expand_builtin_strlen (tree, rtx, enum machine_mode);
124 static rtx expand_builtin_strstr (tree, rtx, enum machine_mode);
125 static rtx expand_builtin_strpbrk (tree, rtx, enum machine_mode);
126 static rtx expand_builtin_strchr (tree, rtx, enum machine_mode);
127 static rtx expand_builtin_strrchr (tree, rtx, enum machine_mode);
128 static rtx expand_builtin_alloca (tree, rtx);
129 static rtx expand_builtin_unop (enum machine_mode, tree, rtx, rtx, optab);
130 static rtx expand_builtin_frame_address (tree, tree);
131 static rtx expand_builtin_fputs (tree, rtx, bool);
132 static rtx expand_builtin_printf (tree, rtx, enum machine_mode, bool);
133 static rtx expand_builtin_fprintf (tree, rtx, enum machine_mode, bool);
134 static rtx expand_builtin_sprintf (tree, rtx, enum machine_mode);
135 static tree stabilize_va_list (tree, int);
136 static rtx expand_builtin_expect (tree, rtx);
137 static tree fold_builtin_constant_p (tree);
138 static tree fold_builtin_classify_type (tree);
139 static tree fold_builtin_inf (tree, int);
140 static tree fold_builtin_nan (tree, tree, int);
141 static int validate_arglist (tree, ...);
142 static bool integer_valued_real_p (tree);
143 static tree fold_trunc_transparent_mathfn (tree);
144 static bool readonly_data_expr (tree);
145 static rtx expand_builtin_fabs (tree, rtx, rtx);
146 static rtx expand_builtin_cabs (tree, rtx);
147 static rtx expand_builtin_signbit (tree, rtx);
148 static tree fold_builtin_cabs (tree, tree);
149 static tree fold_builtin_trunc (tree);
150 static tree fold_builtin_floor (tree);
151 static tree fold_builtin_ceil (tree);
152 static tree fold_builtin_round (tree);
153 static tree fold_builtin_bitop (tree);
154 static tree fold_builtin_memcpy (tree);
155 static tree fold_builtin_mempcpy (tree);
156 static tree fold_builtin_memmove (tree);
157 static tree fold_builtin_strcpy (tree);
158 static tree fold_builtin_strncpy (tree);
159 static tree fold_builtin_memcmp (tree);
160 static tree fold_builtin_strcmp (tree);
161 static tree fold_builtin_strncmp (tree);
162 static tree fold_builtin_signbit (tree);
164 static tree simplify_builtin_memcmp (tree);
165 static tree simplify_builtin_strcmp (tree);
166 static tree simplify_builtin_strncmp (tree);
167 static tree simplify_builtin_strpbrk (tree);
168 static tree simplify_builtin_strstr (tree);
169 static tree simplify_builtin_strchr (tree);
170 static tree simplify_builtin_strrchr (tree);
171 static tree simplify_builtin_strcat (tree);
172 static tree simplify_builtin_strncat (tree);
173 static tree simplify_builtin_strspn (tree);
174 static tree simplify_builtin_strcspn (tree);
175 static void simplify_builtin_next_arg (tree);
176 static void simplify_builtin_va_start (tree);
177 static tree simplify_builtin_sprintf (tree, int);
180 /* Return the alignment in bits of EXP, a pointer valued expression.
181 But don't return more than MAX_ALIGN no matter what.
182 The alignment returned is, by default, the alignment of the thing that
183 EXP points to. If it is not a POINTER_TYPE, 0 is returned.
185 Otherwise, look at the expression to see if we can do better, i.e., if the
186 expression is actually pointing at an object whose alignment is tighter. */
188 static int
189 get_pointer_alignment (tree exp, unsigned int max_align)
191 unsigned int align, inner;
193 if (TREE_CODE (TREE_TYPE (exp)) != POINTER_TYPE)
194 return 0;
196 align = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
197 align = MIN (align, max_align);
199 while (1)
201 switch (TREE_CODE (exp))
203 case NOP_EXPR:
204 case CONVERT_EXPR:
205 case NON_LVALUE_EXPR:
206 exp = TREE_OPERAND (exp, 0);
207 if (TREE_CODE (TREE_TYPE (exp)) != POINTER_TYPE)
208 return align;
210 inner = TYPE_ALIGN (TREE_TYPE (TREE_TYPE (exp)));
211 align = MIN (inner, max_align);
212 break;
214 case PLUS_EXPR:
215 /* If sum of pointer + int, restrict our maximum alignment to that
216 imposed by the integer. If not, we can't do any better than
217 ALIGN. */
218 if (! host_integerp (TREE_OPERAND (exp, 1), 1))
219 return align;
221 while (((tree_low_cst (TREE_OPERAND (exp, 1), 1))
222 & (max_align / BITS_PER_UNIT - 1))
223 != 0)
224 max_align >>= 1;
226 exp = TREE_OPERAND (exp, 0);
227 break;
229 case ADDR_EXPR:
230 /* See what we are pointing at and look at its alignment. */
231 exp = TREE_OPERAND (exp, 0);
232 if (TREE_CODE (exp) == FUNCTION_DECL)
233 align = FUNCTION_BOUNDARY;
234 else if (DECL_P (exp))
235 align = DECL_ALIGN (exp);
236 #ifdef CONSTANT_ALIGNMENT
237 else if (TREE_CODE_CLASS (TREE_CODE (exp)) == 'c')
238 align = CONSTANT_ALIGNMENT (exp, align);
239 #endif
240 return MIN (align, max_align);
242 default:
243 return align;
248 /* Compute the length of a C string. TREE_STRING_LENGTH is not the right
249 way, because it could contain a zero byte in the middle.
250 TREE_STRING_LENGTH is the size of the character array, not the string.
252 ONLY_VALUE should be nonzero if the result is not going to be emitted
253 into the instruction stream and zero if it is going to be expanded.
254 E.g. with i++ ? "foo" : "bar", if ONLY_VALUE is nonzero, constant 3
255 is returned, otherwise NULL, since
256 len = c_strlen (src, 1); if (len) expand_expr (len, ...); would not
257 evaluate the side-effects.
259 The value returned is of type `ssizetype'.
261 Unfortunately, string_constant can't access the values of const char
262 arrays with initializers, so neither can we do so here. */
264 tree
265 c_strlen (tree src, int only_value)
267 tree offset_node;
268 HOST_WIDE_INT offset;
269 int max;
270 const char *ptr;
272 STRIP_NOPS (src);
273 if (TREE_CODE (src) == COND_EXPR
274 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
276 tree len1, len2;
278 len1 = c_strlen (TREE_OPERAND (src, 1), only_value);
279 len2 = c_strlen (TREE_OPERAND (src, 2), only_value);
280 if (tree_int_cst_equal (len1, len2))
281 return len1;
284 if (TREE_CODE (src) == COMPOUND_EXPR
285 && (only_value || !TREE_SIDE_EFFECTS (TREE_OPERAND (src, 0))))
286 return c_strlen (TREE_OPERAND (src, 1), only_value);
288 src = string_constant (src, &offset_node);
289 if (src == 0)
290 return 0;
292 max = TREE_STRING_LENGTH (src) - 1;
293 ptr = TREE_STRING_POINTER (src);
295 if (offset_node && TREE_CODE (offset_node) != INTEGER_CST)
297 /* If the string has an internal zero byte (e.g., "foo\0bar"), we can't
298 compute the offset to the following null if we don't know where to
299 start searching for it. */
300 int i;
302 for (i = 0; i < max; i++)
303 if (ptr[i] == 0)
304 return 0;
306 /* We don't know the starting offset, but we do know that the string
307 has no internal zero bytes. We can assume that the offset falls
308 within the bounds of the string; otherwise, the programmer deserves
309 what he gets. Subtract the offset from the length of the string,
310 and return that. This would perhaps not be valid if we were dealing
311 with named arrays in addition to literal string constants. */
313 return size_diffop (size_int (max), offset_node);
316 /* We have a known offset into the string. Start searching there for
317 a null character if we can represent it as a single HOST_WIDE_INT. */
318 if (offset_node == 0)
319 offset = 0;
320 else if (! host_integerp (offset_node, 0))
321 offset = -1;
322 else
323 offset = tree_low_cst (offset_node, 0);
325 /* If the offset is known to be out of bounds, warn, and call strlen at
326 runtime. */
327 if (offset < 0 || offset > max)
329 warning ("offset outside bounds of constant string");
330 return 0;
333 /* Use strlen to search for the first zero byte. Since any strings
334 constructed with build_string will have nulls appended, we win even
335 if we get handed something like (char[4])"abcd".
337 Since OFFSET is our starting index into the string, no further
338 calculation is needed. */
339 return ssize_int (strlen (ptr + offset));
342 /* Return a char pointer for a C string if it is a string constant
343 or sum of string constant and integer constant. */
345 static const char *
346 c_getstr (tree src)
348 tree offset_node;
350 src = string_constant (src, &offset_node);
351 if (src == 0)
352 return 0;
354 if (offset_node == 0)
355 return TREE_STRING_POINTER (src);
356 else if (!host_integerp (offset_node, 1)
357 || compare_tree_int (offset_node, TREE_STRING_LENGTH (src) - 1) > 0)
358 return 0;
360 return TREE_STRING_POINTER (src) + tree_low_cst (offset_node, 1);
363 /* Return a CONST_INT or CONST_DOUBLE corresponding to target reading
364 GET_MODE_BITSIZE (MODE) bits from string constant STR. */
366 static rtx
367 c_readstr (const char *str, enum machine_mode mode)
369 HOST_WIDE_INT c[2];
370 HOST_WIDE_INT ch;
371 unsigned int i, j;
373 if (GET_MODE_CLASS (mode) != MODE_INT)
374 abort ();
375 c[0] = 0;
376 c[1] = 0;
377 ch = 1;
378 for (i = 0; i < GET_MODE_SIZE (mode); i++)
380 j = i;
381 if (WORDS_BIG_ENDIAN)
382 j = GET_MODE_SIZE (mode) - i - 1;
383 if (BYTES_BIG_ENDIAN != WORDS_BIG_ENDIAN
384 && GET_MODE_SIZE (mode) > UNITS_PER_WORD)
385 j = j + UNITS_PER_WORD - 2 * (j % UNITS_PER_WORD) - 1;
386 j *= BITS_PER_UNIT;
387 if (j > 2 * HOST_BITS_PER_WIDE_INT)
388 abort ();
389 if (ch)
390 ch = (unsigned char) str[i];
391 c[j / HOST_BITS_PER_WIDE_INT] |= ch << (j % HOST_BITS_PER_WIDE_INT);
393 return immed_double_const (c[0], c[1], mode);
396 /* Cast a target constant CST to target CHAR and if that value fits into
397 host char type, return zero and put that value into variable pointed by
398 P. */
400 static int
401 target_char_cast (tree cst, char *p)
403 unsigned HOST_WIDE_INT val, hostval;
405 if (!host_integerp (cst, 1)
406 || CHAR_TYPE_SIZE > HOST_BITS_PER_WIDE_INT)
407 return 1;
409 val = tree_low_cst (cst, 1);
410 if (CHAR_TYPE_SIZE < HOST_BITS_PER_WIDE_INT)
411 val &= (((unsigned HOST_WIDE_INT) 1) << CHAR_TYPE_SIZE) - 1;
413 hostval = val;
414 if (HOST_BITS_PER_CHAR < HOST_BITS_PER_WIDE_INT)
415 hostval &= (((unsigned HOST_WIDE_INT) 1) << HOST_BITS_PER_CHAR) - 1;
417 if (val != hostval)
418 return 1;
420 *p = hostval;
421 return 0;
424 /* Similar to save_expr, but assumes that arbitrary code is not executed
425 in between the multiple evaluations. In particular, we assume that a
426 non-addressable local variable will not be modified. */
428 static tree
429 builtin_save_expr (tree exp)
431 if (TREE_ADDRESSABLE (exp) == 0
432 && (TREE_CODE (exp) == PARM_DECL
433 || (TREE_CODE (exp) == VAR_DECL && !TREE_STATIC (exp))))
434 return exp;
436 return save_expr (exp);
439 /* Given TEM, a pointer to a stack frame, follow the dynamic chain COUNT
440 times to get the address of either a higher stack frame, or a return
441 address located within it (depending on FNDECL_CODE). */
444 expand_builtin_return_addr (enum built_in_function fndecl_code, int count,
445 rtx tem)
447 int i;
449 /* Some machines need special handling before we can access
450 arbitrary frames. For example, on the sparc, we must first flush
451 all register windows to the stack. */
452 #ifdef SETUP_FRAME_ADDRESSES
453 if (count > 0)
454 SETUP_FRAME_ADDRESSES ();
455 #endif
457 /* On the sparc, the return address is not in the frame, it is in a
458 register. There is no way to access it off of the current frame
459 pointer, but it can be accessed off the previous frame pointer by
460 reading the value from the register window save area. */
461 #ifdef RETURN_ADDR_IN_PREVIOUS_FRAME
462 if (fndecl_code == BUILT_IN_RETURN_ADDRESS)
463 count--;
464 #endif
466 /* Scan back COUNT frames to the specified frame. */
467 for (i = 0; i < count; i++)
469 /* Assume the dynamic chain pointer is in the word that the
470 frame address points to, unless otherwise specified. */
471 #ifdef DYNAMIC_CHAIN_ADDRESS
472 tem = DYNAMIC_CHAIN_ADDRESS (tem);
473 #endif
474 tem = memory_address (Pmode, tem);
475 tem = gen_rtx_MEM (Pmode, tem);
476 set_mem_alias_set (tem, get_frame_alias_set ());
477 tem = copy_to_reg (tem);
480 /* For __builtin_frame_address, return what we've got. */
481 if (fndecl_code == BUILT_IN_FRAME_ADDRESS)
482 return tem;
484 /* For __builtin_return_address, Get the return address from that
485 frame. */
486 #ifdef RETURN_ADDR_RTX
487 tem = RETURN_ADDR_RTX (count, tem);
488 #else
489 tem = memory_address (Pmode,
490 plus_constant (tem, GET_MODE_SIZE (Pmode)));
491 tem = gen_rtx_MEM (Pmode, tem);
492 set_mem_alias_set (tem, get_frame_alias_set ());
493 #endif
494 return tem;
497 /* Alias set used for setjmp buffer. */
498 static HOST_WIDE_INT setjmp_alias_set = -1;
500 /* Construct the leading half of a __builtin_setjmp call. Control will
501 return to RECEIVER_LABEL. This is used directly by sjlj exception
502 handling code. */
504 void
505 expand_builtin_setjmp_setup (rtx buf_addr, rtx receiver_label)
507 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
508 rtx stack_save;
509 rtx mem;
511 if (setjmp_alias_set == -1)
512 setjmp_alias_set = new_alias_set ();
514 buf_addr = convert_memory_address (Pmode, buf_addr);
516 buf_addr = force_reg (Pmode, force_operand (buf_addr, NULL_RTX));
518 emit_queue ();
520 /* We store the frame pointer and the address of receiver_label in
521 the buffer and use the rest of it for the stack save area, which
522 is machine-dependent. */
524 mem = gen_rtx_MEM (Pmode, buf_addr);
525 set_mem_alias_set (mem, setjmp_alias_set);
526 emit_move_insn (mem, targetm.builtin_setjmp_frame_value ());
528 mem = gen_rtx_MEM (Pmode, plus_constant (buf_addr, GET_MODE_SIZE (Pmode))),
529 set_mem_alias_set (mem, setjmp_alias_set);
531 emit_move_insn (validize_mem (mem),
532 force_reg (Pmode, gen_rtx_LABEL_REF (Pmode, receiver_label)));
534 stack_save = gen_rtx_MEM (sa_mode,
535 plus_constant (buf_addr,
536 2 * GET_MODE_SIZE (Pmode)));
537 set_mem_alias_set (stack_save, setjmp_alias_set);
538 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
540 /* If there is further processing to do, do it. */
541 #ifdef HAVE_builtin_setjmp_setup
542 if (HAVE_builtin_setjmp_setup)
543 emit_insn (gen_builtin_setjmp_setup (buf_addr));
544 #endif
546 /* Tell optimize_save_area_alloca that extra work is going to
547 need to go on during alloca. */
548 current_function_calls_setjmp = 1;
550 /* Set this so all the registers get saved in our frame; we need to be
551 able to copy the saved values for any registers from frames we unwind. */
552 current_function_has_nonlocal_label = 1;
555 /* Construct the trailing part of a __builtin_setjmp call.
556 This is used directly by sjlj exception handling code. */
558 void
559 expand_builtin_setjmp_receiver (rtx receiver_label ATTRIBUTE_UNUSED)
561 /* Clobber the FP when we get here, so we have to make sure it's
562 marked as used by this function. */
563 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
565 /* Mark the static chain as clobbered here so life information
566 doesn't get messed up for it. */
567 emit_insn (gen_rtx_CLOBBER (VOIDmode, static_chain_rtx));
569 /* Now put in the code to restore the frame pointer, and argument
570 pointer, if needed. The code below is from expand_end_bindings
571 in stmt.c; see detailed documentation there. */
572 #ifdef HAVE_nonlocal_goto
573 if (! HAVE_nonlocal_goto)
574 #endif
575 emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx);
577 #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM
578 if (fixed_regs[ARG_POINTER_REGNUM])
580 #ifdef ELIMINABLE_REGS
581 size_t i;
582 static const struct elims {const int from, to;} elim_regs[] = ELIMINABLE_REGS;
584 for (i = 0; i < ARRAY_SIZE (elim_regs); i++)
585 if (elim_regs[i].from == ARG_POINTER_REGNUM
586 && elim_regs[i].to == HARD_FRAME_POINTER_REGNUM)
587 break;
589 if (i == ARRAY_SIZE (elim_regs))
590 #endif
592 /* Now restore our arg pointer from the address at which it
593 was saved in our stack frame. */
594 emit_move_insn (virtual_incoming_args_rtx,
595 copy_to_reg (get_arg_pointer_save_area (cfun)));
598 #endif
600 #ifdef HAVE_builtin_setjmp_receiver
601 if (HAVE_builtin_setjmp_receiver)
602 emit_insn (gen_builtin_setjmp_receiver (receiver_label));
603 else
604 #endif
605 #ifdef HAVE_nonlocal_goto_receiver
606 if (HAVE_nonlocal_goto_receiver)
607 emit_insn (gen_nonlocal_goto_receiver ());
608 else
609 #endif
610 { /* Nothing */ }
612 /* @@@ This is a kludge. Not all machine descriptions define a blockage
613 insn, but we must not allow the code we just generated to be reordered
614 by scheduling. Specifically, the update of the frame pointer must
615 happen immediately, not later. So emit an ASM_INPUT to act as blockage
616 insn. */
617 emit_insn (gen_rtx_ASM_INPUT (VOIDmode, ""));
620 /* __builtin_setjmp is passed a pointer to an array of five words (not
621 all will be used on all machines). It operates similarly to the C
622 library function of the same name, but is more efficient. Much of
623 the code below (and for longjmp) is copied from the handling of
624 non-local gotos.
626 NOTE: This is intended for use by GNAT and the exception handling
627 scheme in the compiler and will only work in the method used by
628 them. */
630 static rtx
631 expand_builtin_setjmp (tree arglist, rtx target)
633 rtx buf_addr, next_lab, cont_lab;
635 if (!validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
636 return NULL_RTX;
638 if (target == 0 || GET_CODE (target) != REG
639 || REGNO (target) < FIRST_PSEUDO_REGISTER)
640 target = gen_reg_rtx (TYPE_MODE (integer_type_node));
642 buf_addr = expand_expr (TREE_VALUE (arglist), NULL_RTX, VOIDmode, 0);
644 next_lab = gen_label_rtx ();
645 cont_lab = gen_label_rtx ();
647 expand_builtin_setjmp_setup (buf_addr, next_lab);
649 /* Set TARGET to zero and branch to the continue label. Use emit_jump to
650 ensure that pending stack adjustments are flushed. */
651 emit_move_insn (target, const0_rtx);
652 emit_jump (cont_lab);
654 emit_label (next_lab);
656 expand_builtin_setjmp_receiver (next_lab);
658 /* Set TARGET to one. */
659 emit_move_insn (target, const1_rtx);
660 emit_label (cont_lab);
662 /* Tell flow about the strange goings on. Putting `next_lab' on
663 `nonlocal_goto_handler_labels' to indicates that function
664 calls may traverse the arc back to this label. */
666 current_function_has_nonlocal_label = 1;
667 nonlocal_goto_handler_labels
668 = gen_rtx_EXPR_LIST (VOIDmode, next_lab, nonlocal_goto_handler_labels);
670 return target;
673 /* __builtin_longjmp is passed a pointer to an array of five words (not
674 all will be used on all machines). It operates similarly to the C
675 library function of the same name, but is more efficient. Much of
676 the code below is copied from the handling of non-local gotos.
678 NOTE: This is intended for use by GNAT and the exception handling
679 scheme in the compiler and will only work in the method used by
680 them. */
682 void
683 expand_builtin_longjmp (rtx buf_addr, rtx value)
685 rtx fp, lab, stack, insn, last;
686 enum machine_mode sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
688 if (setjmp_alias_set == -1)
689 setjmp_alias_set = new_alias_set ();
691 buf_addr = convert_memory_address (Pmode, buf_addr);
693 buf_addr = force_reg (Pmode, buf_addr);
695 /* We used to store value in static_chain_rtx, but that fails if pointers
696 are smaller than integers. We instead require that the user must pass
697 a second argument of 1, because that is what builtin_setjmp will
698 return. This also makes EH slightly more efficient, since we are no
699 longer copying around a value that we don't care about. */
700 if (value != const1_rtx)
701 abort ();
703 current_function_calls_longjmp = 1;
705 last = get_last_insn ();
706 #ifdef HAVE_builtin_longjmp
707 if (HAVE_builtin_longjmp)
708 emit_insn (gen_builtin_longjmp (buf_addr));
709 else
710 #endif
712 fp = gen_rtx_MEM (Pmode, buf_addr);
713 lab = gen_rtx_MEM (Pmode, plus_constant (buf_addr,
714 GET_MODE_SIZE (Pmode)));
716 stack = gen_rtx_MEM (sa_mode, plus_constant (buf_addr,
717 2 * GET_MODE_SIZE (Pmode)));
718 set_mem_alias_set (fp, setjmp_alias_set);
719 set_mem_alias_set (lab, setjmp_alias_set);
720 set_mem_alias_set (stack, setjmp_alias_set);
722 /* Pick up FP, label, and SP from the block and jump. This code is
723 from expand_goto in stmt.c; see there for detailed comments. */
724 #if HAVE_nonlocal_goto
725 if (HAVE_nonlocal_goto)
726 /* We have to pass a value to the nonlocal_goto pattern that will
727 get copied into the static_chain pointer, but it does not matter
728 what that value is, because builtin_setjmp does not use it. */
729 emit_insn (gen_nonlocal_goto (value, lab, stack, fp));
730 else
731 #endif
733 lab = copy_to_reg (lab);
735 emit_insn (gen_rtx_CLOBBER (VOIDmode,
736 gen_rtx_MEM (BLKmode,
737 gen_rtx_SCRATCH (VOIDmode))));
738 emit_insn (gen_rtx_CLOBBER (VOIDmode,
739 gen_rtx_MEM (BLKmode,
740 hard_frame_pointer_rtx)));
742 emit_move_insn (hard_frame_pointer_rtx, fp);
743 emit_stack_restore (SAVE_NONLOCAL, stack, NULL_RTX);
745 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
746 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
747 emit_indirect_jump (lab);
751 /* Search backwards and mark the jump insn as a non-local goto.
752 Note that this precludes the use of __builtin_longjmp to a
753 __builtin_setjmp target in the same function. However, we've
754 already cautioned the user that these functions are for
755 internal exception handling use only. */
756 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
758 if (insn == last)
759 abort ();
760 if (GET_CODE (insn) == JUMP_INSN)
762 REG_NOTES (insn) = alloc_EXPR_LIST (REG_NON_LOCAL_GOTO, const0_rtx,
763 REG_NOTES (insn));
764 break;
766 else if (GET_CODE (insn) == CALL_INSN)
767 break;
771 /* Expand a call to __builtin_nonlocal_goto. We're passed the target label
772 and the address of the save area. */
774 static rtx
775 expand_builtin_nonlocal_goto (tree arglist)
777 tree t_label, t_save_area;
778 rtx r_label, r_save_area, r_fp, r_sp, insn;
780 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
781 return NULL_RTX;
783 t_label = TREE_VALUE (arglist);
784 arglist = TREE_CHAIN (arglist);
785 t_save_area = TREE_VALUE (arglist);
787 r_label = expand_expr (t_label, NULL_RTX, VOIDmode, 0);
788 r_save_area = expand_expr (t_save_area, NULL_RTX, VOIDmode, 0);
789 r_fp = gen_rtx_MEM (Pmode, r_save_area);
790 r_sp = gen_rtx_MEM (STACK_SAVEAREA_MODE (SAVE_NONLOCAL),
791 plus_constant (r_save_area, GET_MODE_SIZE (Pmode)));
793 current_function_has_nonlocal_goto = 1;
795 #if HAVE_nonlocal_goto
796 /* ??? We no longer need to pass the static chain value, afaik. */
797 if (HAVE_nonlocal_goto)
798 emit_insn (gen_nonlocal_goto (const0_rtx, r_label, r_sp, r_fp));
799 else
800 #endif
802 r_label = copy_to_reg (r_label);
804 emit_insn (gen_rtx_CLOBBER (VOIDmode,
805 gen_rtx_MEM (BLKmode,
806 gen_rtx_SCRATCH (VOIDmode))));
808 emit_insn (gen_rtx_CLOBBER (VOIDmode,
809 gen_rtx_MEM (BLKmode,
810 hard_frame_pointer_rtx)));
812 /* Restore frame pointer for containing function.
813 This sets the actual hard register used for the frame pointer
814 to the location of the function's incoming static chain info.
815 The non-local goto handler will then adjust it to contain the
816 proper value and reload the argument pointer, if needed. */
817 emit_move_insn (hard_frame_pointer_rtx, r_fp);
818 emit_stack_restore (SAVE_NONLOCAL, r_sp, NULL_RTX);
820 /* USE of hard_frame_pointer_rtx added for consistency;
821 not clear if really needed. */
822 emit_insn (gen_rtx_USE (VOIDmode, hard_frame_pointer_rtx));
823 emit_insn (gen_rtx_USE (VOIDmode, stack_pointer_rtx));
824 emit_indirect_jump (r_label);
827 /* Search backwards to the jump insn and mark it as a
828 non-local goto. */
829 for (insn = get_last_insn (); insn; insn = PREV_INSN (insn))
831 if (GET_CODE (insn) == JUMP_INSN)
833 REG_NOTES (insn) = alloc_EXPR_LIST (REG_NON_LOCAL_GOTO,
834 const0_rtx, REG_NOTES (insn));
835 break;
837 else if (GET_CODE (insn) == CALL_INSN)
838 break;
841 return const0_rtx;
844 /* __builtin_update_setjmp_buf is passed a pointer to an array of five words
845 (not all will be used on all machines) that was passed to __builtin_setjmp.
846 It updates the stack pointer in that block to correspond to the current
847 stack pointer. */
849 static void
850 expand_builtin_update_setjmp_buf (rtx buf_addr)
852 enum machine_mode sa_mode = Pmode;
853 rtx stack_save;
856 #ifdef HAVE_save_stack_nonlocal
857 if (HAVE_save_stack_nonlocal)
858 sa_mode = insn_data[(int) CODE_FOR_save_stack_nonlocal].operand[0].mode;
859 #endif
860 #ifdef STACK_SAVEAREA_MODE
861 sa_mode = STACK_SAVEAREA_MODE (SAVE_NONLOCAL);
862 #endif
864 stack_save
865 = gen_rtx_MEM (sa_mode,
866 memory_address
867 (sa_mode,
868 plus_constant (buf_addr, 2 * GET_MODE_SIZE (Pmode))));
870 #ifdef HAVE_setjmp
871 if (HAVE_setjmp)
872 emit_insn (gen_setjmp ());
873 #endif
875 emit_stack_save (SAVE_NONLOCAL, &stack_save, NULL_RTX);
878 /* Expand a call to __builtin_prefetch. For a target that does not support
879 data prefetch, evaluate the memory address argument in case it has side
880 effects. */
882 static void
883 expand_builtin_prefetch (tree arglist)
885 tree arg0, arg1, arg2;
886 rtx op0, op1, op2;
888 if (!validate_arglist (arglist, POINTER_TYPE, 0))
889 return;
891 arg0 = TREE_VALUE (arglist);
892 /* Arguments 1 and 2 are optional; argument 1 (read/write) defaults to
893 zero (read) and argument 2 (locality) defaults to 3 (high degree of
894 locality). */
895 if (TREE_CHAIN (arglist))
897 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
898 if (TREE_CHAIN (TREE_CHAIN (arglist)))
899 arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
900 else
901 arg2 = build_int_2 (3, 0);
903 else
905 arg1 = integer_zero_node;
906 arg2 = build_int_2 (3, 0);
909 /* Argument 0 is an address. */
910 op0 = expand_expr (arg0, NULL_RTX, Pmode, EXPAND_NORMAL);
912 /* Argument 1 (read/write flag) must be a compile-time constant int. */
913 if (TREE_CODE (arg1) != INTEGER_CST)
915 error ("second arg to `__builtin_prefetch' must be a constant");
916 arg1 = integer_zero_node;
918 op1 = expand_expr (arg1, NULL_RTX, VOIDmode, 0);
919 /* Argument 1 must be either zero or one. */
920 if (INTVAL (op1) != 0 && INTVAL (op1) != 1)
922 warning ("invalid second arg to __builtin_prefetch; using zero");
923 op1 = const0_rtx;
926 /* Argument 2 (locality) must be a compile-time constant int. */
927 if (TREE_CODE (arg2) != INTEGER_CST)
929 error ("third arg to `__builtin_prefetch' must be a constant");
930 arg2 = integer_zero_node;
932 op2 = expand_expr (arg2, NULL_RTX, VOIDmode, 0);
933 /* Argument 2 must be 0, 1, 2, or 3. */
934 if (INTVAL (op2) < 0 || INTVAL (op2) > 3)
936 warning ("invalid third arg to __builtin_prefetch; using zero");
937 op2 = const0_rtx;
940 #ifdef HAVE_prefetch
941 if (HAVE_prefetch)
943 if ((! (*insn_data[(int) CODE_FOR_prefetch].operand[0].predicate)
944 (op0,
945 insn_data[(int) CODE_FOR_prefetch].operand[0].mode))
946 || (GET_MODE (op0) != Pmode))
948 op0 = convert_memory_address (Pmode, op0);
949 op0 = force_reg (Pmode, op0);
951 emit_insn (gen_prefetch (op0, op1, op2));
953 else
954 #endif
955 op0 = protect_from_queue (op0, 0);
956 /* Don't do anything with direct references to volatile memory, but
957 generate code to handle other side effects. */
958 if (GET_CODE (op0) != MEM && side_effects_p (op0))
959 emit_insn (op0);
962 /* Get a MEM rtx for expression EXP which is the address of an operand
963 to be used to be used in a string instruction (cmpstrsi, movstrsi, ..). */
965 static rtx
966 get_memory_rtx (tree exp)
968 rtx addr = expand_expr (exp, NULL_RTX, ptr_mode, EXPAND_SUM);
969 rtx mem;
971 addr = convert_memory_address (Pmode, addr);
973 mem = gen_rtx_MEM (BLKmode, memory_address (BLKmode, addr));
975 /* Get an expression we can use to find the attributes to assign to MEM.
976 If it is an ADDR_EXPR, use the operand. Otherwise, dereference it if
977 we can. First remove any nops. */
978 while ((TREE_CODE (exp) == NOP_EXPR || TREE_CODE (exp) == CONVERT_EXPR
979 || TREE_CODE (exp) == NON_LVALUE_EXPR)
980 && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (exp, 0))))
981 exp = TREE_OPERAND (exp, 0);
983 if (TREE_CODE (exp) == ADDR_EXPR)
985 exp = TREE_OPERAND (exp, 0);
986 set_mem_attributes (mem, exp, 0);
988 else if (POINTER_TYPE_P (TREE_TYPE (exp)))
990 exp = build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (exp)), exp);
991 /* memcpy, memset and other builtin stringops can alias with anything. */
992 set_mem_alias_set (mem, 0);
995 return mem;
998 /* Built-in functions to perform an untyped call and return. */
1000 /* For each register that may be used for calling a function, this
1001 gives a mode used to copy the register's value. VOIDmode indicates
1002 the register is not used for calling a function. If the machine
1003 has register windows, this gives only the outbound registers.
1004 INCOMING_REGNO gives the corresponding inbound register. */
1005 static enum machine_mode apply_args_mode[FIRST_PSEUDO_REGISTER];
1007 /* For each register that may be used for returning values, this gives
1008 a mode used to copy the register's value. VOIDmode indicates the
1009 register is not used for returning values. If the machine has
1010 register windows, this gives only the outbound registers.
1011 INCOMING_REGNO gives the corresponding inbound register. */
1012 static enum machine_mode apply_result_mode[FIRST_PSEUDO_REGISTER];
1014 /* For each register that may be used for calling a function, this
1015 gives the offset of that register into the block returned by
1016 __builtin_apply_args. 0 indicates that the register is not
1017 used for calling a function. */
1018 static int apply_args_reg_offset[FIRST_PSEUDO_REGISTER];
1020 /* Return the size required for the block returned by __builtin_apply_args,
1021 and initialize apply_args_mode. */
1023 static int
1024 apply_args_size (void)
1026 static int size = -1;
1027 int align;
1028 unsigned int regno;
1029 enum machine_mode mode;
1031 /* The values computed by this function never change. */
1032 if (size < 0)
1034 /* The first value is the incoming arg-pointer. */
1035 size = GET_MODE_SIZE (Pmode);
1037 /* The second value is the structure value address unless this is
1038 passed as an "invisible" first argument. */
1039 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1040 size += GET_MODE_SIZE (Pmode);
1042 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1043 if (FUNCTION_ARG_REGNO_P (regno))
1045 mode = reg_raw_mode[regno];
1047 if (mode == VOIDmode)
1048 abort ();
1050 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1051 if (size % align != 0)
1052 size = CEIL (size, align) * align;
1053 apply_args_reg_offset[regno] = size;
1054 size += GET_MODE_SIZE (mode);
1055 apply_args_mode[regno] = mode;
1057 else
1059 apply_args_mode[regno] = VOIDmode;
1060 apply_args_reg_offset[regno] = 0;
1063 return size;
1066 /* Return the size required for the block returned by __builtin_apply,
1067 and initialize apply_result_mode. */
1069 static int
1070 apply_result_size (void)
1072 static int size = -1;
1073 int align, regno;
1074 enum machine_mode mode;
1076 /* The values computed by this function never change. */
1077 if (size < 0)
1079 size = 0;
1081 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1082 if (FUNCTION_VALUE_REGNO_P (regno))
1084 mode = reg_raw_mode[regno];
1086 if (mode == VOIDmode)
1087 abort ();
1089 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1090 if (size % align != 0)
1091 size = CEIL (size, align) * align;
1092 size += GET_MODE_SIZE (mode);
1093 apply_result_mode[regno] = mode;
1095 else
1096 apply_result_mode[regno] = VOIDmode;
1098 /* Allow targets that use untyped_call and untyped_return to override
1099 the size so that machine-specific information can be stored here. */
1100 #ifdef APPLY_RESULT_SIZE
1101 size = APPLY_RESULT_SIZE;
1102 #endif
1104 return size;
1107 #if defined (HAVE_untyped_call) || defined (HAVE_untyped_return)
1108 /* Create a vector describing the result block RESULT. If SAVEP is true,
1109 the result block is used to save the values; otherwise it is used to
1110 restore the values. */
1112 static rtx
1113 result_vector (int savep, rtx result)
1115 int regno, size, align, nelts;
1116 enum machine_mode mode;
1117 rtx reg, mem;
1118 rtx *savevec = alloca (FIRST_PSEUDO_REGISTER * sizeof (rtx));
1120 size = nelts = 0;
1121 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1122 if ((mode = apply_result_mode[regno]) != VOIDmode)
1124 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1125 if (size % align != 0)
1126 size = CEIL (size, align) * align;
1127 reg = gen_rtx_REG (mode, savep ? regno : INCOMING_REGNO (regno));
1128 mem = adjust_address (result, mode, size);
1129 savevec[nelts++] = (savep
1130 ? gen_rtx_SET (VOIDmode, mem, reg)
1131 : gen_rtx_SET (VOIDmode, reg, mem));
1132 size += GET_MODE_SIZE (mode);
1134 return gen_rtx_PARALLEL (VOIDmode, gen_rtvec_v (nelts, savevec));
1136 #endif /* HAVE_untyped_call or HAVE_untyped_return */
1138 /* Save the state required to perform an untyped call with the same
1139 arguments as were passed to the current function. */
1141 static rtx
1142 expand_builtin_apply_args_1 (void)
1144 rtx registers, tem;
1145 int size, align, regno;
1146 enum machine_mode mode;
1147 rtx struct_incoming_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 1);
1149 /* Create a block where the arg-pointer, structure value address,
1150 and argument registers can be saved. */
1151 registers = assign_stack_local (BLKmode, apply_args_size (), -1);
1153 /* Walk past the arg-pointer and structure value address. */
1154 size = GET_MODE_SIZE (Pmode);
1155 if (targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0))
1156 size += GET_MODE_SIZE (Pmode);
1158 /* Save each register used in calling a function to the block. */
1159 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1160 if ((mode = apply_args_mode[regno]) != VOIDmode)
1162 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1163 if (size % align != 0)
1164 size = CEIL (size, align) * align;
1166 tem = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1168 emit_move_insn (adjust_address (registers, mode, size), tem);
1169 size += GET_MODE_SIZE (mode);
1172 /* Save the arg pointer to the block. */
1173 tem = copy_to_reg (virtual_incoming_args_rtx);
1174 #ifdef STACK_GROWS_DOWNWARD
1175 /* We need the pointer as the caller actually passed them to us, not
1176 as we might have pretended they were passed. Make sure it's a valid
1177 operand, as emit_move_insn isn't expected to handle a PLUS. */
1179 = force_operand (plus_constant (tem, current_function_pretend_args_size),
1180 NULL_RTX);
1181 #endif
1182 emit_move_insn (adjust_address (registers, Pmode, 0), tem);
1184 size = GET_MODE_SIZE (Pmode);
1186 /* Save the structure value address unless this is passed as an
1187 "invisible" first argument. */
1188 if (struct_incoming_value)
1190 emit_move_insn (adjust_address (registers, Pmode, size),
1191 copy_to_reg (struct_incoming_value));
1192 size += GET_MODE_SIZE (Pmode);
1195 /* Return the address of the block. */
1196 return copy_addr_to_reg (XEXP (registers, 0));
1199 /* __builtin_apply_args returns block of memory allocated on
1200 the stack into which is stored the arg pointer, structure
1201 value address, static chain, and all the registers that might
1202 possibly be used in performing a function call. The code is
1203 moved to the start of the function so the incoming values are
1204 saved. */
1206 static rtx
1207 expand_builtin_apply_args (void)
1209 /* Don't do __builtin_apply_args more than once in a function.
1210 Save the result of the first call and reuse it. */
1211 if (apply_args_value != 0)
1212 return apply_args_value;
1214 /* When this function is called, it means that registers must be
1215 saved on entry to this function. So we migrate the
1216 call to the first insn of this function. */
1217 rtx temp;
1218 rtx seq;
1220 start_sequence ();
1221 temp = expand_builtin_apply_args_1 ();
1222 seq = get_insns ();
1223 end_sequence ();
1225 apply_args_value = temp;
1227 /* Put the insns after the NOTE that starts the function.
1228 If this is inside a start_sequence, make the outer-level insn
1229 chain current, so the code is placed at the start of the
1230 function. */
1231 push_topmost_sequence ();
1232 emit_insn_before (seq, NEXT_INSN (get_insns ()));
1233 pop_topmost_sequence ();
1234 return temp;
1238 /* Perform an untyped call and save the state required to perform an
1239 untyped return of whatever value was returned by the given function. */
1241 static rtx
1242 expand_builtin_apply (rtx function, rtx arguments, rtx argsize)
1244 int size, align, regno;
1245 enum machine_mode mode;
1246 rtx incoming_args, result, reg, dest, src, call_insn;
1247 rtx old_stack_level = 0;
1248 rtx call_fusage = 0;
1249 rtx struct_value = targetm.calls.struct_value_rtx (cfun ? TREE_TYPE (cfun->decl) : 0, 0);
1251 arguments = convert_memory_address (Pmode, arguments);
1253 /* Create a block where the return registers can be saved. */
1254 result = assign_stack_local (BLKmode, apply_result_size (), -1);
1256 /* Fetch the arg pointer from the ARGUMENTS block. */
1257 incoming_args = gen_reg_rtx (Pmode);
1258 emit_move_insn (incoming_args, gen_rtx_MEM (Pmode, arguments));
1259 #ifndef STACK_GROWS_DOWNWARD
1260 incoming_args = expand_simple_binop (Pmode, MINUS, incoming_args, argsize,
1261 incoming_args, 0, OPTAB_LIB_WIDEN);
1262 #endif
1264 /* Perform postincrements before actually calling the function. */
1265 emit_queue ();
1267 /* Push a new argument block and copy the arguments. Do not allow
1268 the (potential) memcpy call below to interfere with our stack
1269 manipulations. */
1270 do_pending_stack_adjust ();
1271 NO_DEFER_POP;
1273 /* Save the stack with nonlocal if available. */
1274 #ifdef HAVE_save_stack_nonlocal
1275 if (HAVE_save_stack_nonlocal)
1276 emit_stack_save (SAVE_NONLOCAL, &old_stack_level, NULL_RTX);
1277 else
1278 #endif
1279 emit_stack_save (SAVE_BLOCK, &old_stack_level, NULL_RTX);
1281 /* Allocate a block of memory onto the stack and copy the memory
1282 arguments to the outgoing arguments address. */
1283 allocate_dynamic_stack_space (argsize, 0, BITS_PER_UNIT);
1284 dest = virtual_outgoing_args_rtx;
1285 #ifndef STACK_GROWS_DOWNWARD
1286 if (GET_CODE (argsize) == CONST_INT)
1287 dest = plus_constant (dest, -INTVAL (argsize));
1288 else
1289 dest = gen_rtx_PLUS (Pmode, dest, negate_rtx (Pmode, argsize));
1290 #endif
1291 dest = gen_rtx_MEM (BLKmode, dest);
1292 set_mem_align (dest, PARM_BOUNDARY);
1293 src = gen_rtx_MEM (BLKmode, incoming_args);
1294 set_mem_align (src, PARM_BOUNDARY);
1295 emit_block_move (dest, src, argsize, BLOCK_OP_NORMAL);
1297 /* Refer to the argument block. */
1298 apply_args_size ();
1299 arguments = gen_rtx_MEM (BLKmode, arguments);
1300 set_mem_align (arguments, PARM_BOUNDARY);
1302 /* Walk past the arg-pointer and structure value address. */
1303 size = GET_MODE_SIZE (Pmode);
1304 if (struct_value)
1305 size += GET_MODE_SIZE (Pmode);
1307 /* Restore each of the registers previously saved. Make USE insns
1308 for each of these registers for use in making the call. */
1309 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1310 if ((mode = apply_args_mode[regno]) != VOIDmode)
1312 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1313 if (size % align != 0)
1314 size = CEIL (size, align) * align;
1315 reg = gen_rtx_REG (mode, regno);
1316 emit_move_insn (reg, adjust_address (arguments, mode, size));
1317 use_reg (&call_fusage, reg);
1318 size += GET_MODE_SIZE (mode);
1321 /* Restore the structure value address unless this is passed as an
1322 "invisible" first argument. */
1323 size = GET_MODE_SIZE (Pmode);
1324 if (struct_value)
1326 rtx value = gen_reg_rtx (Pmode);
1327 emit_move_insn (value, adjust_address (arguments, Pmode, size));
1328 emit_move_insn (struct_value, value);
1329 if (GET_CODE (struct_value) == REG)
1330 use_reg (&call_fusage, struct_value);
1331 size += GET_MODE_SIZE (Pmode);
1334 /* All arguments and registers used for the call are set up by now! */
1335 function = prepare_call_address (function, NULL, &call_fusage, 0, 0);
1337 /* Ensure address is valid. SYMBOL_REF is already valid, so no need,
1338 and we don't want to load it into a register as an optimization,
1339 because prepare_call_address already did it if it should be done. */
1340 if (GET_CODE (function) != SYMBOL_REF)
1341 function = memory_address (FUNCTION_MODE, function);
1343 /* Generate the actual call instruction and save the return value. */
1344 #ifdef HAVE_untyped_call
1345 if (HAVE_untyped_call)
1346 emit_call_insn (gen_untyped_call (gen_rtx_MEM (FUNCTION_MODE, function),
1347 result, result_vector (1, result)));
1348 else
1349 #endif
1350 #ifdef HAVE_call_value
1351 if (HAVE_call_value)
1353 rtx valreg = 0;
1355 /* Locate the unique return register. It is not possible to
1356 express a call that sets more than one return register using
1357 call_value; use untyped_call for that. In fact, untyped_call
1358 only needs to save the return registers in the given block. */
1359 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1360 if ((mode = apply_result_mode[regno]) != VOIDmode)
1362 if (valreg)
1363 abort (); /* HAVE_untyped_call required. */
1364 valreg = gen_rtx_REG (mode, regno);
1367 emit_call_insn (GEN_CALL_VALUE (valreg,
1368 gen_rtx_MEM (FUNCTION_MODE, function),
1369 const0_rtx, NULL_RTX, const0_rtx));
1371 emit_move_insn (adjust_address (result, GET_MODE (valreg), 0), valreg);
1373 else
1374 #endif
1375 abort ();
1377 /* Find the CALL insn we just emitted, and attach the register usage
1378 information. */
1379 call_insn = last_call_insn ();
1380 add_function_usage_to (call_insn, call_fusage);
1382 /* Restore the stack. */
1383 #ifdef HAVE_save_stack_nonlocal
1384 if (HAVE_save_stack_nonlocal)
1385 emit_stack_restore (SAVE_NONLOCAL, old_stack_level, NULL_RTX);
1386 else
1387 #endif
1388 emit_stack_restore (SAVE_BLOCK, old_stack_level, NULL_RTX);
1390 OK_DEFER_POP;
1392 /* Return the address of the result block. */
1393 result = copy_addr_to_reg (XEXP (result, 0));
1394 return convert_memory_address (ptr_mode, result);
1397 /* Perform an untyped return. */
1399 static void
1400 expand_builtin_return (rtx result)
1402 int size, align, regno;
1403 enum machine_mode mode;
1404 rtx reg;
1405 rtx call_fusage = 0;
1407 result = convert_memory_address (Pmode, result);
1409 apply_result_size ();
1410 result = gen_rtx_MEM (BLKmode, result);
1412 #ifdef HAVE_untyped_return
1413 if (HAVE_untyped_return)
1415 emit_jump_insn (gen_untyped_return (result, result_vector (0, result)));
1416 emit_barrier ();
1417 return;
1419 #endif
1421 /* Restore the return value and note that each value is used. */
1422 size = 0;
1423 for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
1424 if ((mode = apply_result_mode[regno]) != VOIDmode)
1426 align = GET_MODE_ALIGNMENT (mode) / BITS_PER_UNIT;
1427 if (size % align != 0)
1428 size = CEIL (size, align) * align;
1429 reg = gen_rtx_REG (mode, INCOMING_REGNO (regno));
1430 emit_move_insn (reg, adjust_address (result, mode, size));
1432 push_to_sequence (call_fusage);
1433 emit_insn (gen_rtx_USE (VOIDmode, reg));
1434 call_fusage = get_insns ();
1435 end_sequence ();
1436 size += GET_MODE_SIZE (mode);
1439 /* Put the USE insns before the return. */
1440 emit_insn (call_fusage);
1442 /* Return whatever values was restored by jumping directly to the end
1443 of the function. */
1444 expand_naked_return ();
1447 /* Used by expand_builtin_classify_type and fold_builtin_classify_type. */
1449 static enum type_class
1450 type_to_class (tree type)
1452 switch (TREE_CODE (type))
1454 case VOID_TYPE: return void_type_class;
1455 case INTEGER_TYPE: return integer_type_class;
1456 case CHAR_TYPE: return char_type_class;
1457 case ENUMERAL_TYPE: return enumeral_type_class;
1458 case BOOLEAN_TYPE: return boolean_type_class;
1459 case POINTER_TYPE: return pointer_type_class;
1460 case REFERENCE_TYPE: return reference_type_class;
1461 case OFFSET_TYPE: return offset_type_class;
1462 case REAL_TYPE: return real_type_class;
1463 case COMPLEX_TYPE: return complex_type_class;
1464 case FUNCTION_TYPE: return function_type_class;
1465 case METHOD_TYPE: return method_type_class;
1466 case RECORD_TYPE: return record_type_class;
1467 case UNION_TYPE:
1468 case QUAL_UNION_TYPE: return union_type_class;
1469 case ARRAY_TYPE: return (TYPE_STRING_FLAG (type)
1470 ? string_type_class : array_type_class);
1471 case SET_TYPE: return set_type_class;
1472 case FILE_TYPE: return file_type_class;
1473 case LANG_TYPE: return lang_type_class;
1474 default: return no_type_class;
1478 /* Expand a call to __builtin_classify_type with arguments found in
1479 ARGLIST. */
1481 static rtx
1482 expand_builtin_classify_type (tree arglist)
1484 if (arglist != 0)
1485 return GEN_INT (type_to_class (TREE_TYPE (TREE_VALUE (arglist))));
1486 return GEN_INT (no_type_class);
1489 /* This helper macro, meant to be used in mathfn_built_in below,
1490 determines which among a set of three builtin math functions is
1491 appropriate for a given type mode. The `F' and `L' cases are
1492 automatically generated from the `double' case. */
1493 #define CASE_MATHFN(BUILT_IN_MATHFN) \
1494 case BUILT_IN_MATHFN: case BUILT_IN_MATHFN##F: case BUILT_IN_MATHFN##L: \
1495 fcode = BUILT_IN_MATHFN; fcodef = BUILT_IN_MATHFN##F ; \
1496 fcodel = BUILT_IN_MATHFN##L ; break;
1498 /* Return mathematic function equivalent to FN but operating directly
1499 on TYPE, if available. If we can't do the conversion, return zero. */
1500 tree
1501 mathfn_built_in (tree type, enum built_in_function fn)
1503 enum built_in_function fcode, fcodef, fcodel;
1505 switch (fn)
1507 CASE_MATHFN (BUILT_IN_ACOS)
1508 CASE_MATHFN (BUILT_IN_ACOSH)
1509 CASE_MATHFN (BUILT_IN_ASIN)
1510 CASE_MATHFN (BUILT_IN_ASINH)
1511 CASE_MATHFN (BUILT_IN_ATAN)
1512 CASE_MATHFN (BUILT_IN_ATAN2)
1513 CASE_MATHFN (BUILT_IN_ATANH)
1514 CASE_MATHFN (BUILT_IN_CBRT)
1515 CASE_MATHFN (BUILT_IN_CEIL)
1516 CASE_MATHFN (BUILT_IN_COPYSIGN)
1517 CASE_MATHFN (BUILT_IN_COS)
1518 CASE_MATHFN (BUILT_IN_COSH)
1519 CASE_MATHFN (BUILT_IN_DREM)
1520 CASE_MATHFN (BUILT_IN_ERF)
1521 CASE_MATHFN (BUILT_IN_ERFC)
1522 CASE_MATHFN (BUILT_IN_EXP)
1523 CASE_MATHFN (BUILT_IN_EXP10)
1524 CASE_MATHFN (BUILT_IN_EXP2)
1525 CASE_MATHFN (BUILT_IN_EXPM1)
1526 CASE_MATHFN (BUILT_IN_FABS)
1527 CASE_MATHFN (BUILT_IN_FDIM)
1528 CASE_MATHFN (BUILT_IN_FLOOR)
1529 CASE_MATHFN (BUILT_IN_FMA)
1530 CASE_MATHFN (BUILT_IN_FMAX)
1531 CASE_MATHFN (BUILT_IN_FMIN)
1532 CASE_MATHFN (BUILT_IN_FMOD)
1533 CASE_MATHFN (BUILT_IN_FREXP)
1534 CASE_MATHFN (BUILT_IN_GAMMA)
1535 CASE_MATHFN (BUILT_IN_HUGE_VAL)
1536 CASE_MATHFN (BUILT_IN_HYPOT)
1537 CASE_MATHFN (BUILT_IN_ILOGB)
1538 CASE_MATHFN (BUILT_IN_INF)
1539 CASE_MATHFN (BUILT_IN_J0)
1540 CASE_MATHFN (BUILT_IN_J1)
1541 CASE_MATHFN (BUILT_IN_JN)
1542 CASE_MATHFN (BUILT_IN_LDEXP)
1543 CASE_MATHFN (BUILT_IN_LGAMMA)
1544 CASE_MATHFN (BUILT_IN_LLRINT)
1545 CASE_MATHFN (BUILT_IN_LLROUND)
1546 CASE_MATHFN (BUILT_IN_LOG)
1547 CASE_MATHFN (BUILT_IN_LOG10)
1548 CASE_MATHFN (BUILT_IN_LOG1P)
1549 CASE_MATHFN (BUILT_IN_LOG2)
1550 CASE_MATHFN (BUILT_IN_LOGB)
1551 CASE_MATHFN (BUILT_IN_LRINT)
1552 CASE_MATHFN (BUILT_IN_LROUND)
1553 CASE_MATHFN (BUILT_IN_MODF)
1554 CASE_MATHFN (BUILT_IN_NAN)
1555 CASE_MATHFN (BUILT_IN_NANS)
1556 CASE_MATHFN (BUILT_IN_NEARBYINT)
1557 CASE_MATHFN (BUILT_IN_NEXTAFTER)
1558 CASE_MATHFN (BUILT_IN_NEXTTOWARD)
1559 CASE_MATHFN (BUILT_IN_POW)
1560 CASE_MATHFN (BUILT_IN_POW10)
1561 CASE_MATHFN (BUILT_IN_REMAINDER)
1562 CASE_MATHFN (BUILT_IN_REMQUO)
1563 CASE_MATHFN (BUILT_IN_RINT)
1564 CASE_MATHFN (BUILT_IN_ROUND)
1565 CASE_MATHFN (BUILT_IN_SCALB)
1566 CASE_MATHFN (BUILT_IN_SCALBLN)
1567 CASE_MATHFN (BUILT_IN_SCALBN)
1568 CASE_MATHFN (BUILT_IN_SIGNIFICAND)
1569 CASE_MATHFN (BUILT_IN_SIN)
1570 CASE_MATHFN (BUILT_IN_SINCOS)
1571 CASE_MATHFN (BUILT_IN_SINH)
1572 CASE_MATHFN (BUILT_IN_SQRT)
1573 CASE_MATHFN (BUILT_IN_TAN)
1574 CASE_MATHFN (BUILT_IN_TANH)
1575 CASE_MATHFN (BUILT_IN_TGAMMA)
1576 CASE_MATHFN (BUILT_IN_TRUNC)
1577 CASE_MATHFN (BUILT_IN_Y0)
1578 CASE_MATHFN (BUILT_IN_Y1)
1579 CASE_MATHFN (BUILT_IN_YN)
1581 default:
1582 return 0;
1585 if (TYPE_MAIN_VARIANT (type) == double_type_node)
1586 return implicit_built_in_decls[fcode];
1587 else if (TYPE_MAIN_VARIANT (type) == float_type_node)
1588 return implicit_built_in_decls[fcodef];
1589 else if (TYPE_MAIN_VARIANT (type) == long_double_type_node)
1590 return implicit_built_in_decls[fcodel];
1591 else
1592 return 0;
1595 /* If errno must be maintained, expand the RTL to check if the result,
1596 TARGET, of a built-in function call, EXP, is NaN, and if so set
1597 errno to EDOM. */
1599 static void
1600 expand_errno_check (tree exp, rtx target)
1602 rtx lab = gen_label_rtx ();
1604 /* Test the result; if it is NaN, set errno=EDOM because
1605 the argument was not in the domain. */
1606 emit_cmp_and_jump_insns (target, target, EQ, 0, GET_MODE (target),
1607 0, lab);
1609 #ifdef TARGET_EDOM
1610 /* If this built-in doesn't throw an exception, set errno directly. */
1611 if (TREE_NOTHROW (TREE_OPERAND (TREE_OPERAND (exp, 0), 0)))
1613 #ifdef GEN_ERRNO_RTX
1614 rtx errno_rtx = GEN_ERRNO_RTX;
1615 #else
1616 rtx errno_rtx
1617 = gen_rtx_MEM (word_mode, gen_rtx_SYMBOL_REF (Pmode, "errno"));
1618 #endif
1619 emit_move_insn (errno_rtx, GEN_INT (TARGET_EDOM));
1620 emit_label (lab);
1621 return;
1623 #endif
1625 /* We can't set errno=EDOM directly; let the library call do it.
1626 Pop the arguments right away in case the call gets deleted. */
1627 NO_DEFER_POP;
1628 expand_call (exp, target, 0);
1629 OK_DEFER_POP;
1630 emit_label (lab);
1634 /* Expand a call to one of the builtin math functions (sqrt, exp, or log).
1635 Return 0 if a normal call should be emitted rather than expanding the
1636 function in-line. EXP is the expression that is a call to the builtin
1637 function; if convenient, the result should be placed in TARGET.
1638 SUBTARGET may be used as the target for computing one of EXP's operands. */
1640 static rtx
1641 expand_builtin_mathfn (tree exp, rtx target, rtx subtarget)
1643 optab builtin_optab;
1644 rtx op0, insns, before_call;
1645 tree fndecl = get_callee_fndecl (exp);
1646 tree arglist = TREE_OPERAND (exp, 1);
1647 enum machine_mode mode;
1648 bool errno_set = false;
1649 tree arg, narg;
1651 if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
1652 return 0;
1654 arg = TREE_VALUE (arglist);
1656 switch (DECL_FUNCTION_CODE (fndecl))
1658 case BUILT_IN_SQRT:
1659 case BUILT_IN_SQRTF:
1660 case BUILT_IN_SQRTL:
1661 errno_set = ! tree_expr_nonnegative_p (arg);
1662 builtin_optab = sqrt_optab;
1663 break;
1664 case BUILT_IN_EXP:
1665 case BUILT_IN_EXPF:
1666 case BUILT_IN_EXPL:
1667 errno_set = true; builtin_optab = exp_optab; break;
1668 case BUILT_IN_EXP10:
1669 case BUILT_IN_EXP10F:
1670 case BUILT_IN_EXP10L:
1671 case BUILT_IN_POW10:
1672 case BUILT_IN_POW10F:
1673 case BUILT_IN_POW10L:
1674 errno_set = true; builtin_optab = exp10_optab; break;
1675 case BUILT_IN_EXP2:
1676 case BUILT_IN_EXP2F:
1677 case BUILT_IN_EXP2L:
1678 errno_set = true; builtin_optab = exp2_optab; break;
1679 case BUILT_IN_EXPM1:
1680 case BUILT_IN_EXPM1F:
1681 case BUILT_IN_EXPM1L:
1682 errno_set = true; builtin_optab = expm1_optab; break;
1683 case BUILT_IN_LOGB:
1684 case BUILT_IN_LOGBF:
1685 case BUILT_IN_LOGBL:
1686 errno_set = true; builtin_optab = logb_optab; break;
1687 case BUILT_IN_ILOGB:
1688 case BUILT_IN_ILOGBF:
1689 case BUILT_IN_ILOGBL:
1690 errno_set = true; builtin_optab = ilogb_optab; break;
1691 case BUILT_IN_LOG:
1692 case BUILT_IN_LOGF:
1693 case BUILT_IN_LOGL:
1694 errno_set = true; builtin_optab = log_optab; break;
1695 case BUILT_IN_LOG10:
1696 case BUILT_IN_LOG10F:
1697 case BUILT_IN_LOG10L:
1698 errno_set = true; builtin_optab = log10_optab; break;
1699 case BUILT_IN_LOG2:
1700 case BUILT_IN_LOG2F:
1701 case BUILT_IN_LOG2L:
1702 errno_set = true; builtin_optab = log2_optab; break;
1703 case BUILT_IN_LOG1P:
1704 case BUILT_IN_LOG1PF:
1705 case BUILT_IN_LOG1PL:
1706 errno_set = true; builtin_optab = log1p_optab; break;
1707 case BUILT_IN_ASIN:
1708 case BUILT_IN_ASINF:
1709 case BUILT_IN_ASINL:
1710 builtin_optab = asin_optab; break;
1711 case BUILT_IN_ACOS:
1712 case BUILT_IN_ACOSF:
1713 case BUILT_IN_ACOSL:
1714 builtin_optab = acos_optab; break;
1715 case BUILT_IN_TAN:
1716 case BUILT_IN_TANF:
1717 case BUILT_IN_TANL:
1718 builtin_optab = tan_optab; break;
1719 case BUILT_IN_ATAN:
1720 case BUILT_IN_ATANF:
1721 case BUILT_IN_ATANL:
1722 builtin_optab = atan_optab; break;
1723 case BUILT_IN_FLOOR:
1724 case BUILT_IN_FLOORF:
1725 case BUILT_IN_FLOORL:
1726 builtin_optab = floor_optab; break;
1727 case BUILT_IN_CEIL:
1728 case BUILT_IN_CEILF:
1729 case BUILT_IN_CEILL:
1730 builtin_optab = ceil_optab; break;
1731 case BUILT_IN_TRUNC:
1732 case BUILT_IN_TRUNCF:
1733 case BUILT_IN_TRUNCL:
1734 builtin_optab = btrunc_optab; break;
1735 case BUILT_IN_ROUND:
1736 case BUILT_IN_ROUNDF:
1737 case BUILT_IN_ROUNDL:
1738 builtin_optab = round_optab; break;
1739 case BUILT_IN_NEARBYINT:
1740 case BUILT_IN_NEARBYINTF:
1741 case BUILT_IN_NEARBYINTL:
1742 builtin_optab = nearbyint_optab; break;
1743 default:
1744 abort ();
1747 /* Make a suitable register to place result in. */
1748 mode = TYPE_MODE (TREE_TYPE (exp));
1750 if (! flag_errno_math || ! HONOR_NANS (mode))
1751 errno_set = false;
1753 /* Before working hard, check whether the instruction is available. */
1754 if (builtin_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
1756 target = gen_reg_rtx (mode);
1758 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
1759 need to expand the argument again. This way, we will not perform
1760 side-effects more the once. */
1761 narg = builtin_save_expr (arg);
1762 if (narg != arg)
1764 arglist = build_tree_list (NULL_TREE, arg);
1765 exp = build_function_call_expr (fndecl, arglist);
1768 op0 = expand_expr (arg, subtarget, VOIDmode, 0);
1770 emit_queue ();
1771 start_sequence ();
1773 /* Compute into TARGET.
1774 Set TARGET to wherever the result comes back. */
1775 target = expand_unop (mode, builtin_optab, op0, target, 0);
1777 if (target != 0)
1779 if (errno_set)
1780 expand_errno_check (exp, target);
1782 /* Output the entire sequence. */
1783 insns = get_insns ();
1784 end_sequence ();
1785 emit_insn (insns);
1786 return target;
1789 /* If we were unable to expand via the builtin, stop the sequence
1790 (without outputting the insns) and call to the library function
1791 with the stabilized argument list. */
1792 end_sequence ();
1795 before_call = get_last_insn ();
1797 target = expand_call (exp, target, target == const0_rtx);
1799 /* If this is a sqrt operation and we don't care about errno, try to
1800 attach a REG_EQUAL note with a SQRT rtx to the emitted libcall.
1801 This allows the semantics of the libcall to be visible to the RTL
1802 optimizers. */
1803 if (builtin_optab == sqrt_optab && !errno_set)
1805 /* Search backwards through the insns emitted by expand_call looking
1806 for the instruction with the REG_RETVAL note. */
1807 rtx last = get_last_insn ();
1808 while (last != before_call)
1810 if (find_reg_note (last, REG_RETVAL, NULL))
1812 rtx note = find_reg_note (last, REG_EQUAL, NULL);
1813 /* Check that the REQ_EQUAL note is an EXPR_LIST with
1814 two elements, i.e. symbol_ref(sqrt) and the operand. */
1815 if (note
1816 && GET_CODE (note) == EXPR_LIST
1817 && GET_CODE (XEXP (note, 0)) == EXPR_LIST
1818 && XEXP (XEXP (note, 0), 1) != NULL_RTX
1819 && XEXP (XEXP (XEXP (note, 0), 1), 1) == NULL_RTX)
1821 rtx operand = XEXP (XEXP (XEXP (note, 0), 1), 0);
1822 /* Check operand is a register with expected mode. */
1823 if (operand
1824 && GET_CODE (operand) == REG
1825 && GET_MODE (operand) == mode)
1827 /* Replace the REG_EQUAL note with a SQRT rtx. */
1828 rtx equiv = gen_rtx_SQRT (mode, operand);
1829 set_unique_reg_note (last, REG_EQUAL, equiv);
1832 break;
1834 last = PREV_INSN (last);
1838 return target;
1841 /* Expand a call to the builtin binary math functions (pow and atan2).
1842 Return 0 if a normal call should be emitted rather than expanding the
1843 function in-line. EXP is the expression that is a call to the builtin
1844 function; if convenient, the result should be placed in TARGET.
1845 SUBTARGET may be used as the target for computing one of EXP's
1846 operands. */
1848 static rtx
1849 expand_builtin_mathfn_2 (tree exp, rtx target, rtx subtarget)
1851 optab builtin_optab;
1852 rtx op0, op1, insns;
1853 tree fndecl = get_callee_fndecl (exp);
1854 tree arglist = TREE_OPERAND (exp, 1);
1855 tree arg0, arg1, temp, narg;
1856 enum machine_mode mode;
1857 bool errno_set = true;
1858 bool stable = true;
1860 if (!validate_arglist (arglist, REAL_TYPE, REAL_TYPE, VOID_TYPE))
1861 return 0;
1863 arg0 = TREE_VALUE (arglist);
1864 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
1866 switch (DECL_FUNCTION_CODE (fndecl))
1868 case BUILT_IN_POW:
1869 case BUILT_IN_POWF:
1870 case BUILT_IN_POWL:
1871 builtin_optab = pow_optab; break;
1872 case BUILT_IN_ATAN2:
1873 case BUILT_IN_ATAN2F:
1874 case BUILT_IN_ATAN2L:
1875 builtin_optab = atan2_optab; break;
1876 case BUILT_IN_FMOD:
1877 case BUILT_IN_FMODF:
1878 case BUILT_IN_FMODL:
1879 builtin_optab = fmod_optab; break;
1880 case BUILT_IN_DREM:
1881 case BUILT_IN_DREMF:
1882 case BUILT_IN_DREML:
1883 builtin_optab = drem_optab; break;
1884 default:
1885 abort ();
1888 /* Make a suitable register to place result in. */
1889 mode = TYPE_MODE (TREE_TYPE (exp));
1891 /* Before working hard, check whether the instruction is available. */
1892 if (builtin_optab->handlers[(int) mode].insn_code == CODE_FOR_nothing)
1893 return 0;
1895 target = gen_reg_rtx (mode);
1897 if (! flag_errno_math || ! HONOR_NANS (mode))
1898 errno_set = false;
1900 /* Always stabilize the argument list. */
1901 narg = builtin_save_expr (arg1);
1902 if (narg != arg1)
1904 temp = build_tree_list (NULL_TREE, narg);
1905 stable = false;
1907 else
1908 temp = TREE_CHAIN (arglist);
1910 narg = builtin_save_expr (arg0);
1911 if (narg != arg0)
1913 arglist = tree_cons (NULL_TREE, narg, temp);
1914 stable = false;
1916 else if (! stable)
1917 arglist = tree_cons (NULL_TREE, arg0, temp);
1919 if (! stable)
1920 exp = build_function_call_expr (fndecl, arglist);
1922 op0 = expand_expr (arg0, subtarget, VOIDmode, 0);
1923 op1 = expand_expr (arg1, 0, VOIDmode, 0);
1925 emit_queue ();
1926 start_sequence ();
1928 /* Compute into TARGET.
1929 Set TARGET to wherever the result comes back. */
1930 target = expand_binop (mode, builtin_optab, op0, op1,
1931 target, 0, OPTAB_DIRECT);
1933 /* If we were unable to expand via the builtin, stop the sequence
1934 (without outputting the insns) and call to the library function
1935 with the stabilized argument list. */
1936 if (target == 0)
1938 end_sequence ();
1939 return expand_call (exp, target, target == const0_rtx);
1942 if (errno_set)
1943 expand_errno_check (exp, target);
1945 /* Output the entire sequence. */
1946 insns = get_insns ();
1947 end_sequence ();
1948 emit_insn (insns);
1950 return target;
1953 /* Expand a call to the builtin sin and cos math functions.
1954 Return 0 if a normal call should be emitted rather than expanding the
1955 function in-line. EXP is the expression that is a call to the builtin
1956 function; if convenient, the result should be placed in TARGET.
1957 SUBTARGET may be used as the target for computing one of EXP's
1958 operands. */
1960 static rtx
1961 expand_builtin_mathfn_3 (tree exp, rtx target, rtx subtarget)
1963 optab builtin_optab;
1964 rtx op0, insns, before_call;
1965 tree fndecl = get_callee_fndecl (exp);
1966 tree arglist = TREE_OPERAND (exp, 1);
1967 enum machine_mode mode;
1968 bool errno_set = false;
1969 tree arg, narg;
1971 if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
1972 return 0;
1974 arg = TREE_VALUE (arglist);
1976 switch (DECL_FUNCTION_CODE (fndecl))
1978 case BUILT_IN_SIN:
1979 case BUILT_IN_SINF:
1980 case BUILT_IN_SINL:
1981 case BUILT_IN_COS:
1982 case BUILT_IN_COSF:
1983 case BUILT_IN_COSL:
1984 builtin_optab = sincos_optab; break;
1985 default:
1986 abort ();
1989 /* Make a suitable register to place result in. */
1990 mode = TYPE_MODE (TREE_TYPE (exp));
1992 if (! flag_errno_math || ! HONOR_NANS (mode))
1993 errno_set = false;
1995 /* Check if sincos insn is available, otherwise fallback
1996 to sin or cos insn. */
1997 if (builtin_optab->handlers[(int) mode].insn_code == CODE_FOR_nothing) {
1998 switch (DECL_FUNCTION_CODE (fndecl))
2000 case BUILT_IN_SIN:
2001 case BUILT_IN_SINF:
2002 case BUILT_IN_SINL:
2003 builtin_optab = sin_optab; break;
2004 case BUILT_IN_COS:
2005 case BUILT_IN_COSF:
2006 case BUILT_IN_COSL:
2007 builtin_optab = cos_optab; break;
2008 default:
2009 abort();
2013 /* Before working hard, check whether the instruction is available. */
2014 if (builtin_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
2016 target = gen_reg_rtx (mode);
2018 /* Wrap the computation of the argument in a SAVE_EXPR, as we may
2019 need to expand the argument again. This way, we will not perform
2020 side-effects more the once. */
2021 narg = save_expr (arg);
2022 if (narg != arg)
2024 arglist = build_tree_list (NULL_TREE, arg);
2025 exp = build_function_call_expr (fndecl, arglist);
2028 op0 = expand_expr (arg, subtarget, VOIDmode, 0);
2030 emit_queue ();
2031 start_sequence ();
2033 /* Compute into TARGET.
2034 Set TARGET to wherever the result comes back. */
2035 if (builtin_optab == sincos_optab)
2037 switch (DECL_FUNCTION_CODE (fndecl))
2039 case BUILT_IN_SIN:
2040 case BUILT_IN_SINF:
2041 case BUILT_IN_SINL:
2042 if (!expand_twoval_unop (builtin_optab, op0, 0, target, 0))
2043 abort();
2044 break;
2045 case BUILT_IN_COS:
2046 case BUILT_IN_COSF:
2047 case BUILT_IN_COSL:
2048 if (!expand_twoval_unop (builtin_optab, op0, target, 0, 0))
2049 abort();
2050 break;
2051 default:
2052 abort();
2055 else
2057 target = expand_unop (mode, builtin_optab, op0, target, 0);
2060 if (target != 0)
2062 if (errno_set)
2063 expand_errno_check (exp, target);
2065 /* Output the entire sequence. */
2066 insns = get_insns ();
2067 end_sequence ();
2068 emit_insn (insns);
2069 return target;
2072 /* If we were unable to expand via the builtin, stop the sequence
2073 (without outputting the insns) and call to the library function
2074 with the stabilized argument list. */
2075 end_sequence ();
2078 before_call = get_last_insn ();
2080 target = expand_call (exp, target, target == const0_rtx);
2082 return target;
2085 /* To evaluate powi(x,n), the floating point value x raised to the
2086 constant integer exponent n, we use a hybrid algorithm that
2087 combines the "window method" with look-up tables. For an
2088 introduction to exponentiation algorithms and "addition chains",
2089 see section 4.6.3, "Evaluation of Powers" of Donald E. Knuth,
2090 "Seminumerical Algorithms", Vol. 2, "The Art of Computer Programming",
2091 3rd Edition, 1998, and Daniel M. Gordon, "A Survey of Fast Exponentiation
2092 Methods", Journal of Algorithms, Vol. 27, pp. 129-146, 1998. */
2094 /* Provide a default value for POWI_MAX_MULTS, the maximum number of
2095 multiplications to inline before calling the system library's pow
2096 function. powi(x,n) requires at worst 2*bits(n)-2 multiplications,
2097 so this default never requires calling pow, powf or powl. */
2099 #ifndef POWI_MAX_MULTS
2100 #define POWI_MAX_MULTS (2*HOST_BITS_PER_WIDE_INT-2)
2101 #endif
2103 /* The size of the "optimal power tree" lookup table. All
2104 exponents less than this value are simply looked up in the
2105 powi_table below. This threshold is also used to size the
2106 cache of pseudo registers that hold intermediate results. */
2107 #define POWI_TABLE_SIZE 256
2109 /* The size, in bits of the window, used in the "window method"
2110 exponentiation algorithm. This is equivalent to a radix of
2111 (1<<POWI_WINDOW_SIZE) in the corresponding "m-ary method". */
2112 #define POWI_WINDOW_SIZE 3
2114 /* The following table is an efficient representation of an
2115 "optimal power tree". For each value, i, the corresponding
2116 value, j, in the table states than an optimal evaluation
2117 sequence for calculating pow(x,i) can be found by evaluating
2118 pow(x,j)*pow(x,i-j). An optimal power tree for the first
2119 100 integers is given in Knuth's "Seminumerical algorithms". */
2121 static const unsigned char powi_table[POWI_TABLE_SIZE] =
2123 0, 1, 1, 2, 2, 3, 3, 4, /* 0 - 7 */
2124 4, 6, 5, 6, 6, 10, 7, 9, /* 8 - 15 */
2125 8, 16, 9, 16, 10, 12, 11, 13, /* 16 - 23 */
2126 12, 17, 13, 18, 14, 24, 15, 26, /* 24 - 31 */
2127 16, 17, 17, 19, 18, 33, 19, 26, /* 32 - 39 */
2128 20, 25, 21, 40, 22, 27, 23, 44, /* 40 - 47 */
2129 24, 32, 25, 34, 26, 29, 27, 44, /* 48 - 55 */
2130 28, 31, 29, 34, 30, 60, 31, 36, /* 56 - 63 */
2131 32, 64, 33, 34, 34, 46, 35, 37, /* 64 - 71 */
2132 36, 65, 37, 50, 38, 48, 39, 69, /* 72 - 79 */
2133 40, 49, 41, 43, 42, 51, 43, 58, /* 80 - 87 */
2134 44, 64, 45, 47, 46, 59, 47, 76, /* 88 - 95 */
2135 48, 65, 49, 66, 50, 67, 51, 66, /* 96 - 103 */
2136 52, 70, 53, 74, 54, 104, 55, 74, /* 104 - 111 */
2137 56, 64, 57, 69, 58, 78, 59, 68, /* 112 - 119 */
2138 60, 61, 61, 80, 62, 75, 63, 68, /* 120 - 127 */
2139 64, 65, 65, 128, 66, 129, 67, 90, /* 128 - 135 */
2140 68, 73, 69, 131, 70, 94, 71, 88, /* 136 - 143 */
2141 72, 128, 73, 98, 74, 132, 75, 121, /* 144 - 151 */
2142 76, 102, 77, 124, 78, 132, 79, 106, /* 152 - 159 */
2143 80, 97, 81, 160, 82, 99, 83, 134, /* 160 - 167 */
2144 84, 86, 85, 95, 86, 160, 87, 100, /* 168 - 175 */
2145 88, 113, 89, 98, 90, 107, 91, 122, /* 176 - 183 */
2146 92, 111, 93, 102, 94, 126, 95, 150, /* 184 - 191 */
2147 96, 128, 97, 130, 98, 133, 99, 195, /* 192 - 199 */
2148 100, 128, 101, 123, 102, 164, 103, 138, /* 200 - 207 */
2149 104, 145, 105, 146, 106, 109, 107, 149, /* 208 - 215 */
2150 108, 200, 109, 146, 110, 170, 111, 157, /* 216 - 223 */
2151 112, 128, 113, 130, 114, 182, 115, 132, /* 224 - 231 */
2152 116, 200, 117, 132, 118, 158, 119, 206, /* 232 - 239 */
2153 120, 240, 121, 162, 122, 147, 123, 152, /* 240 - 247 */
2154 124, 166, 125, 214, 126, 138, 127, 153, /* 248 - 255 */
2158 /* Return the number of multiplications required to calculate
2159 powi(x,n) where n is less than POWI_TABLE_SIZE. This is a
2160 subroutine of powi_cost. CACHE is an array indicating
2161 which exponents have already been calculated. */
2163 static int
2164 powi_lookup_cost (unsigned HOST_WIDE_INT n, bool *cache)
2166 /* If we've already calculated this exponent, then this evaluation
2167 doesn't require any additional multiplications. */
2168 if (cache[n])
2169 return 0;
2171 cache[n] = true;
2172 return powi_lookup_cost (n - powi_table[n], cache)
2173 + powi_lookup_cost (powi_table[n], cache) + 1;
2176 /* Return the number of multiplications required to calculate
2177 powi(x,n) for an arbitrary x, given the exponent N. This
2178 function needs to be kept in sync with expand_powi below. */
2180 static int
2181 powi_cost (HOST_WIDE_INT n)
2183 bool cache[POWI_TABLE_SIZE];
2184 unsigned HOST_WIDE_INT digit;
2185 unsigned HOST_WIDE_INT val;
2186 int result;
2188 if (n == 0)
2189 return 0;
2191 /* Ignore the reciprocal when calculating the cost. */
2192 val = (n < 0) ? -n : n;
2194 /* Initialize the exponent cache. */
2195 memset (cache, 0, POWI_TABLE_SIZE * sizeof (bool));
2196 cache[1] = true;
2198 result = 0;
2200 while (val >= POWI_TABLE_SIZE)
2202 if (val & 1)
2204 digit = val & ((1 << POWI_WINDOW_SIZE) - 1);
2205 result += powi_lookup_cost (digit, cache)
2206 + POWI_WINDOW_SIZE + 1;
2207 val >>= POWI_WINDOW_SIZE;
2209 else
2211 val >>= 1;
2212 result++;
2216 return result + powi_lookup_cost (val, cache);
2219 /* Recursive subroutine of expand_powi. This function takes the array,
2220 CACHE, of already calculated exponents and an exponent N and returns
2221 an RTX that corresponds to CACHE[1]**N, as calculated in mode MODE. */
2223 static rtx
2224 expand_powi_1 (enum machine_mode mode, unsigned HOST_WIDE_INT n, rtx *cache)
2226 unsigned HOST_WIDE_INT digit;
2227 rtx target, result;
2228 rtx op0, op1;
2230 if (n < POWI_TABLE_SIZE)
2232 if (cache[n])
2233 return cache[n];
2235 target = gen_reg_rtx (mode);
2236 cache[n] = target;
2238 op0 = expand_powi_1 (mode, n - powi_table[n], cache);
2239 op1 = expand_powi_1 (mode, powi_table[n], cache);
2241 else if (n & 1)
2243 target = gen_reg_rtx (mode);
2244 digit = n & ((1 << POWI_WINDOW_SIZE) - 1);
2245 op0 = expand_powi_1 (mode, n - digit, cache);
2246 op1 = expand_powi_1 (mode, digit, cache);
2248 else
2250 target = gen_reg_rtx (mode);
2251 op0 = expand_powi_1 (mode, n >> 1, cache);
2252 op1 = op0;
2255 result = expand_mult (mode, op0, op1, target, 0);
2256 if (result != target)
2257 emit_move_insn (target, result);
2258 return target;
2261 /* Expand the RTL to evaluate powi(x,n) in mode MODE. X is the
2262 floating point operand in mode MODE, and N is the exponent. This
2263 function needs to be kept in sync with powi_cost above. */
2265 static rtx
2266 expand_powi (rtx x, enum machine_mode mode, HOST_WIDE_INT n)
2268 unsigned HOST_WIDE_INT val;
2269 rtx cache[POWI_TABLE_SIZE];
2270 rtx result;
2272 if (n == 0)
2273 return CONST1_RTX (mode);
2275 val = (n < 0) ? -n : n;
2277 memset (cache, 0, sizeof (cache));
2278 cache[1] = x;
2280 result = expand_powi_1 (mode, (n < 0) ? -n : n, cache);
2282 /* If the original exponent was negative, reciprocate the result. */
2283 if (n < 0)
2284 result = expand_binop (mode, sdiv_optab, CONST1_RTX (mode),
2285 result, NULL_RTX, 0, OPTAB_LIB_WIDEN);
2287 return result;
2290 /* Expand a call to the pow built-in mathematical function. Return 0 if
2291 a normal call should be emitted rather than expanding the function
2292 in-line. EXP is the expression that is a call to the builtin
2293 function; if convenient, the result should be placed in TARGET. */
2295 static rtx
2296 expand_builtin_pow (tree exp, rtx target, rtx subtarget)
2298 tree arglist = TREE_OPERAND (exp, 1);
2299 tree arg0, arg1;
2301 if (! validate_arglist (arglist, REAL_TYPE, REAL_TYPE, VOID_TYPE))
2302 return 0;
2304 arg0 = TREE_VALUE (arglist);
2305 arg1 = TREE_VALUE (TREE_CHAIN (arglist));
2307 if (TREE_CODE (arg1) == REAL_CST
2308 && ! TREE_CONSTANT_OVERFLOW (arg1))
2310 REAL_VALUE_TYPE cint;
2311 REAL_VALUE_TYPE c;
2312 HOST_WIDE_INT n;
2314 c = TREE_REAL_CST (arg1);
2315 n = real_to_integer (&c);
2316 real_from_integer (&cint, VOIDmode, n, n < 0 ? -1 : 0, 0);
2317 if (real_identical (&c, &cint))
2319 /* If the exponent is -1, 0, 1 or 2, then expand_powi is exact.
2320 Otherwise, check the number of multiplications required.
2321 Note that pow never sets errno for an integer exponent. */
2322 if ((n >= -1 && n <= 2)
2323 || (flag_unsafe_math_optimizations
2324 && ! optimize_size
2325 && powi_cost (n) <= POWI_MAX_MULTS))
2327 enum machine_mode mode = TYPE_MODE (TREE_TYPE (exp));
2328 rtx op = expand_expr (arg0, subtarget, VOIDmode, 0);
2329 op = force_reg (mode, op);
2330 return expand_powi (op, mode, n);
2335 if (! flag_unsafe_math_optimizations)
2336 return NULL_RTX;
2337 return expand_builtin_mathfn_2 (exp, target, subtarget);
2340 /* Expand expression EXP which is a call to the strlen builtin. Return 0
2341 if we failed the caller should emit a normal call, otherwise
2342 try to get the result in TARGET, if convenient. */
2344 static rtx
2345 expand_builtin_strlen (tree arglist, rtx target,
2346 enum machine_mode target_mode)
2348 if (!validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
2349 return 0;
2350 else
2352 rtx pat;
2353 tree len, src = TREE_VALUE (arglist);
2354 rtx result, src_reg, char_rtx, before_strlen;
2355 enum machine_mode insn_mode = target_mode, char_mode;
2356 enum insn_code icode = CODE_FOR_nothing;
2357 int align;
2359 /* If the length can be computed at compile-time, return it. */
2360 len = c_strlen (src, 0);
2361 if (len)
2362 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
2364 /* If the length can be computed at compile-time and is constant
2365 integer, but there are side-effects in src, evaluate
2366 src for side-effects, then return len.
2367 E.g. x = strlen (i++ ? "xfoo" + 1 : "bar");
2368 can be optimized into: i++; x = 3; */
2369 len = c_strlen (src, 1);
2370 if (len && TREE_CODE (len) == INTEGER_CST)
2372 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
2373 return expand_expr (len, target, target_mode, EXPAND_NORMAL);
2376 align = get_pointer_alignment (src, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
2378 /* If SRC is not a pointer type, don't do this operation inline. */
2379 if (align == 0)
2380 return 0;
2382 /* Bail out if we can't compute strlen in the right mode. */
2383 while (insn_mode != VOIDmode)
2385 icode = strlen_optab->handlers[(int) insn_mode].insn_code;
2386 if (icode != CODE_FOR_nothing)
2387 break;
2389 insn_mode = GET_MODE_WIDER_MODE (insn_mode);
2391 if (insn_mode == VOIDmode)
2392 return 0;
2394 /* Make a place to write the result of the instruction. */
2395 result = target;
2396 if (! (result != 0
2397 && GET_CODE (result) == REG
2398 && GET_MODE (result) == insn_mode
2399 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
2400 result = gen_reg_rtx (insn_mode);
2402 /* Make a place to hold the source address. We will not expand
2403 the actual source until we are sure that the expansion will
2404 not fail -- there are trees that cannot be expanded twice. */
2405 src_reg = gen_reg_rtx (Pmode);
2407 /* Mark the beginning of the strlen sequence so we can emit the
2408 source operand later. */
2409 before_strlen = get_last_insn ();
2411 char_rtx = const0_rtx;
2412 char_mode = insn_data[(int) icode].operand[2].mode;
2413 if (! (*insn_data[(int) icode].operand[2].predicate) (char_rtx,
2414 char_mode))
2415 char_rtx = copy_to_mode_reg (char_mode, char_rtx);
2417 pat = GEN_FCN (icode) (result, gen_rtx_MEM (BLKmode, src_reg),
2418 char_rtx, GEN_INT (align));
2419 if (! pat)
2420 return 0;
2421 emit_insn (pat);
2423 /* Now that we are assured of success, expand the source. */
2424 start_sequence ();
2425 pat = memory_address (BLKmode,
2426 expand_expr (src, src_reg, ptr_mode, EXPAND_SUM));
2427 if (pat != src_reg)
2428 emit_move_insn (src_reg, pat);
2429 pat = get_insns ();
2430 end_sequence ();
2432 if (before_strlen)
2433 emit_insn_after (pat, before_strlen);
2434 else
2435 emit_insn_before (pat, get_insns ());
2437 /* Return the value in the proper mode for this function. */
2438 if (GET_MODE (result) == target_mode)
2439 target = result;
2440 else if (target != 0)
2441 convert_move (target, result, 0);
2442 else
2443 target = convert_to_mode (target_mode, result, 0);
2445 return target;
2449 /* Expand a call to the strstr builtin. Return 0 if we failed the
2450 caller should emit a normal call, otherwise try to get the result
2451 in TARGET, if convenient (and in mode MODE if that's convenient). */
2453 static rtx
2454 expand_builtin_strstr (tree arglist, rtx target, enum machine_mode mode)
2456 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
2457 return 0;
2458 else
2460 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
2461 tree fn, tmp;
2462 const char *p1, *p2;
2464 p2 = c_getstr (s2);
2465 if (p2 == NULL)
2466 return 0;
2468 p1 = c_getstr (s1);
2469 if (p1 != NULL)
2471 const char *r = strstr (p1, p2);
2473 if (r == NULL)
2474 return const0_rtx;
2476 /* Return an offset into the constant string argument. */
2477 tmp = fold (build2 (PLUS_EXPR, TREE_TYPE (s1), s1,
2478 fold_convert (TREE_TYPE (s1),
2479 ssize_int (r - p1))));
2480 return expand_expr (tmp, target, mode, EXPAND_NORMAL);
2483 if (p2[0] == '\0')
2484 return expand_expr (s1, target, mode, EXPAND_NORMAL);
2486 if (p2[1] != '\0')
2487 return 0;
2489 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
2490 if (!fn)
2491 return 0;
2493 /* New argument list transforming strstr(s1, s2) to
2494 strchr(s1, s2[0]). */
2495 arglist =
2496 build_tree_list (NULL_TREE, build_int_2 (p2[0], 0));
2497 arglist = tree_cons (NULL_TREE, s1, arglist);
2498 return expand_expr (build_function_call_expr (fn, arglist),
2499 target, mode, EXPAND_NORMAL);
2503 /* Expand a call to the strchr builtin. Return 0 if we failed the
2504 caller should emit a normal call, otherwise try to get the result
2505 in TARGET, if convenient (and in mode MODE if that's convenient). */
2507 static rtx
2508 expand_builtin_strchr (tree arglist, rtx target, enum machine_mode mode)
2510 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2511 return 0;
2512 else
2514 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
2515 const char *p1;
2517 if (TREE_CODE (s2) != INTEGER_CST)
2518 return 0;
2520 p1 = c_getstr (s1);
2521 if (p1 != NULL)
2523 char c;
2524 const char *r;
2525 tree tmp;
2527 if (target_char_cast (s2, &c))
2528 return 0;
2530 r = strchr (p1, c);
2532 if (r == NULL)
2533 return const0_rtx;
2535 /* Return an offset into the constant string argument. */
2536 tmp = fold (build2 (PLUS_EXPR, TREE_TYPE (s1), s1,
2537 fold_convert (TREE_TYPE (s1),
2538 ssize_int (r - p1))));
2539 return expand_expr (tmp, target, mode, EXPAND_NORMAL);
2542 /* FIXME: Should use here strchrM optab so that ports can optimize
2543 this. */
2544 return 0;
2548 /* Expand a call to the strrchr builtin. Return 0 if we failed the
2549 caller should emit a normal call, otherwise try to get the result
2550 in TARGET, if convenient (and in mode MODE if that's convenient). */
2552 static rtx
2553 expand_builtin_strrchr (tree arglist, rtx target, enum machine_mode mode)
2555 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2556 return 0;
2557 else
2559 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
2560 tree fn, tmp;
2561 const char *p1;
2563 if (TREE_CODE (s2) != INTEGER_CST)
2564 return 0;
2566 p1 = c_getstr (s1);
2567 if (p1 != NULL)
2569 char c;
2570 const char *r;
2572 if (target_char_cast (s2, &c))
2573 return 0;
2575 r = strrchr (p1, c);
2577 if (r == NULL)
2578 return const0_rtx;
2580 /* Return an offset into the constant string argument. */
2581 tmp = fold (build2 (PLUS_EXPR, TREE_TYPE (s1), s1,
2582 fold_convert (TREE_TYPE (s1),
2583 ssize_int (r - p1))));
2584 return expand_expr (tmp, target, mode, EXPAND_NORMAL);
2587 if (! integer_zerop (s2))
2588 return 0;
2590 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
2591 if (!fn)
2592 return 0;
2594 /* Transform strrchr(s1, '\0') to strchr(s1, '\0'). */
2595 return expand_expr (build_function_call_expr (fn, arglist),
2596 target, mode, EXPAND_NORMAL);
2600 /* Expand a call to the strpbrk builtin. Return 0 if we failed the
2601 caller should emit a normal call, otherwise try to get the result
2602 in TARGET, if convenient (and in mode MODE if that's convenient). */
2604 static rtx
2605 expand_builtin_strpbrk (tree arglist, rtx target, enum machine_mode mode)
2607 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
2608 return 0;
2609 else
2611 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
2612 tree fn, tmp;
2613 const char *p1, *p2;
2615 p2 = c_getstr (s2);
2616 if (p2 == NULL)
2617 return 0;
2619 p1 = c_getstr (s1);
2620 if (p1 != NULL)
2622 const char *r = strpbrk (p1, p2);
2624 if (r == NULL)
2625 return const0_rtx;
2627 /* Return an offset into the constant string argument. */
2628 tmp = fold (build2 (PLUS_EXPR, TREE_TYPE (s1), s1,
2629 fold_convert (TREE_TYPE (s1),
2630 ssize_int (r - p1))));
2631 return expand_expr (tmp, target, mode, EXPAND_NORMAL);
2634 if (p2[0] == '\0')
2636 /* strpbrk(x, "") == NULL.
2637 Evaluate and ignore the arguments in case they had
2638 side-effects. */
2639 expand_expr (s1, const0_rtx, VOIDmode, EXPAND_NORMAL);
2640 return const0_rtx;
2643 if (p2[1] != '\0')
2644 return 0; /* Really call strpbrk. */
2646 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
2647 if (!fn)
2648 return 0;
2650 /* New argument list transforming strpbrk(s1, s2) to
2651 strchr(s1, s2[0]). */
2652 arglist =
2653 build_tree_list (NULL_TREE, build_int_2 (p2[0], 0));
2654 arglist = tree_cons (NULL_TREE, s1, arglist);
2655 return expand_expr (build_function_call_expr (fn, arglist),
2656 target, mode, EXPAND_NORMAL);
2660 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
2661 bytes from constant string DATA + OFFSET and return it as target
2662 constant. */
2664 static rtx
2665 builtin_memcpy_read_str (void *data, HOST_WIDE_INT offset,
2666 enum machine_mode mode)
2668 const char *str = (const char *) data;
2670 if (offset < 0
2671 || ((unsigned HOST_WIDE_INT) offset + GET_MODE_SIZE (mode)
2672 > strlen (str) + 1))
2673 abort (); /* Attempt to read past the end of constant string. */
2675 return c_readstr (str + offset, mode);
2678 /* Expand a call to the memcpy builtin, with arguments in ARGLIST.
2679 Return 0 if we failed, the caller should emit a normal call,
2680 otherwise try to get the result in TARGET, if convenient (and in
2681 mode MODE if that's convenient). */
2682 static rtx
2683 expand_builtin_memcpy (tree arglist, rtx target, enum machine_mode mode)
2685 if (!validate_arglist (arglist,
2686 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2687 return 0;
2688 else
2690 tree dest = TREE_VALUE (arglist);
2691 tree src = TREE_VALUE (TREE_CHAIN (arglist));
2692 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
2693 const char *src_str;
2694 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
2695 unsigned int dest_align
2696 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
2697 rtx dest_mem, src_mem, dest_addr, len_rtx;
2699 /* If DEST is not a pointer type, call the normal function. */
2700 if (dest_align == 0)
2701 return 0;
2703 /* If the LEN parameter is zero, return DEST. */
2704 if (integer_zerop (len))
2706 /* Evaluate and ignore SRC in case it has side-effects. */
2707 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
2708 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2711 /* If SRC and DEST are the same (and not volatile), return DEST. */
2712 if (operand_equal_p (src, dest, 0))
2714 /* Evaluate and ignore LEN in case it has side-effects. */
2715 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
2716 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2719 /* If either SRC is not a pointer type, don't do this
2720 operation in-line. */
2721 if (src_align == 0)
2722 return 0;
2724 dest_mem = get_memory_rtx (dest);
2725 set_mem_align (dest_mem, dest_align);
2726 len_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
2727 src_str = c_getstr (src);
2729 /* If SRC is a string constant and block move would be done
2730 by pieces, we can avoid loading the string from memory
2731 and only stored the computed constants. */
2732 if (src_str
2733 && GET_CODE (len_rtx) == CONST_INT
2734 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
2735 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
2736 (void *) src_str, dest_align))
2738 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
2739 builtin_memcpy_read_str,
2740 (void *) src_str, dest_align, 0);
2741 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
2742 dest_mem = convert_memory_address (ptr_mode, dest_mem);
2743 return dest_mem;
2746 src_mem = get_memory_rtx (src);
2747 set_mem_align (src_mem, src_align);
2749 /* Copy word part most expediently. */
2750 dest_addr = emit_block_move (dest_mem, src_mem, len_rtx,
2751 BLOCK_OP_NORMAL);
2753 if (dest_addr == 0)
2755 dest_addr = force_operand (XEXP (dest_mem, 0), NULL_RTX);
2756 dest_addr = convert_memory_address (ptr_mode, dest_addr);
2758 return dest_addr;
2762 /* Expand a call to the mempcpy builtin, with arguments in ARGLIST.
2763 Return 0 if we failed the caller should emit a normal call,
2764 otherwise try to get the result in TARGET, if convenient (and in
2765 mode MODE if that's convenient). If ENDP is 0 return the
2766 destination pointer, if ENDP is 1 return the end pointer ala
2767 mempcpy, and if ENDP is 2 return the end pointer minus one ala
2768 stpcpy. */
2770 static rtx
2771 expand_builtin_mempcpy (tree arglist, rtx target, enum machine_mode mode,
2772 int endp)
2774 if (!validate_arglist (arglist,
2775 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2776 return 0;
2777 /* If return value is ignored, transform mempcpy into memcpy. */
2778 else if (target == const0_rtx)
2780 tree fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
2782 if (!fn)
2783 return 0;
2785 return expand_expr (build_function_call_expr (fn, arglist),
2786 target, mode, EXPAND_NORMAL);
2788 else
2790 tree dest = TREE_VALUE (arglist);
2791 tree src = TREE_VALUE (TREE_CHAIN (arglist));
2792 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
2793 const char *src_str;
2794 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
2795 unsigned int dest_align
2796 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
2797 rtx dest_mem, src_mem, len_rtx;
2799 /* If DEST is not a pointer type, call the normal function. */
2800 if (dest_align == 0)
2801 return 0;
2803 /* If SRC and DEST are the same (and not volatile), do nothing. */
2804 if (operand_equal_p (src, dest, 0))
2806 tree expr;
2808 if (endp == 0)
2810 /* Evaluate and ignore LEN in case it has side-effects. */
2811 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
2812 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2815 if (endp == 2)
2816 len = fold (build2 (MINUS_EXPR, TREE_TYPE (len), len,
2817 integer_one_node));
2818 len = fold_convert (TREE_TYPE (dest), len);
2819 expr = fold (build2 (PLUS_EXPR, TREE_TYPE (dest), dest, len));
2820 return expand_expr (expr, target, mode, EXPAND_NORMAL);
2823 /* If LEN is not constant, call the normal function. */
2824 if (! host_integerp (len, 1))
2825 return 0;
2827 /* If the LEN parameter is zero, return DEST. */
2828 if (tree_low_cst (len, 1) == 0)
2830 /* Evaluate and ignore SRC in case it has side-effects. */
2831 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
2832 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2835 /* If either SRC is not a pointer type, don't do this
2836 operation in-line. */
2837 if (src_align == 0)
2838 return 0;
2840 len_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
2841 src_str = c_getstr (src);
2843 /* If SRC is a string constant and block move would be done
2844 by pieces, we can avoid loading the string from memory
2845 and only stored the computed constants. */
2846 if (src_str
2847 && GET_CODE (len_rtx) == CONST_INT
2848 && (unsigned HOST_WIDE_INT) INTVAL (len_rtx) <= strlen (src_str) + 1
2849 && can_store_by_pieces (INTVAL (len_rtx), builtin_memcpy_read_str,
2850 (void *) src_str, dest_align))
2852 dest_mem = get_memory_rtx (dest);
2853 set_mem_align (dest_mem, dest_align);
2854 dest_mem = store_by_pieces (dest_mem, INTVAL (len_rtx),
2855 builtin_memcpy_read_str,
2856 (void *) src_str, dest_align, endp);
2857 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
2858 dest_mem = convert_memory_address (ptr_mode, dest_mem);
2859 return dest_mem;
2862 if (GET_CODE (len_rtx) == CONST_INT
2863 && can_move_by_pieces (INTVAL (len_rtx),
2864 MIN (dest_align, src_align)))
2866 dest_mem = get_memory_rtx (dest);
2867 set_mem_align (dest_mem, dest_align);
2868 src_mem = get_memory_rtx (src);
2869 set_mem_align (src_mem, src_align);
2870 dest_mem = move_by_pieces (dest_mem, src_mem, INTVAL (len_rtx),
2871 MIN (dest_align, src_align), endp);
2872 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
2873 dest_mem = convert_memory_address (ptr_mode, dest_mem);
2874 return dest_mem;
2877 return 0;
2881 /* Expand expression EXP, which is a call to the memmove builtin. Return 0
2882 if we failed the caller should emit a normal call. */
2884 static rtx
2885 expand_builtin_memmove (tree arglist, rtx target, enum machine_mode mode)
2887 if (!validate_arglist (arglist,
2888 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2889 return 0;
2890 else
2892 tree dest = TREE_VALUE (arglist);
2893 tree src = TREE_VALUE (TREE_CHAIN (arglist));
2894 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
2896 unsigned int src_align = get_pointer_alignment (src, BIGGEST_ALIGNMENT);
2897 unsigned int dest_align
2898 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
2900 /* If DEST is not a pointer type, call the normal function. */
2901 if (dest_align == 0)
2902 return 0;
2904 /* If the LEN parameter is zero, return DEST. */
2905 if (integer_zerop (len))
2907 /* Evaluate and ignore SRC in case it has side-effects. */
2908 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
2909 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2912 /* If SRC and DEST are the same (and not volatile), return DEST. */
2913 if (operand_equal_p (src, dest, 0))
2915 /* Evaluate and ignore LEN in case it has side-effects. */
2916 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
2917 return expand_expr (dest, target, mode, EXPAND_NORMAL);
2920 /* If either SRC is not a pointer type, don't do this
2921 operation in-line. */
2922 if (src_align == 0)
2923 return 0;
2925 /* If src is categorized for a readonly section we can use
2926 normal memcpy. */
2927 if (readonly_data_expr (src))
2929 tree const fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
2930 if (!fn)
2931 return 0;
2932 return expand_expr (build_function_call_expr (fn, arglist),
2933 target, mode, EXPAND_NORMAL);
2936 /* Otherwise, call the normal function. */
2937 return 0;
2941 /* Expand expression EXP, which is a call to the bcopy builtin. Return 0
2942 if we failed the caller should emit a normal call. */
2944 static rtx
2945 expand_builtin_bcopy (tree arglist)
2947 tree src, dest, size, newarglist;
2949 if (!validate_arglist (arglist,
2950 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
2951 return NULL_RTX;
2953 src = TREE_VALUE (arglist);
2954 dest = TREE_VALUE (TREE_CHAIN (arglist));
2955 size = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
2957 /* New argument list transforming bcopy(ptr x, ptr y, int z) to
2958 memmove(ptr y, ptr x, size_t z). This is done this way
2959 so that if it isn't expanded inline, we fallback to
2960 calling bcopy instead of memmove. */
2962 newarglist = build_tree_list (NULL_TREE, fold_convert (sizetype, size));
2963 newarglist = tree_cons (NULL_TREE, src, newarglist);
2964 newarglist = tree_cons (NULL_TREE, dest, newarglist);
2966 return expand_builtin_memmove (newarglist, const0_rtx, VOIDmode);
2969 /* Expand expression EXP, which is a call to the strcpy builtin. Return 0
2970 if we failed the caller should emit a normal call, otherwise try to get
2971 the result in TARGET, if convenient (and in mode MODE if that's
2972 convenient). */
2974 static rtx
2975 expand_builtin_strcpy (tree arglist, rtx target, enum machine_mode mode)
2977 tree fn, len, src, dst;
2979 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
2980 return 0;
2982 src = TREE_VALUE (TREE_CHAIN (arglist));
2983 dst = TREE_VALUE (arglist);
2985 /* If SRC and DST are equal (and not volatile), return DST. */
2986 if (operand_equal_p (src, dst, 0))
2987 return expand_expr (dst, target, mode, EXPAND_NORMAL);
2989 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
2990 if (!fn)
2991 return 0;
2993 len = c_strlen (src, 1);
2994 if (len == 0 || TREE_SIDE_EFFECTS (len))
2995 return 0;
2997 len = size_binop (PLUS_EXPR, len, ssize_int (1));
2998 arglist = build_tree_list (NULL_TREE, len);
2999 arglist = tree_cons (NULL_TREE, src, arglist);
3000 arglist = tree_cons (NULL_TREE, dst, arglist);
3001 return expand_expr (build_function_call_expr (fn, arglist),
3002 target, mode, EXPAND_NORMAL);
3005 /* Expand a call to the stpcpy builtin, with arguments in ARGLIST.
3006 Return 0 if we failed the caller should emit a normal call,
3007 otherwise try to get the result in TARGET, if convenient (and in
3008 mode MODE if that's convenient). */
3010 static rtx
3011 expand_builtin_stpcpy (tree arglist, rtx target, enum machine_mode mode)
3013 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3014 return 0;
3015 else
3017 tree dst, src, len;
3019 /* If return value is ignored, transform stpcpy into strcpy. */
3020 if (target == const0_rtx)
3022 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
3023 if (!fn)
3024 return 0;
3026 return expand_expr (build_function_call_expr (fn, arglist),
3027 target, mode, EXPAND_NORMAL);
3030 /* Ensure we get an actual string whose length can be evaluated at
3031 compile-time, not an expression containing a string. This is
3032 because the latter will potentially produce pessimized code
3033 when used to produce the return value. */
3034 src = TREE_VALUE (TREE_CHAIN (arglist));
3035 if (! c_getstr (src) || ! (len = c_strlen (src, 0)))
3036 return 0;
3038 dst = TREE_VALUE (arglist);
3039 len = fold (size_binop (PLUS_EXPR, len, ssize_int (1)));
3040 arglist = build_tree_list (NULL_TREE, len);
3041 arglist = tree_cons (NULL_TREE, src, arglist);
3042 arglist = tree_cons (NULL_TREE, dst, arglist);
3043 return expand_builtin_mempcpy (arglist, target, mode, /*endp=*/2);
3047 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3048 bytes from constant string DATA + OFFSET and return it as target
3049 constant. */
3051 static rtx
3052 builtin_strncpy_read_str (void *data, HOST_WIDE_INT offset,
3053 enum machine_mode mode)
3055 const char *str = (const char *) data;
3057 if ((unsigned HOST_WIDE_INT) offset > strlen (str))
3058 return const0_rtx;
3060 return c_readstr (str + offset, mode);
3063 /* Expand expression EXP, which is a call to the strncpy builtin. Return 0
3064 if we failed the caller should emit a normal call. */
3066 static rtx
3067 expand_builtin_strncpy (tree arglist, rtx target, enum machine_mode mode)
3069 if (!validate_arglist (arglist,
3070 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3071 return 0;
3072 else
3074 tree slen = c_strlen (TREE_VALUE (TREE_CHAIN (arglist)), 1);
3075 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
3076 tree fn;
3078 /* We must be passed a constant len parameter. */
3079 if (TREE_CODE (len) != INTEGER_CST)
3080 return 0;
3082 /* If the len parameter is zero, return the dst parameter. */
3083 if (integer_zerop (len))
3085 /* Evaluate and ignore the src argument in case it has
3086 side-effects. */
3087 expand_expr (TREE_VALUE (TREE_CHAIN (arglist)), const0_rtx,
3088 VOIDmode, EXPAND_NORMAL);
3089 /* Return the dst parameter. */
3090 return expand_expr (TREE_VALUE (arglist), target, mode,
3091 EXPAND_NORMAL);
3094 /* Now, we must be passed a constant src ptr parameter. */
3095 if (slen == 0 || TREE_CODE (slen) != INTEGER_CST)
3096 return 0;
3098 slen = size_binop (PLUS_EXPR, slen, ssize_int (1));
3100 /* We're required to pad with trailing zeros if the requested
3101 len is greater than strlen(s2)+1. In that case try to
3102 use store_by_pieces, if it fails, punt. */
3103 if (tree_int_cst_lt (slen, len))
3105 tree dest = TREE_VALUE (arglist);
3106 unsigned int dest_align
3107 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3108 const char *p = c_getstr (TREE_VALUE (TREE_CHAIN (arglist)));
3109 rtx dest_mem;
3111 if (!p || dest_align == 0 || !host_integerp (len, 1)
3112 || !can_store_by_pieces (tree_low_cst (len, 1),
3113 builtin_strncpy_read_str,
3114 (void *) p, dest_align))
3115 return 0;
3117 dest_mem = get_memory_rtx (dest);
3118 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3119 builtin_strncpy_read_str,
3120 (void *) p, dest_align, 0);
3121 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3122 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3123 return dest_mem;
3126 /* OK transform into builtin memcpy. */
3127 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
3128 if (!fn)
3129 return 0;
3130 return expand_expr (build_function_call_expr (fn, arglist),
3131 target, mode, EXPAND_NORMAL);
3135 /* Callback routine for store_by_pieces. Read GET_MODE_BITSIZE (MODE)
3136 bytes from constant string DATA + OFFSET and return it as target
3137 constant. */
3139 static rtx
3140 builtin_memset_read_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3141 enum machine_mode mode)
3143 const char *c = (const char *) data;
3144 char *p = alloca (GET_MODE_SIZE (mode));
3146 memset (p, *c, GET_MODE_SIZE (mode));
3148 return c_readstr (p, mode);
3151 /* Callback routine for store_by_pieces. Return the RTL of a register
3152 containing GET_MODE_SIZE (MODE) consecutive copies of the unsigned
3153 char value given in the RTL register data. For example, if mode is
3154 4 bytes wide, return the RTL for 0x01010101*data. */
3156 static rtx
3157 builtin_memset_gen_str (void *data, HOST_WIDE_INT offset ATTRIBUTE_UNUSED,
3158 enum machine_mode mode)
3160 rtx target, coeff;
3161 size_t size;
3162 char *p;
3164 size = GET_MODE_SIZE (mode);
3165 if (size == 1)
3166 return (rtx) data;
3168 p = alloca (size);
3169 memset (p, 1, size);
3170 coeff = c_readstr (p, mode);
3172 target = convert_to_mode (mode, (rtx) data, 1);
3173 target = expand_mult (mode, target, coeff, NULL_RTX, 1);
3174 return force_reg (mode, target);
3177 /* Expand expression EXP, which is a call to the memset builtin. Return 0
3178 if we failed the caller should emit a normal call, otherwise try to get
3179 the result in TARGET, if convenient (and in mode MODE if that's
3180 convenient). */
3182 static rtx
3183 expand_builtin_memset (tree arglist, rtx target, enum machine_mode mode)
3185 if (!validate_arglist (arglist,
3186 POINTER_TYPE, INTEGER_TYPE, INTEGER_TYPE, VOID_TYPE))
3187 return 0;
3188 else
3190 tree dest = TREE_VALUE (arglist);
3191 tree val = TREE_VALUE (TREE_CHAIN (arglist));
3192 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
3193 char c;
3195 unsigned int dest_align
3196 = get_pointer_alignment (dest, BIGGEST_ALIGNMENT);
3197 rtx dest_mem, dest_addr, len_rtx;
3199 /* If DEST is not a pointer type, don't do this
3200 operation in-line. */
3201 if (dest_align == 0)
3202 return 0;
3204 /* If the LEN parameter is zero, return DEST. */
3205 if (integer_zerop (len))
3207 /* Evaluate and ignore VAL in case it has side-effects. */
3208 expand_expr (val, const0_rtx, VOIDmode, EXPAND_NORMAL);
3209 return expand_expr (dest, target, mode, EXPAND_NORMAL);
3212 if (TREE_CODE (val) != INTEGER_CST)
3214 rtx val_rtx;
3216 if (!host_integerp (len, 1))
3217 return 0;
3219 if (optimize_size && tree_low_cst (len, 1) > 1)
3220 return 0;
3222 /* Assume that we can memset by pieces if we can store the
3223 * the coefficients by pieces (in the required modes).
3224 * We can't pass builtin_memset_gen_str as that emits RTL. */
3225 c = 1;
3226 if (!can_store_by_pieces (tree_low_cst (len, 1),
3227 builtin_memset_read_str,
3228 &c, dest_align))
3229 return 0;
3231 val = fold (build1 (CONVERT_EXPR, unsigned_char_type_node, val));
3232 val_rtx = expand_expr (val, NULL_RTX, VOIDmode, 0);
3233 val_rtx = force_reg (TYPE_MODE (unsigned_char_type_node),
3234 val_rtx);
3235 dest_mem = get_memory_rtx (dest);
3236 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3237 builtin_memset_gen_str,
3238 val_rtx, dest_align, 0);
3239 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3240 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3241 return dest_mem;
3244 if (target_char_cast (val, &c))
3245 return 0;
3247 if (c)
3249 if (!host_integerp (len, 1))
3250 return 0;
3251 if (!can_store_by_pieces (tree_low_cst (len, 1),
3252 builtin_memset_read_str, &c,
3253 dest_align))
3254 return 0;
3256 dest_mem = get_memory_rtx (dest);
3257 store_by_pieces (dest_mem, tree_low_cst (len, 1),
3258 builtin_memset_read_str,
3259 &c, dest_align, 0);
3260 dest_mem = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3261 dest_mem = convert_memory_address (ptr_mode, dest_mem);
3262 return dest_mem;
3265 len_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
3267 dest_mem = get_memory_rtx (dest);
3268 set_mem_align (dest_mem, dest_align);
3269 dest_addr = clear_storage (dest_mem, len_rtx);
3271 if (dest_addr == 0)
3273 dest_addr = force_operand (XEXP (dest_mem, 0), NULL_RTX);
3274 dest_addr = convert_memory_address (ptr_mode, dest_addr);
3277 return dest_addr;
3281 /* Expand expression EXP, which is a call to the bzero builtin. Return 0
3282 if we failed the caller should emit a normal call. */
3284 static rtx
3285 expand_builtin_bzero (tree arglist)
3287 tree dest, size, newarglist;
3289 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3290 return NULL_RTX;
3292 dest = TREE_VALUE (arglist);
3293 size = TREE_VALUE (TREE_CHAIN (arglist));
3295 /* New argument list transforming bzero(ptr x, int y) to
3296 memset(ptr x, int 0, size_t y). This is done this way
3297 so that if it isn't expanded inline, we fallback to
3298 calling bzero instead of memset. */
3300 newarglist = build_tree_list (NULL_TREE, fold_convert (sizetype, size));
3301 newarglist = tree_cons (NULL_TREE, integer_zero_node, newarglist);
3302 newarglist = tree_cons (NULL_TREE, dest, newarglist);
3304 return expand_builtin_memset (newarglist, const0_rtx, VOIDmode);
3307 /* Expand expression EXP, which is a call to the memcmp built-in function.
3308 ARGLIST is the argument list for this call. Return 0 if we failed and the
3309 caller should emit a normal call, otherwise try to get the result in
3310 TARGET, if convenient (and in mode MODE, if that's convenient). */
3312 static rtx
3313 expand_builtin_memcmp (tree exp ATTRIBUTE_UNUSED, tree arglist, rtx target,
3314 enum machine_mode mode)
3316 tree arg1, arg2, len;
3317 const char *p1, *p2;
3319 if (!validate_arglist (arglist,
3320 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3321 return 0;
3323 arg1 = TREE_VALUE (arglist);
3324 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
3325 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
3327 /* If the len parameter is zero, return zero. */
3328 if (integer_zerop (len))
3330 /* Evaluate and ignore arg1 and arg2 in case they have
3331 side-effects. */
3332 expand_expr (arg1, const0_rtx, VOIDmode, EXPAND_NORMAL);
3333 expand_expr (arg2, const0_rtx, VOIDmode, EXPAND_NORMAL);
3334 return const0_rtx;
3337 /* If both arguments are equal (and not volatile), return zero. */
3338 if (operand_equal_p (arg1, arg2, 0))
3340 /* Evaluate and ignore len in case it has side-effects. */
3341 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
3342 return const0_rtx;
3345 p1 = c_getstr (arg1);
3346 p2 = c_getstr (arg2);
3348 /* If all arguments are constant, and the value of len is not greater
3349 than the lengths of arg1 and arg2, evaluate at compile-time. */
3350 if (host_integerp (len, 1) && p1 && p2
3351 && compare_tree_int (len, strlen (p1) + 1) <= 0
3352 && compare_tree_int (len, strlen (p2) + 1) <= 0)
3354 const int r = memcmp (p1, p2, tree_low_cst (len, 1));
3356 return (r < 0 ? constm1_rtx : (r > 0 ? const1_rtx : const0_rtx));
3359 /* If len parameter is one, return an expression corresponding to
3360 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
3361 if (integer_onep (len))
3363 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
3364 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
3365 tree ind1 =
3366 fold (build1 (CONVERT_EXPR, integer_type_node,
3367 build1 (INDIRECT_REF, cst_uchar_node,
3368 fold_convert (cst_uchar_ptr_node, arg1))));
3369 tree ind2 =
3370 fold (build1 (CONVERT_EXPR, integer_type_node,
3371 build1 (INDIRECT_REF, cst_uchar_node,
3372 fold_convert (cst_uchar_ptr_node, arg2))));
3373 tree result = fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
3374 return expand_expr (result, target, mode, EXPAND_NORMAL);
3377 #if defined HAVE_cmpmemsi || defined HAVE_cmpstrsi
3379 rtx arg1_rtx, arg2_rtx, arg3_rtx;
3380 rtx result;
3381 rtx insn;
3383 int arg1_align
3384 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3385 int arg2_align
3386 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3387 enum machine_mode insn_mode;
3389 #ifdef HAVE_cmpmemsi
3390 if (HAVE_cmpmemsi)
3391 insn_mode = insn_data[(int) CODE_FOR_cmpmemsi].operand[0].mode;
3392 else
3393 #endif
3394 #ifdef HAVE_cmpstrsi
3395 if (HAVE_cmpstrsi)
3396 insn_mode = insn_data[(int) CODE_FOR_cmpstrsi].operand[0].mode;
3397 else
3398 #endif
3399 return 0;
3401 /* If we don't have POINTER_TYPE, call the function. */
3402 if (arg1_align == 0 || arg2_align == 0)
3403 return 0;
3405 /* Make a place to write the result of the instruction. */
3406 result = target;
3407 if (! (result != 0
3408 && GET_CODE (result) == REG && GET_MODE (result) == insn_mode
3409 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
3410 result = gen_reg_rtx (insn_mode);
3412 arg1_rtx = get_memory_rtx (arg1);
3413 arg2_rtx = get_memory_rtx (arg2);
3414 arg3_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
3415 #ifdef HAVE_cmpmemsi
3416 if (HAVE_cmpmemsi)
3417 insn = gen_cmpmemsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
3418 GEN_INT (MIN (arg1_align, arg2_align)));
3419 else
3420 #endif
3421 #ifdef HAVE_cmpstrsi
3422 if (HAVE_cmpstrsi)
3423 insn = gen_cmpstrsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
3424 GEN_INT (MIN (arg1_align, arg2_align)));
3425 else
3426 #endif
3427 abort ();
3429 if (insn)
3430 emit_insn (insn);
3431 else
3432 emit_library_call_value (memcmp_libfunc, result, LCT_PURE_MAKE_BLOCK,
3433 TYPE_MODE (integer_type_node), 3,
3434 XEXP (arg1_rtx, 0), Pmode,
3435 XEXP (arg2_rtx, 0), Pmode,
3436 convert_to_mode (TYPE_MODE (sizetype), arg3_rtx,
3437 TYPE_UNSIGNED (sizetype)),
3438 TYPE_MODE (sizetype));
3440 /* Return the value in the proper mode for this function. */
3441 mode = TYPE_MODE (TREE_TYPE (exp));
3442 if (GET_MODE (result) == mode)
3443 return result;
3444 else if (target != 0)
3446 convert_move (target, result, 0);
3447 return target;
3449 else
3450 return convert_to_mode (mode, result, 0);
3452 #endif
3454 return 0;
3457 /* Expand expression EXP, which is a call to the strcmp builtin. Return 0
3458 if we failed the caller should emit a normal call, otherwise try to get
3459 the result in TARGET, if convenient. */
3461 static rtx
3462 expand_builtin_strcmp (tree exp, rtx target, enum machine_mode mode)
3464 tree arglist = TREE_OPERAND (exp, 1);
3465 tree arg1, arg2;
3466 const char *p1, *p2;
3468 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3469 return 0;
3471 arg1 = TREE_VALUE (arglist);
3472 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
3474 /* If both arguments are equal (and not volatile), return zero. */
3475 if (operand_equal_p (arg1, arg2, 0))
3476 return const0_rtx;
3478 p1 = c_getstr (arg1);
3479 p2 = c_getstr (arg2);
3481 if (p1 && p2)
3483 const int i = strcmp (p1, p2);
3484 return (i < 0 ? constm1_rtx : (i > 0 ? const1_rtx : const0_rtx));
3487 /* If either arg is "", return an expression corresponding to
3488 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
3489 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
3491 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
3492 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
3493 tree ind1 =
3494 fold (build1 (CONVERT_EXPR, integer_type_node,
3495 build1 (INDIRECT_REF, cst_uchar_node,
3496 fold_convert (cst_uchar_ptr_node, arg1))));
3497 tree ind2 =
3498 fold (build1 (CONVERT_EXPR, integer_type_node,
3499 build1 (INDIRECT_REF, cst_uchar_node,
3500 fold_convert (cst_uchar_ptr_node, arg2))));
3501 tree result = fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
3502 return expand_expr (result, target, mode, EXPAND_NORMAL);
3505 #ifdef HAVE_cmpstrsi
3506 if (HAVE_cmpstrsi)
3508 tree len, len1, len2;
3509 rtx arg1_rtx, arg2_rtx, arg3_rtx;
3510 rtx result, insn;
3511 tree fndecl;
3513 int arg1_align
3514 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3515 int arg2_align
3516 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3517 enum machine_mode insn_mode
3518 = insn_data[(int) CODE_FOR_cmpstrsi].operand[0].mode;
3520 len1 = c_strlen (arg1, 1);
3521 len2 = c_strlen (arg2, 1);
3523 if (len1)
3524 len1 = size_binop (PLUS_EXPR, ssize_int (1), len1);
3525 if (len2)
3526 len2 = size_binop (PLUS_EXPR, ssize_int (1), len2);
3528 /* If we don't have a constant length for the first, use the length
3529 of the second, if we know it. We don't require a constant for
3530 this case; some cost analysis could be done if both are available
3531 but neither is constant. For now, assume they're equally cheap,
3532 unless one has side effects. If both strings have constant lengths,
3533 use the smaller. */
3535 if (!len1)
3536 len = len2;
3537 else if (!len2)
3538 len = len1;
3539 else if (TREE_SIDE_EFFECTS (len1))
3540 len = len2;
3541 else if (TREE_SIDE_EFFECTS (len2))
3542 len = len1;
3543 else if (TREE_CODE (len1) != INTEGER_CST)
3544 len = len2;
3545 else if (TREE_CODE (len2) != INTEGER_CST)
3546 len = len1;
3547 else if (tree_int_cst_lt (len1, len2))
3548 len = len1;
3549 else
3550 len = len2;
3552 /* If both arguments have side effects, we cannot optimize. */
3553 if (!len || TREE_SIDE_EFFECTS (len))
3554 return 0;
3556 /* If we don't have POINTER_TYPE, call the function. */
3557 if (arg1_align == 0 || arg2_align == 0)
3558 return 0;
3560 /* Make a place to write the result of the instruction. */
3561 result = target;
3562 if (! (result != 0
3563 && GET_CODE (result) == REG && GET_MODE (result) == insn_mode
3564 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
3565 result = gen_reg_rtx (insn_mode);
3567 /* Stabilize the arguments in case gen_cmpstrsi fails. */
3568 arg1 = builtin_save_expr (arg1);
3569 arg2 = builtin_save_expr (arg2);
3571 arg1_rtx = get_memory_rtx (arg1);
3572 arg2_rtx = get_memory_rtx (arg2);
3573 arg3_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
3574 insn = gen_cmpstrsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
3575 GEN_INT (MIN (arg1_align, arg2_align)));
3576 if (insn)
3578 emit_insn (insn);
3580 /* Return the value in the proper mode for this function. */
3581 mode = TYPE_MODE (TREE_TYPE (exp));
3582 if (GET_MODE (result) == mode)
3583 return result;
3584 if (target == 0)
3585 return convert_to_mode (mode, result, 0);
3586 convert_move (target, result, 0);
3587 return target;
3590 /* Expand the library call ourselves using a stabilized argument
3591 list to avoid re-evaluating the function's arguments twice. */
3592 arglist = build_tree_list (NULL_TREE, arg2);
3593 arglist = tree_cons (NULL_TREE, arg1, arglist);
3594 fndecl = get_callee_fndecl (exp);
3595 exp = build_function_call_expr (fndecl, arglist);
3596 return expand_call (exp, target, target == const0_rtx);
3598 #endif
3599 return 0;
3602 /* Expand expression EXP, which is a call to the strncmp builtin. Return 0
3603 if we failed the caller should emit a normal call, otherwise try to get
3604 the result in TARGET, if convenient. */
3606 static rtx
3607 expand_builtin_strncmp (tree exp, rtx target, enum machine_mode mode)
3609 tree arglist = TREE_OPERAND (exp, 1);
3610 tree arg1, arg2, arg3;
3611 const char *p1, *p2;
3613 if (!validate_arglist (arglist,
3614 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3615 return 0;
3617 arg1 = TREE_VALUE (arglist);
3618 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
3619 arg3 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
3621 /* If the len parameter is zero, return zero. */
3622 if (integer_zerop (arg3))
3624 /* Evaluate and ignore arg1 and arg2 in case they have
3625 side-effects. */
3626 expand_expr (arg1, const0_rtx, VOIDmode, EXPAND_NORMAL);
3627 expand_expr (arg2, const0_rtx, VOIDmode, EXPAND_NORMAL);
3628 return const0_rtx;
3631 /* If arg1 and arg2 are equal (and not volatile), return zero. */
3632 if (operand_equal_p (arg1, arg2, 0))
3634 /* Evaluate and ignore arg3 in case it has side-effects. */
3635 expand_expr (arg3, const0_rtx, VOIDmode, EXPAND_NORMAL);
3636 return const0_rtx;
3639 p1 = c_getstr (arg1);
3640 p2 = c_getstr (arg2);
3642 /* If all arguments are constant, evaluate at compile-time. */
3643 if (host_integerp (arg3, 1) && p1 && p2)
3645 const int r = strncmp (p1, p2, tree_low_cst (arg3, 1));
3646 return (r < 0 ? constm1_rtx : (r > 0 ? const1_rtx : const0_rtx));
3649 /* If len == 1 or (either string parameter is "" and (len >= 1)),
3650 return (*(const u_char*)arg1 - *(const u_char*)arg2). */
3651 if (host_integerp (arg3, 1)
3652 && (tree_low_cst (arg3, 1) == 1
3653 || (tree_low_cst (arg3, 1) > 1
3654 && ((p1 && *p1 == '\0') || (p2 && *p2 == '\0')))))
3656 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
3657 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
3658 tree ind1 =
3659 fold (build1 (CONVERT_EXPR, integer_type_node,
3660 build1 (INDIRECT_REF, cst_uchar_node,
3661 fold_convert (cst_uchar_ptr_node, arg1))));
3662 tree ind2 =
3663 fold (build1 (CONVERT_EXPR, integer_type_node,
3664 build1 (INDIRECT_REF, cst_uchar_node,
3665 fold_convert (cst_uchar_ptr_node, arg2))));
3666 tree result = fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
3667 return expand_expr (result, target, mode, EXPAND_NORMAL);
3670 /* If c_strlen can determine an expression for one of the string
3671 lengths, and it doesn't have side effects, then emit cmpstrsi
3672 using length MIN(strlen(string)+1, arg3). */
3673 #ifdef HAVE_cmpstrsi
3674 if (HAVE_cmpstrsi)
3676 tree len, len1, len2;
3677 rtx arg1_rtx, arg2_rtx, arg3_rtx;
3678 rtx result, insn;
3679 tree fndecl;
3681 int arg1_align
3682 = get_pointer_alignment (arg1, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3683 int arg2_align
3684 = get_pointer_alignment (arg2, BIGGEST_ALIGNMENT) / BITS_PER_UNIT;
3685 enum machine_mode insn_mode
3686 = insn_data[(int) CODE_FOR_cmpstrsi].operand[0].mode;
3688 len1 = c_strlen (arg1, 1);
3689 len2 = c_strlen (arg2, 1);
3691 if (len1)
3692 len1 = size_binop (PLUS_EXPR, ssize_int (1), len1);
3693 if (len2)
3694 len2 = size_binop (PLUS_EXPR, ssize_int (1), len2);
3696 /* If we don't have a constant length for the first, use the length
3697 of the second, if we know it. We don't require a constant for
3698 this case; some cost analysis could be done if both are available
3699 but neither is constant. For now, assume they're equally cheap,
3700 unless one has side effects. If both strings have constant lengths,
3701 use the smaller. */
3703 if (!len1)
3704 len = len2;
3705 else if (!len2)
3706 len = len1;
3707 else if (TREE_SIDE_EFFECTS (len1))
3708 len = len2;
3709 else if (TREE_SIDE_EFFECTS (len2))
3710 len = len1;
3711 else if (TREE_CODE (len1) != INTEGER_CST)
3712 len = len2;
3713 else if (TREE_CODE (len2) != INTEGER_CST)
3714 len = len1;
3715 else if (tree_int_cst_lt (len1, len2))
3716 len = len1;
3717 else
3718 len = len2;
3720 /* If both arguments have side effects, we cannot optimize. */
3721 if (!len || TREE_SIDE_EFFECTS (len))
3722 return 0;
3724 /* The actual new length parameter is MIN(len,arg3). */
3725 len = fold (build2 (MIN_EXPR, TREE_TYPE (len), len, arg3));
3727 /* If we don't have POINTER_TYPE, call the function. */
3728 if (arg1_align == 0 || arg2_align == 0)
3729 return 0;
3731 /* Make a place to write the result of the instruction. */
3732 result = target;
3733 if (! (result != 0
3734 && GET_CODE (result) == REG && GET_MODE (result) == insn_mode
3735 && REGNO (result) >= FIRST_PSEUDO_REGISTER))
3736 result = gen_reg_rtx (insn_mode);
3738 /* Stabilize the arguments in case gen_cmpstrsi fails. */
3739 arg1 = builtin_save_expr (arg1);
3740 arg2 = builtin_save_expr (arg2);
3741 len = builtin_save_expr (len);
3743 arg1_rtx = get_memory_rtx (arg1);
3744 arg2_rtx = get_memory_rtx (arg2);
3745 arg3_rtx = expand_expr (len, NULL_RTX, VOIDmode, 0);
3746 insn = gen_cmpstrsi (result, arg1_rtx, arg2_rtx, arg3_rtx,
3747 GEN_INT (MIN (arg1_align, arg2_align)));
3748 if (insn)
3750 emit_insn (insn);
3752 /* Return the value in the proper mode for this function. */
3753 mode = TYPE_MODE (TREE_TYPE (exp));
3754 if (GET_MODE (result) == mode)
3755 return result;
3756 if (target == 0)
3757 return convert_to_mode (mode, result, 0);
3758 convert_move (target, result, 0);
3759 return target;
3762 /* Expand the library call ourselves using a stabilized argument
3763 list to avoid re-evaluating the function's arguments twice. */
3764 arglist = build_tree_list (NULL_TREE, len);
3765 arglist = tree_cons (NULL_TREE, arg2, arglist);
3766 arglist = tree_cons (NULL_TREE, arg1, arglist);
3767 fndecl = get_callee_fndecl (exp);
3768 exp = build_function_call_expr (fndecl, arglist);
3769 return expand_call (exp, target, target == const0_rtx);
3771 #endif
3772 return 0;
3775 /* Expand expression EXP, which is a call to the strcat builtin.
3776 Return 0 if we failed the caller should emit a normal call,
3777 otherwise try to get the result in TARGET, if convenient. */
3779 static rtx
3780 expand_builtin_strcat (tree arglist, rtx target, enum machine_mode mode)
3782 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3783 return 0;
3784 else
3786 tree dst = TREE_VALUE (arglist),
3787 src = TREE_VALUE (TREE_CHAIN (arglist));
3788 const char *p = c_getstr (src);
3790 if (p)
3792 /* If the string length is zero, return the dst parameter. */
3793 if (*p == '\0')
3794 return expand_expr (dst, target, mode, EXPAND_NORMAL);
3795 else if (!optimize_size)
3797 /* Otherwise if !optimize_size, see if we can store by
3798 pieces into (dst + strlen(dst)). */
3799 tree newdst, arglist,
3800 strlen_fn = implicit_built_in_decls[BUILT_IN_STRLEN];
3802 /* This is the length argument. */
3803 arglist = build_tree_list (NULL_TREE,
3804 fold (size_binop (PLUS_EXPR,
3805 c_strlen (src, 0),
3806 ssize_int (1))));
3807 /* Prepend src argument. */
3808 arglist = tree_cons (NULL_TREE, src, arglist);
3810 /* We're going to use dst more than once. */
3811 dst = builtin_save_expr (dst);
3813 /* Create strlen (dst). */
3814 newdst =
3815 fold (build_function_call_expr (strlen_fn,
3816 build_tree_list (NULL_TREE,
3817 dst)));
3818 /* Create (dst + strlen (dst)). */
3819 newdst = fold (build2 (PLUS_EXPR, TREE_TYPE (dst), dst, newdst));
3821 /* Prepend the new dst argument. */
3822 arglist = tree_cons (NULL_TREE, newdst, arglist);
3824 /* We don't want to get turned into a memcpy if the
3825 target is const0_rtx, i.e. when the return value
3826 isn't used. That would produce pessimized code so
3827 pass in a target of zero, it should never actually be
3828 used. If this was successful return the original
3829 dst, not the result of mempcpy. */
3830 if (expand_builtin_mempcpy (arglist, /*target=*/0, mode, /*endp=*/0))
3831 return expand_expr (dst, target, mode, EXPAND_NORMAL);
3832 else
3833 return 0;
3837 return 0;
3841 /* Expand expression EXP, which is a call to the strncat builtin.
3842 Return 0 if we failed the caller should emit a normal call,
3843 otherwise try to get the result in TARGET, if convenient. */
3845 static rtx
3846 expand_builtin_strncat (tree arglist, rtx target, enum machine_mode mode)
3848 if (!validate_arglist (arglist,
3849 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
3850 return 0;
3851 else
3853 tree dst = TREE_VALUE (arglist),
3854 src = TREE_VALUE (TREE_CHAIN (arglist)),
3855 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
3856 const char *p = c_getstr (src);
3858 /* If the requested length is zero, or the src parameter string
3859 length is zero, return the dst parameter. */
3860 if (integer_zerop (len) || (p && *p == '\0'))
3862 /* Evaluate and ignore the src and len parameters in case
3863 they have side-effects. */
3864 expand_expr (src, const0_rtx, VOIDmode, EXPAND_NORMAL);
3865 expand_expr (len, const0_rtx, VOIDmode, EXPAND_NORMAL);
3866 return expand_expr (dst, target, mode, EXPAND_NORMAL);
3869 /* If the requested len is greater than or equal to the string
3870 length, call strcat. */
3871 if (TREE_CODE (len) == INTEGER_CST && p
3872 && compare_tree_int (len, strlen (p)) >= 0)
3874 tree newarglist
3875 = tree_cons (NULL_TREE, dst, build_tree_list (NULL_TREE, src));
3876 tree fn = implicit_built_in_decls[BUILT_IN_STRCAT];
3878 /* If the replacement _DECL isn't initialized, don't do the
3879 transformation. */
3880 if (!fn)
3881 return 0;
3883 return expand_expr (build_function_call_expr (fn, newarglist),
3884 target, mode, EXPAND_NORMAL);
3886 return 0;
3890 /* Expand expression EXP, which is a call to the strspn builtin.
3891 Return 0 if we failed the caller should emit a normal call,
3892 otherwise try to get the result in TARGET, if convenient. */
3894 static rtx
3895 expand_builtin_strspn (tree arglist, rtx target, enum machine_mode mode)
3897 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3898 return 0;
3899 else
3901 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
3902 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
3904 /* If both arguments are constants, evaluate at compile-time. */
3905 if (p1 && p2)
3907 const size_t r = strspn (p1, p2);
3908 return expand_expr (size_int (r), target, mode, EXPAND_NORMAL);
3911 /* If either argument is "", return 0. */
3912 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
3914 /* Evaluate and ignore both arguments in case either one has
3915 side-effects. */
3916 expand_expr (s1, const0_rtx, VOIDmode, EXPAND_NORMAL);
3917 expand_expr (s2, const0_rtx, VOIDmode, EXPAND_NORMAL);
3918 return const0_rtx;
3920 return 0;
3924 /* Expand expression EXP, which is a call to the strcspn builtin.
3925 Return 0 if we failed the caller should emit a normal call,
3926 otherwise try to get the result in TARGET, if convenient. */
3928 static rtx
3929 expand_builtin_strcspn (tree arglist, rtx target, enum machine_mode mode)
3931 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
3932 return 0;
3933 else
3935 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
3936 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
3938 /* If both arguments are constants, evaluate at compile-time. */
3939 if (p1 && p2)
3941 const size_t r = strcspn (p1, p2);
3942 return expand_expr (size_int (r), target, mode, EXPAND_NORMAL);
3945 /* If the first argument is "", return 0. */
3946 if (p1 && *p1 == '\0')
3948 /* Evaluate and ignore argument s2 in case it has
3949 side-effects. */
3950 expand_expr (s2, const0_rtx, VOIDmode, EXPAND_NORMAL);
3951 return const0_rtx;
3954 /* If the second argument is "", return __builtin_strlen(s1). */
3955 if (p2 && *p2 == '\0')
3957 tree newarglist = build_tree_list (NULL_TREE, s1),
3958 fn = implicit_built_in_decls[BUILT_IN_STRLEN];
3960 /* If the replacement _DECL isn't initialized, don't do the
3961 transformation. */
3962 if (!fn)
3963 return 0;
3965 return expand_expr (build_function_call_expr (fn, newarglist),
3966 target, mode, EXPAND_NORMAL);
3968 return 0;
3972 /* Expand a call to __builtin_saveregs, generating the result in TARGET,
3973 if that's convenient. */
3976 expand_builtin_saveregs (void)
3978 rtx val, seq;
3980 /* Don't do __builtin_saveregs more than once in a function.
3981 Save the result of the first call and reuse it. */
3982 if (saveregs_value != 0)
3983 return saveregs_value;
3985 /* When this function is called, it means that registers must be
3986 saved on entry to this function. So we migrate the call to the
3987 first insn of this function. */
3989 start_sequence ();
3991 /* Do whatever the machine needs done in this case. */
3992 val = targetm.calls.expand_builtin_saveregs ();
3994 seq = get_insns ();
3995 end_sequence ();
3997 saveregs_value = val;
3999 /* Put the insns after the NOTE that starts the function. If this
4000 is inside a start_sequence, make the outer-level insn chain current, so
4001 the code is placed at the start of the function. */
4002 push_topmost_sequence ();
4003 emit_insn_after (seq, get_insns ());
4004 pop_topmost_sequence ();
4006 return val;
4009 /* __builtin_args_info (N) returns word N of the arg space info
4010 for the current function. The number and meanings of words
4011 is controlled by the definition of CUMULATIVE_ARGS. */
4013 static rtx
4014 expand_builtin_args_info (tree arglist)
4016 int nwords = sizeof (CUMULATIVE_ARGS) / sizeof (int);
4017 int *word_ptr = (int *) &current_function_args_info;
4019 if (sizeof (CUMULATIVE_ARGS) % sizeof (int) != 0)
4020 abort ();
4022 if (arglist != 0)
4024 if (!host_integerp (TREE_VALUE (arglist), 0))
4025 error ("argument of `__builtin_args_info' must be constant");
4026 else
4028 HOST_WIDE_INT wordnum = tree_low_cst (TREE_VALUE (arglist), 0);
4030 if (wordnum < 0 || wordnum >= nwords)
4031 error ("argument of `__builtin_args_info' out of range");
4032 else
4033 return GEN_INT (word_ptr[wordnum]);
4036 else
4037 error ("missing argument in `__builtin_args_info'");
4039 return const0_rtx;
4042 /* Expand ARGLIST, from a call to __builtin_next_arg. */
4044 static rtx
4045 expand_builtin_next_arg (tree arglist)
4047 tree fntype = TREE_TYPE (current_function_decl);
4049 if (TYPE_ARG_TYPES (fntype) == 0
4050 || (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
4051 == void_type_node))
4053 error ("`va_start' used in function with fixed args");
4054 return const0_rtx;
4057 if (arglist)
4059 tree last_parm = tree_last (DECL_ARGUMENTS (current_function_decl));
4060 tree arg = TREE_VALUE (arglist);
4062 /* Strip off all nops for the sake of the comparison. This
4063 is not quite the same as STRIP_NOPS. It does more.
4064 We must also strip off INDIRECT_EXPR for C++ reference
4065 parameters. */
4066 while (TREE_CODE (arg) == NOP_EXPR
4067 || TREE_CODE (arg) == CONVERT_EXPR
4068 || TREE_CODE (arg) == NON_LVALUE_EXPR
4069 || TREE_CODE (arg) == INDIRECT_REF)
4070 arg = TREE_OPERAND (arg, 0);
4071 if (arg != last_parm)
4072 warning ("second parameter of `va_start' not last named argument");
4074 else
4075 /* Evidently an out of date version of <stdarg.h>; can't validate
4076 va_start's second argument, but can still work as intended. */
4077 warning ("`__builtin_next_arg' called without an argument");
4079 return expand_binop (Pmode, add_optab,
4080 current_function_internal_arg_pointer,
4081 current_function_arg_offset_rtx,
4082 NULL_RTX, 0, OPTAB_LIB_WIDEN);
4085 /* Make it easier for the backends by protecting the valist argument
4086 from multiple evaluations. */
4088 static tree
4089 stabilize_va_list (tree valist, int needs_lvalue)
4091 if (TREE_CODE (va_list_type_node) == ARRAY_TYPE)
4093 if (TREE_SIDE_EFFECTS (valist))
4094 valist = save_expr (valist);
4096 /* For this case, the backends will be expecting a pointer to
4097 TREE_TYPE (va_list_type_node), but it's possible we've
4098 actually been given an array (an actual va_list_type_node).
4099 So fix it. */
4100 if (TREE_CODE (TREE_TYPE (valist)) == ARRAY_TYPE)
4102 tree p1 = build_pointer_type (TREE_TYPE (va_list_type_node));
4103 tree p2 = build_pointer_type (va_list_type_node);
4105 valist = build1 (ADDR_EXPR, p2, valist);
4106 valist = fold_convert (p1, valist);
4109 else
4111 tree pt;
4113 if (! needs_lvalue)
4115 if (! TREE_SIDE_EFFECTS (valist))
4116 return valist;
4118 pt = build_pointer_type (va_list_type_node);
4119 valist = fold (build1 (ADDR_EXPR, pt, valist));
4120 TREE_SIDE_EFFECTS (valist) = 1;
4123 if (TREE_SIDE_EFFECTS (valist))
4124 valist = save_expr (valist);
4125 valist = fold (build1 (INDIRECT_REF, TREE_TYPE (TREE_TYPE (valist)),
4126 valist));
4129 return valist;
4132 /* The "standard" definition of va_list is void*. */
4134 tree
4135 std_build_builtin_va_list (void)
4137 return ptr_type_node;
4140 /* The "standard" implementation of va_start: just assign `nextarg' to
4141 the variable. */
4143 void
4144 std_expand_builtin_va_start (tree valist, rtx nextarg)
4146 tree t;
4148 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist,
4149 make_tree (ptr_type_node, nextarg));
4150 TREE_SIDE_EFFECTS (t) = 1;
4152 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4155 /* Expand ARGLIST, from a call to __builtin_va_start. */
4157 static rtx
4158 expand_builtin_va_start (tree arglist)
4160 rtx nextarg;
4161 tree chain, valist;
4163 chain = TREE_CHAIN (arglist);
4165 if (TREE_CHAIN (chain))
4166 error ("too many arguments to function `va_start'");
4168 nextarg = expand_builtin_next_arg (chain);
4169 valist = stabilize_va_list (TREE_VALUE (arglist), 1);
4171 #ifdef EXPAND_BUILTIN_VA_START
4172 EXPAND_BUILTIN_VA_START (valist, nextarg);
4173 #else
4174 std_expand_builtin_va_start (valist, nextarg);
4175 #endif
4177 return const0_rtx;
4180 /* The "standard" implementation of va_arg: read the value from the
4181 current (padded) address and increment by the (padded) size. */
4184 std_expand_builtin_va_arg (tree valist, tree type)
4186 tree addr_tree, t, type_size = NULL;
4187 tree align, alignm1;
4188 tree rounded_size;
4189 rtx addr;
4190 HOST_WIDE_INT boundary;
4192 /* Compute the rounded size of the type. */
4193 align = size_int (PARM_BOUNDARY / BITS_PER_UNIT);
4194 alignm1 = size_int (PARM_BOUNDARY / BITS_PER_UNIT - 1);
4195 boundary = FUNCTION_ARG_BOUNDARY (TYPE_MODE (type), type);
4197 /* va_list pointer is aligned to PARM_BOUNDARY. If argument actually
4198 requires greater alignment, we must perform dynamic alignment. */
4200 if (boundary > PARM_BOUNDARY)
4202 if (!PAD_VARARGS_DOWN)
4204 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist,
4205 build2 (PLUS_EXPR, TREE_TYPE (valist), valist,
4206 build_int_2 (boundary / BITS_PER_UNIT - 1, 0)));
4207 TREE_SIDE_EFFECTS (t) = 1;
4208 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4210 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist,
4211 build2 (BIT_AND_EXPR, TREE_TYPE (valist), valist,
4212 build_int_2 (~(boundary / BITS_PER_UNIT - 1), -1)));
4213 TREE_SIDE_EFFECTS (t) = 1;
4214 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4216 if (type == error_mark_node
4217 || (type_size = TYPE_SIZE_UNIT (TYPE_MAIN_VARIANT (type))) == NULL
4218 || TREE_OVERFLOW (type_size))
4219 rounded_size = size_zero_node;
4220 else
4222 rounded_size = fold (build2 (PLUS_EXPR, sizetype, type_size, alignm1));
4223 rounded_size = fold (build2 (TRUNC_DIV_EXPR, sizetype,
4224 rounded_size, align));
4225 rounded_size = fold (build2 (MULT_EXPR, sizetype,
4226 rounded_size, align));
4229 /* Get AP. */
4230 addr_tree = valist;
4231 if (PAD_VARARGS_DOWN && ! integer_zerop (rounded_size))
4233 /* Small args are padded downward. */
4234 addr_tree = fold (build2 (PLUS_EXPR, TREE_TYPE (addr_tree), addr_tree,
4235 fold (build3 (COND_EXPR, sizetype,
4236 fold (build2 (GT_EXPR, sizetype,
4237 rounded_size,
4238 align)),
4239 size_zero_node,
4240 fold (build2 (MINUS_EXPR,
4241 sizetype,
4242 rounded_size,
4243 type_size))))));
4246 addr = expand_expr (addr_tree, NULL_RTX, Pmode, EXPAND_NORMAL);
4247 addr = copy_to_reg (addr);
4249 /* Compute new value for AP. */
4250 if (! integer_zerop (rounded_size))
4252 t = build2 (MODIFY_EXPR, TREE_TYPE (valist), valist,
4253 build2 (PLUS_EXPR, TREE_TYPE (valist), valist,
4254 rounded_size));
4255 TREE_SIDE_EFFECTS (t) = 1;
4256 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4259 return addr;
4262 /* Expand __builtin_va_arg, which is not really a builtin function, but
4263 a very special sort of operator. */
4266 expand_builtin_va_arg (tree valist, tree type)
4268 rtx addr, result;
4269 tree promoted_type, want_va_type, have_va_type;
4271 /* Verify that valist is of the proper type. */
4273 want_va_type = va_list_type_node;
4274 have_va_type = TREE_TYPE (valist);
4275 if (TREE_CODE (want_va_type) == ARRAY_TYPE)
4277 /* If va_list is an array type, the argument may have decayed
4278 to a pointer type, e.g. by being passed to another function.
4279 In that case, unwrap both types so that we can compare the
4280 underlying records. */
4281 if (TREE_CODE (have_va_type) == ARRAY_TYPE
4282 || TREE_CODE (have_va_type) == POINTER_TYPE)
4284 want_va_type = TREE_TYPE (want_va_type);
4285 have_va_type = TREE_TYPE (have_va_type);
4288 if (TYPE_MAIN_VARIANT (want_va_type) != TYPE_MAIN_VARIANT (have_va_type))
4290 error ("first argument to `va_arg' not of type `va_list'");
4291 addr = const0_rtx;
4294 /* Generate a diagnostic for requesting data of a type that cannot
4295 be passed through `...' due to type promotion at the call site. */
4296 else if ((promoted_type = lang_hooks.types.type_promotes_to (type))
4297 != type)
4299 const char *name = "<anonymous type>", *pname = 0;
4300 static bool gave_help;
4302 if (TYPE_NAME (type))
4304 if (TREE_CODE (TYPE_NAME (type)) == IDENTIFIER_NODE)
4305 name = IDENTIFIER_POINTER (TYPE_NAME (type));
4306 else if (TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
4307 && DECL_NAME (TYPE_NAME (type)))
4308 name = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type)));
4310 if (TYPE_NAME (promoted_type))
4312 if (TREE_CODE (TYPE_NAME (promoted_type)) == IDENTIFIER_NODE)
4313 pname = IDENTIFIER_POINTER (TYPE_NAME (promoted_type));
4314 else if (TREE_CODE (TYPE_NAME (promoted_type)) == TYPE_DECL
4315 && DECL_NAME (TYPE_NAME (promoted_type)))
4316 pname = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (promoted_type)));
4319 /* Unfortunately, this is merely undefined, rather than a constraint
4320 violation, so we cannot make this an error. If this call is never
4321 executed, the program is still strictly conforming. */
4322 warning ("`%s' is promoted to `%s' when passed through `...'",
4323 name, pname);
4324 if (! gave_help)
4326 gave_help = true;
4327 warning ("(so you should pass `%s' not `%s' to `va_arg')",
4328 pname, name);
4331 /* We can, however, treat "undefined" any way we please.
4332 Call abort to encourage the user to fix the program. */
4333 inform ("if this code is reached, the program will abort");
4334 expand_builtin_trap ();
4336 /* This is dead code, but go ahead and finish so that the
4337 mode of the result comes out right. */
4338 addr = const0_rtx;
4340 else
4342 /* Make it easier for the backends by protecting the valist argument
4343 from multiple evaluations. */
4344 valist = stabilize_va_list (valist, 0);
4346 #ifdef EXPAND_BUILTIN_VA_ARG
4347 addr = EXPAND_BUILTIN_VA_ARG (valist, type);
4348 #else
4349 addr = std_expand_builtin_va_arg (valist, type);
4350 #endif
4353 addr = convert_memory_address (Pmode, addr);
4355 result = gen_rtx_MEM (TYPE_MODE (type), addr);
4356 set_mem_alias_set (result, get_varargs_alias_set ());
4358 return result;
4361 /* Expand ARGLIST, from a call to __builtin_va_end. */
4363 static rtx
4364 expand_builtin_va_end (tree arglist)
4366 tree valist = TREE_VALUE (arglist);
4368 /* Evaluate for side effects, if needed. I hate macros that don't
4369 do that. */
4370 if (TREE_SIDE_EFFECTS (valist))
4371 expand_expr (valist, const0_rtx, VOIDmode, EXPAND_NORMAL);
4373 return const0_rtx;
4376 /* Expand ARGLIST, from a call to __builtin_va_copy. We do this as a
4377 builtin rather than just as an assignment in stdarg.h because of the
4378 nastiness of array-type va_list types. */
4380 static rtx
4381 expand_builtin_va_copy (tree arglist)
4383 tree dst, src, t;
4385 dst = TREE_VALUE (arglist);
4386 src = TREE_VALUE (TREE_CHAIN (arglist));
4388 dst = stabilize_va_list (dst, 1);
4389 src = stabilize_va_list (src, 0);
4391 if (TREE_CODE (va_list_type_node) != ARRAY_TYPE)
4393 t = build2 (MODIFY_EXPR, va_list_type_node, dst, src);
4394 TREE_SIDE_EFFECTS (t) = 1;
4395 expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
4397 else
4399 rtx dstb, srcb, size;
4401 /* Evaluate to pointers. */
4402 dstb = expand_expr (dst, NULL_RTX, Pmode, EXPAND_NORMAL);
4403 srcb = expand_expr (src, NULL_RTX, Pmode, EXPAND_NORMAL);
4404 size = expand_expr (TYPE_SIZE_UNIT (va_list_type_node), NULL_RTX,
4405 VOIDmode, EXPAND_NORMAL);
4407 dstb = convert_memory_address (Pmode, dstb);
4408 srcb = convert_memory_address (Pmode, srcb);
4410 /* "Dereference" to BLKmode memories. */
4411 dstb = gen_rtx_MEM (BLKmode, dstb);
4412 set_mem_alias_set (dstb, get_alias_set (TREE_TYPE (TREE_TYPE (dst))));
4413 set_mem_align (dstb, TYPE_ALIGN (va_list_type_node));
4414 srcb = gen_rtx_MEM (BLKmode, srcb);
4415 set_mem_alias_set (srcb, get_alias_set (TREE_TYPE (TREE_TYPE (src))));
4416 set_mem_align (srcb, TYPE_ALIGN (va_list_type_node));
4418 /* Copy. */
4419 emit_block_move (dstb, srcb, size, BLOCK_OP_NORMAL);
4422 return const0_rtx;
4425 /* Expand a call to one of the builtin functions __builtin_frame_address or
4426 __builtin_return_address. */
4428 static rtx
4429 expand_builtin_frame_address (tree fndecl, tree arglist)
4431 /* The argument must be a nonnegative integer constant.
4432 It counts the number of frames to scan up the stack.
4433 The value is the return address saved in that frame. */
4434 if (arglist == 0)
4435 /* Warning about missing arg was already issued. */
4436 return const0_rtx;
4437 else if (! host_integerp (TREE_VALUE (arglist), 1))
4439 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4440 error ("invalid arg to `__builtin_frame_address'");
4441 else
4442 error ("invalid arg to `__builtin_return_address'");
4443 return const0_rtx;
4445 else
4447 rtx tem
4448 = expand_builtin_return_addr (DECL_FUNCTION_CODE (fndecl),
4449 tree_low_cst (TREE_VALUE (arglist), 1),
4450 hard_frame_pointer_rtx);
4452 /* Some ports cannot access arbitrary stack frames. */
4453 if (tem == NULL)
4455 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4456 warning ("unsupported arg to `__builtin_frame_address'");
4457 else
4458 warning ("unsupported arg to `__builtin_return_address'");
4459 return const0_rtx;
4462 /* For __builtin_frame_address, return what we've got. */
4463 if (DECL_FUNCTION_CODE (fndecl) == BUILT_IN_FRAME_ADDRESS)
4464 return tem;
4466 if (GET_CODE (tem) != REG
4467 && ! CONSTANT_P (tem))
4468 tem = copy_to_mode_reg (Pmode, tem);
4469 return tem;
4473 /* Expand a call to the alloca builtin, with arguments ARGLIST. Return 0 if
4474 we failed and the caller should emit a normal call, otherwise try to get
4475 the result in TARGET, if convenient. */
4477 static rtx
4478 expand_builtin_alloca (tree arglist, rtx target)
4480 rtx op0;
4481 rtx result;
4483 /* In -fmudflap-instrumented code, alloca() and __builtin_alloca()
4484 should always expand to function calls. These can be intercepted
4485 in libmudflap. */
4486 if (flag_mudflap)
4487 return 0;
4489 if (!validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
4490 return 0;
4492 /* Compute the argument. */
4493 op0 = expand_expr (TREE_VALUE (arglist), NULL_RTX, VOIDmode, 0);
4495 /* Allocate the desired space. */
4496 result = allocate_dynamic_stack_space (op0, target, BITS_PER_UNIT);
4497 result = convert_memory_address (ptr_mode, result);
4499 return result;
4502 /* Expand a call to a unary builtin. The arguments are in ARGLIST.
4503 Return 0 if a normal call should be emitted rather than expanding the
4504 function in-line. If convenient, the result should be placed in TARGET.
4505 SUBTARGET may be used as the target for computing one of EXP's operands. */
4507 static rtx
4508 expand_builtin_unop (enum machine_mode target_mode, tree arglist, rtx target,
4509 rtx subtarget, optab op_optab)
4511 rtx op0;
4512 if (!validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
4513 return 0;
4515 /* Compute the argument. */
4516 op0 = expand_expr (TREE_VALUE (arglist), subtarget, VOIDmode, 0);
4517 /* Compute op, into TARGET if possible.
4518 Set TARGET to wherever the result comes back. */
4519 target = expand_unop (TYPE_MODE (TREE_TYPE (TREE_VALUE (arglist))),
4520 op_optab, op0, target, 1);
4521 if (target == 0)
4522 abort ();
4524 return convert_to_mode (target_mode, target, 0);
4527 /* If the string passed to fputs is a constant and is one character
4528 long, we attempt to transform this call into __builtin_fputc(). */
4530 static rtx
4531 expand_builtin_fputs (tree arglist, rtx target, bool unlocked)
4533 tree len, fn;
4534 tree fn_fputc = unlocked ? implicit_built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
4535 : implicit_built_in_decls[BUILT_IN_FPUTC];
4536 tree fn_fwrite = unlocked ? implicit_built_in_decls[BUILT_IN_FWRITE_UNLOCKED]
4537 : implicit_built_in_decls[BUILT_IN_FWRITE];
4539 /* If the return value is used, or the replacement _DECL isn't
4540 initialized, don't do the transformation. */
4541 if (target != const0_rtx || !fn_fputc || !fn_fwrite)
4542 return 0;
4544 /* Verify the arguments in the original call. */
4545 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
4546 return 0;
4548 /* Get the length of the string passed to fputs. If the length
4549 can't be determined, punt. */
4550 if (!(len = c_strlen (TREE_VALUE (arglist), 1))
4551 || TREE_CODE (len) != INTEGER_CST)
4552 return 0;
4554 switch (compare_tree_int (len, 1))
4556 case -1: /* length is 0, delete the call entirely . */
4558 /* Evaluate and ignore the argument in case it has
4559 side-effects. */
4560 expand_expr (TREE_VALUE (TREE_CHAIN (arglist)), const0_rtx,
4561 VOIDmode, EXPAND_NORMAL);
4562 return const0_rtx;
4564 case 0: /* length is 1, call fputc. */
4566 const char *p = c_getstr (TREE_VALUE (arglist));
4568 if (p != NULL)
4570 /* New argument list transforming fputs(string, stream) to
4571 fputc(string[0], stream). */
4572 arglist =
4573 build_tree_list (NULL_TREE, TREE_VALUE (TREE_CHAIN (arglist)));
4574 arglist =
4575 tree_cons (NULL_TREE, build_int_2 (p[0], 0), arglist);
4576 fn = fn_fputc;
4577 break;
4580 /* Fall through. */
4581 case 1: /* length is greater than 1, call fwrite. */
4583 tree string_arg;
4585 /* If optimizing for size keep fputs. */
4586 if (optimize_size)
4587 return 0;
4588 string_arg = TREE_VALUE (arglist);
4589 /* New argument list transforming fputs(string, stream) to
4590 fwrite(string, 1, len, stream). */
4591 arglist = build_tree_list (NULL_TREE, TREE_VALUE (TREE_CHAIN (arglist)));
4592 arglist = tree_cons (NULL_TREE, len, arglist);
4593 arglist = tree_cons (NULL_TREE, size_one_node, arglist);
4594 arglist = tree_cons (NULL_TREE, string_arg, arglist);
4595 fn = fn_fwrite;
4596 break;
4598 default:
4599 abort ();
4602 return expand_expr (build_function_call_expr (fn, arglist),
4603 const0_rtx, VOIDmode, EXPAND_NORMAL);
4606 /* Expand a call to __builtin_expect. We return our argument and emit a
4607 NOTE_INSN_EXPECTED_VALUE note. This is the expansion of __builtin_expect in
4608 a non-jump context. */
4610 static rtx
4611 expand_builtin_expect (tree arglist, rtx target)
4613 tree exp, c;
4614 rtx note, rtx_c;
4616 if (arglist == NULL_TREE
4617 || TREE_CHAIN (arglist) == NULL_TREE)
4618 return const0_rtx;
4619 exp = TREE_VALUE (arglist);
4620 c = TREE_VALUE (TREE_CHAIN (arglist));
4622 if (TREE_CODE (c) != INTEGER_CST)
4624 error ("second arg to `__builtin_expect' must be a constant");
4625 c = integer_zero_node;
4628 target = expand_expr (exp, target, VOIDmode, EXPAND_NORMAL);
4630 /* Don't bother with expected value notes for integral constants. */
4631 if (flag_guess_branch_prob && GET_CODE (target) != CONST_INT)
4633 /* We do need to force this into a register so that we can be
4634 moderately sure to be able to correctly interpret the branch
4635 condition later. */
4636 target = force_reg (GET_MODE (target), target);
4638 rtx_c = expand_expr (c, NULL_RTX, GET_MODE (target), EXPAND_NORMAL);
4640 note = emit_note (NOTE_INSN_EXPECTED_VALUE);
4641 NOTE_EXPECTED_VALUE (note) = gen_rtx_EQ (VOIDmode, target, rtx_c);
4644 return target;
4647 /* Like expand_builtin_expect, except do this in a jump context. This is
4648 called from do_jump if the conditional is a __builtin_expect. Return either
4649 a list of insns to emit the jump or NULL if we cannot optimize
4650 __builtin_expect. We need to optimize this at jump time so that machines
4651 like the PowerPC don't turn the test into a SCC operation, and then jump
4652 based on the test being 0/1. */
4655 expand_builtin_expect_jump (tree exp, rtx if_false_label, rtx if_true_label)
4657 tree arglist = TREE_OPERAND (exp, 1);
4658 tree arg0 = TREE_VALUE (arglist);
4659 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
4660 rtx ret = NULL_RTX;
4662 /* Only handle __builtin_expect (test, 0) and
4663 __builtin_expect (test, 1). */
4664 if (TREE_CODE (TREE_TYPE (arg1)) == INTEGER_TYPE
4665 && (integer_zerop (arg1) || integer_onep (arg1)))
4667 rtx insn, drop_through_label, temp;
4669 /* Expand the jump insns. */
4670 start_sequence ();
4671 do_jump (arg0, if_false_label, if_true_label);
4672 ret = get_insns ();
4674 drop_through_label = get_last_insn ();
4675 if (drop_through_label && GET_CODE (drop_through_label) == NOTE)
4676 drop_through_label = prev_nonnote_insn (drop_through_label);
4677 if (drop_through_label && GET_CODE (drop_through_label) != CODE_LABEL)
4678 drop_through_label = NULL_RTX;
4679 end_sequence ();
4681 if (! if_true_label)
4682 if_true_label = drop_through_label;
4683 if (! if_false_label)
4684 if_false_label = drop_through_label;
4686 /* Go through and add the expect's to each of the conditional jumps. */
4687 insn = ret;
4688 while (insn != NULL_RTX)
4690 rtx next = NEXT_INSN (insn);
4692 if (GET_CODE (insn) == JUMP_INSN && any_condjump_p (insn))
4694 rtx ifelse = SET_SRC (pc_set (insn));
4695 rtx then_dest = XEXP (ifelse, 1);
4696 rtx else_dest = XEXP (ifelse, 2);
4697 int taken = -1;
4699 /* First check if we recognize any of the labels. */
4700 if (GET_CODE (then_dest) == LABEL_REF
4701 && XEXP (then_dest, 0) == if_true_label)
4702 taken = 1;
4703 else if (GET_CODE (then_dest) == LABEL_REF
4704 && XEXP (then_dest, 0) == if_false_label)
4705 taken = 0;
4706 else if (GET_CODE (else_dest) == LABEL_REF
4707 && XEXP (else_dest, 0) == if_false_label)
4708 taken = 1;
4709 else if (GET_CODE (else_dest) == LABEL_REF
4710 && XEXP (else_dest, 0) == if_true_label)
4711 taken = 0;
4712 /* Otherwise check where we drop through. */
4713 else if (else_dest == pc_rtx)
4715 if (next && GET_CODE (next) == NOTE)
4716 next = next_nonnote_insn (next);
4718 if (next && GET_CODE (next) == JUMP_INSN
4719 && any_uncondjump_p (next))
4720 temp = XEXP (SET_SRC (pc_set (next)), 0);
4721 else
4722 temp = next;
4724 /* TEMP is either a CODE_LABEL, NULL_RTX or something
4725 else that can't possibly match either target label. */
4726 if (temp == if_false_label)
4727 taken = 1;
4728 else if (temp == if_true_label)
4729 taken = 0;
4731 else if (then_dest == pc_rtx)
4733 if (next && GET_CODE (next) == NOTE)
4734 next = next_nonnote_insn (next);
4736 if (next && GET_CODE (next) == JUMP_INSN
4737 && any_uncondjump_p (next))
4738 temp = XEXP (SET_SRC (pc_set (next)), 0);
4739 else
4740 temp = next;
4742 if (temp == if_false_label)
4743 taken = 0;
4744 else if (temp == if_true_label)
4745 taken = 1;
4748 if (taken != -1)
4750 /* If the test is expected to fail, reverse the
4751 probabilities. */
4752 if (integer_zerop (arg1))
4753 taken = 1 - taken;
4754 predict_insn_def (insn, PRED_BUILTIN_EXPECT, taken);
4758 insn = next;
4762 return ret;
4765 void
4766 expand_builtin_trap (void)
4768 #ifdef HAVE_trap
4769 if (HAVE_trap)
4770 emit_insn (gen_trap ());
4771 else
4772 #endif
4773 emit_library_call (abort_libfunc, LCT_NORETURN, VOIDmode, 0);
4774 emit_barrier ();
4777 /* Expand a call to fabs, fabsf or fabsl with arguments ARGLIST.
4778 Return 0 if a normal call should be emitted rather than expanding
4779 the function inline. If convenient, the result should be placed
4780 in TARGET. SUBTARGET may be used as the target for computing
4781 the operand. */
4783 static rtx
4784 expand_builtin_fabs (tree arglist, rtx target, rtx subtarget)
4786 enum machine_mode mode;
4787 tree arg;
4788 rtx op0;
4790 if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
4791 return 0;
4793 arg = TREE_VALUE (arglist);
4794 mode = TYPE_MODE (TREE_TYPE (arg));
4795 op0 = expand_expr (arg, subtarget, VOIDmode, 0);
4796 return expand_abs (mode, op0, target, 0, safe_from_p (target, arg, 1));
4799 /* Expand a call to cabs, cabsf or cabsl with arguments ARGLIST.
4800 Return 0 if a normal call should be emitted rather than expanding
4801 the function inline. If convenient, the result should be placed
4802 in target. */
4804 static rtx
4805 expand_builtin_cabs (tree arglist, rtx target)
4807 enum machine_mode mode;
4808 tree arg;
4809 rtx op0;
4811 if (arglist == 0 || TREE_CHAIN (arglist))
4812 return 0;
4813 arg = TREE_VALUE (arglist);
4814 if (TREE_CODE (TREE_TYPE (arg)) != COMPLEX_TYPE
4815 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
4816 return 0;
4818 mode = TYPE_MODE (TREE_TYPE (arg));
4819 op0 = expand_expr (arg, NULL_RTX, VOIDmode, 0);
4820 return expand_complex_abs (mode, op0, target, 0);
4823 /* Create a new constant string literal and return a char* pointer to it.
4824 The STRING_CST value is the LEN characters at STR. */
4825 static tree
4826 build_string_literal (int len, const char *str)
4828 tree t, elem, index, type;
4830 t = build_string (len, str);
4831 elem = build_type_variant (char_type_node, 1, 0);
4832 index = build_index_type (build_int_2 (len - 1, 0));
4833 type = build_array_type (elem, index);
4834 TREE_TYPE (t) = type;
4835 TREE_CONSTANT (t) = 1;
4836 TREE_INVARIANT (t) = 1;
4837 TREE_READONLY (t) = 1;
4838 TREE_STATIC (t) = 1;
4840 type = build_pointer_type (type);
4841 t = build1 (ADDR_EXPR, type, t);
4843 type = build_pointer_type (elem);
4844 t = build1 (NOP_EXPR, type, t);
4845 return t;
4848 /* Expand a call to printf or printf_unlocked with argument list ARGLIST.
4849 Return 0 if a normal call should be emitted rather than transforming
4850 the function inline. If convenient, the result should be placed in
4851 TARGET with mode MODE. UNLOCKED indicates this is a printf_unlocked
4852 call. */
4853 static rtx
4854 expand_builtin_printf (tree arglist, rtx target, enum machine_mode mode,
4855 bool unlocked)
4857 tree fn_putchar = unlocked
4858 ? implicit_built_in_decls[BUILT_IN_PUTCHAR_UNLOCKED]
4859 : implicit_built_in_decls[BUILT_IN_PUTCHAR];
4860 tree fn_puts = unlocked ? implicit_built_in_decls[BUILT_IN_PUTS_UNLOCKED]
4861 : implicit_built_in_decls[BUILT_IN_PUTS];
4862 const char *fmt_str;
4863 tree fn, fmt, arg;
4865 /* If the return value is used, don't do the transformation. */
4866 if (target != const0_rtx)
4867 return 0;
4869 /* Verify the required arguments in the original call. */
4870 if (! arglist)
4871 return 0;
4872 fmt = TREE_VALUE (arglist);
4873 if (TREE_CODE (TREE_TYPE (fmt)) != POINTER_TYPE)
4874 return 0;
4875 arglist = TREE_CHAIN (arglist);
4877 /* Check whether the format is a literal string constant. */
4878 fmt_str = c_getstr (fmt);
4879 if (fmt_str == NULL)
4880 return 0;
4882 /* If the format specifier was "%s\n", call __builtin_puts(arg). */
4883 if (strcmp (fmt_str, "%s\n") == 0)
4885 if (! arglist
4886 || TREE_CODE (TREE_TYPE (TREE_VALUE (arglist))) != POINTER_TYPE
4887 || TREE_CHAIN (arglist))
4888 return 0;
4889 fn = fn_puts;
4891 /* If the format specifier was "%c", call __builtin_putchar(arg). */
4892 else if (strcmp (fmt_str, "%c") == 0)
4894 if (! arglist
4895 || TREE_CODE (TREE_TYPE (TREE_VALUE (arglist))) != INTEGER_TYPE
4896 || TREE_CHAIN (arglist))
4897 return 0;
4898 fn = fn_putchar;
4900 else
4902 /* We can't handle anything else with % args or %% ... yet. */
4903 if (strchr (fmt_str, '%'))
4904 return 0;
4906 if (arglist)
4907 return 0;
4909 /* If the format specifier was "", printf does nothing. */
4910 if (fmt_str[0] == '\0')
4911 return const0_rtx;
4912 /* If the format specifier has length of 1, call putchar. */
4913 if (fmt_str[1] == '\0')
4915 /* Given printf("c"), (where c is any one character,)
4916 convert "c"[0] to an int and pass that to the replacement
4917 function. */
4918 arg = build_int_2 (fmt_str[0], 0);
4919 arglist = build_tree_list (NULL_TREE, arg);
4920 fn = fn_putchar;
4922 else
4924 /* If the format specifier was "string\n", call puts("string"). */
4925 size_t len = strlen (fmt_str);
4926 if (fmt_str[len - 1] == '\n')
4928 /* Create a NUL-terminated string that's one char shorter
4929 than the original, stripping off the trailing '\n'. */
4930 char *newstr = alloca (len);
4931 memcpy (newstr, fmt_str, len - 1);
4932 newstr[len - 1] = 0;
4934 arg = build_string_literal (len, newstr);
4935 arglist = build_tree_list (NULL_TREE, arg);
4936 fn = fn_puts;
4938 else
4939 /* We'd like to arrange to call fputs(string,stdout) here,
4940 but we need stdout and don't have a way to get it yet. */
4941 return 0;
4945 if (!fn)
4946 return 0;
4947 return expand_expr (build_function_call_expr (fn, arglist),
4948 target, mode, EXPAND_NORMAL);
4951 /* Expand a call to fprintf or fprintf_unlocked with argument list ARGLIST.
4952 Return 0 if a normal call should be emitted rather than transforming
4953 the function inline. If convenient, the result should be placed in
4954 TARGET with mode MODE. UNLOCKED indicates this is a fprintf_unlocked
4955 call. */
4956 static rtx
4957 expand_builtin_fprintf (tree arglist, rtx target, enum machine_mode mode,
4958 bool unlocked)
4960 tree fn_fputc = unlocked ? implicit_built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
4961 : implicit_built_in_decls[BUILT_IN_FPUTC];
4962 tree fn_fputs = unlocked ? implicit_built_in_decls[BUILT_IN_FPUTS_UNLOCKED]
4963 : implicit_built_in_decls[BUILT_IN_FPUTS];
4964 const char *fmt_str;
4965 tree fn, fmt, fp, arg;
4967 /* If the return value is used, don't do the transformation. */
4968 if (target != const0_rtx)
4969 return 0;
4971 /* Verify the required arguments in the original call. */
4972 if (! arglist)
4973 return 0;
4974 fp = TREE_VALUE (arglist);
4975 if (TREE_CODE (TREE_TYPE (fp)) != POINTER_TYPE)
4976 return 0;
4977 arglist = TREE_CHAIN (arglist);
4978 if (! arglist)
4979 return 0;
4980 fmt = TREE_VALUE (arglist);
4981 if (TREE_CODE (TREE_TYPE (fmt)) != POINTER_TYPE)
4982 return 0;
4983 arglist = TREE_CHAIN (arglist);
4985 /* Check whether the format is a literal string constant. */
4986 fmt_str = c_getstr (fmt);
4987 if (fmt_str == NULL)
4988 return 0;
4990 /* If the format specifier was "%s", call __builtin_fputs(arg,fp). */
4991 if (strcmp (fmt_str, "%s") == 0)
4993 if (! arglist
4994 || TREE_CODE (TREE_TYPE (TREE_VALUE (arglist))) != POINTER_TYPE
4995 || TREE_CHAIN (arglist))
4996 return 0;
4997 arg = TREE_VALUE (arglist);
4998 arglist = build_tree_list (NULL_TREE, fp);
4999 arglist = tree_cons (NULL_TREE, arg, arglist);
5000 fn = fn_fputs;
5002 /* If the format specifier was "%c", call __builtin_fputc(arg,fp). */
5003 else if (strcmp (fmt_str, "%c") == 0)
5005 if (! arglist
5006 || TREE_CODE (TREE_TYPE (TREE_VALUE (arglist))) != INTEGER_TYPE
5007 || TREE_CHAIN (arglist))
5008 return 0;
5009 arg = TREE_VALUE (arglist);
5010 arglist = build_tree_list (NULL_TREE, fp);
5011 arglist = tree_cons (NULL_TREE, arg, arglist);
5012 fn = fn_fputc;
5014 else
5016 /* We can't handle anything else with % args or %% ... yet. */
5017 if (strchr (fmt_str, '%'))
5018 return 0;
5020 if (arglist)
5021 return 0;
5023 /* If the format specifier was "", fprintf does nothing. */
5024 if (fmt_str[0] == '\0')
5026 /* Evaluate and ignore FILE* argument for side-effects. */
5027 expand_expr (fp, const0_rtx, VOIDmode, EXPAND_NORMAL);
5028 return const0_rtx;
5031 /* When "string" doesn't contain %, replace all cases of
5032 fprintf(stream,string) with fputs(string,stream). The fputs
5033 builtin will take care of special cases like length == 1. */
5034 arglist = build_tree_list (NULL_TREE, fp);
5035 arglist = tree_cons (NULL_TREE, fmt, arglist);
5036 fn = fn_fputs;
5039 if (!fn)
5040 return 0;
5041 return expand_expr (build_function_call_expr (fn, arglist),
5042 target, mode, EXPAND_NORMAL);
5045 /* Expand a call to sprintf with argument list ARGLIST. Return 0 if
5046 a normal call should be emitted rather than expanding the function
5047 inline. If convenient, the result should be placed in TARGET with
5048 mode MODE. */
5050 static rtx
5051 expand_builtin_sprintf (tree arglist, rtx target, enum machine_mode mode)
5053 tree orig_arglist, dest, fmt;
5054 const char *fmt_str;
5056 orig_arglist = arglist;
5058 /* Verify the required arguments in the original call. */
5059 if (! arglist)
5060 return 0;
5061 dest = TREE_VALUE (arglist);
5062 if (TREE_CODE (TREE_TYPE (dest)) != POINTER_TYPE)
5063 return 0;
5064 arglist = TREE_CHAIN (arglist);
5065 if (! arglist)
5066 return 0;
5067 fmt = TREE_VALUE (arglist);
5068 if (TREE_CODE (TREE_TYPE (fmt)) != POINTER_TYPE)
5069 return 0;
5070 arglist = TREE_CHAIN (arglist);
5072 /* Check whether the format is a literal string constant. */
5073 fmt_str = c_getstr (fmt);
5074 if (fmt_str == NULL)
5075 return 0;
5077 /* If the format doesn't contain % args or %%, use strcpy. */
5078 if (strchr (fmt_str, '%') == 0)
5080 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
5081 tree exp;
5083 if (arglist || ! fn)
5084 return 0;
5085 expand_expr (build_function_call_expr (fn, orig_arglist),
5086 const0_rtx, VOIDmode, EXPAND_NORMAL);
5087 if (target == const0_rtx)
5088 return const0_rtx;
5089 exp = build_int_2 (strlen (fmt_str), 0);
5090 exp = fold_convert (integer_type_node, exp);
5091 return expand_expr (exp, target, mode, EXPAND_NORMAL);
5093 /* If the format is "%s", use strcpy if the result isn't used. */
5094 else if (strcmp (fmt_str, "%s") == 0)
5096 tree fn, arg, len;
5097 fn = implicit_built_in_decls[BUILT_IN_STRCPY];
5099 if (! fn)
5100 return 0;
5102 if (! arglist || TREE_CHAIN (arglist))
5103 return 0;
5104 arg = TREE_VALUE (arglist);
5105 if (TREE_CODE (TREE_TYPE (arg)) != POINTER_TYPE)
5106 return 0;
5108 if (target != const0_rtx)
5110 len = c_strlen (arg, 1);
5111 if (! len || TREE_CODE (len) != INTEGER_CST)
5112 return 0;
5114 else
5115 len = NULL_TREE;
5117 arglist = build_tree_list (NULL_TREE, arg);
5118 arglist = tree_cons (NULL_TREE, dest, arglist);
5119 expand_expr (build_function_call_expr (fn, arglist),
5120 const0_rtx, VOIDmode, EXPAND_NORMAL);
5122 if (target == const0_rtx)
5123 return const0_rtx;
5124 return expand_expr (len, target, mode, EXPAND_NORMAL);
5127 return 0;
5130 /* Expand a call to either the entry or exit function profiler. */
5132 static rtx
5133 expand_builtin_profile_func (bool exitp)
5135 rtx this, which;
5137 this = DECL_RTL (current_function_decl);
5138 if (GET_CODE (this) == MEM)
5139 this = XEXP (this, 0);
5140 else
5141 abort ();
5143 if (exitp)
5144 which = profile_function_exit_libfunc;
5145 else
5146 which = profile_function_entry_libfunc;
5148 emit_library_call (which, LCT_NORMAL, VOIDmode, 2, this, Pmode,
5149 expand_builtin_return_addr (BUILT_IN_RETURN_ADDRESS,
5150 0, hard_frame_pointer_rtx),
5151 Pmode);
5153 return const0_rtx;
5156 /* Given a trampoline address, make sure it satisfies TRAMPOLINE_ALIGNMENT. */
5158 static rtx
5159 round_trampoline_addr (rtx tramp)
5161 rtx temp, addend, mask;
5163 /* If we don't need too much alignment, we'll have been guaranteed
5164 proper alignment by get_trampoline_type. */
5165 if (TRAMPOLINE_ALIGNMENT <= STACK_BOUNDARY)
5166 return tramp;
5168 /* Round address up to desired boundary. */
5169 temp = gen_reg_rtx (Pmode);
5170 addend = GEN_INT (TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT - 1);
5171 mask = GEN_INT (-TRAMPOLINE_ALIGNMENT / BITS_PER_UNIT);
5173 temp = expand_simple_binop (Pmode, PLUS, tramp, addend,
5174 temp, 0, OPTAB_LIB_WIDEN);
5175 tramp = expand_simple_binop (Pmode, AND, temp, mask,
5176 temp, 0, OPTAB_LIB_WIDEN);
5178 return tramp;
5181 static rtx
5182 expand_builtin_init_trampoline (tree arglist)
5184 tree t_tramp, t_func, t_chain;
5185 rtx r_tramp, r_func, r_chain;
5186 #ifdef TRAMPOLINE_TEMPLATE
5187 rtx blktramp;
5188 #endif
5190 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE,
5191 POINTER_TYPE, VOID_TYPE))
5192 return NULL_RTX;
5194 t_tramp = TREE_VALUE (arglist);
5195 arglist = TREE_CHAIN (arglist);
5196 t_func = TREE_VALUE (arglist);
5197 arglist = TREE_CHAIN (arglist);
5198 t_chain = TREE_VALUE (arglist);
5200 r_tramp = expand_expr (t_tramp, NULL_RTX, VOIDmode, 0);
5201 r_func = expand_expr (t_func, NULL_RTX, VOIDmode, 0);
5202 r_chain = expand_expr (t_chain, NULL_RTX, VOIDmode, 0);
5204 /* Generate insns to initialize the trampoline. */
5205 r_tramp = round_trampoline_addr (r_tramp);
5206 #ifdef TRAMPOLINE_TEMPLATE
5207 blktramp = gen_rtx_MEM (BLKmode, r_tramp);
5208 set_mem_align (blktramp, TRAMPOLINE_ALIGNMENT);
5209 emit_block_move (blktramp, assemble_trampoline_template (),
5210 GEN_INT (TRAMPOLINE_SIZE), BLOCK_OP_NORMAL);
5211 #endif
5212 trampolines_created = 1;
5213 INITIALIZE_TRAMPOLINE (r_tramp, r_func, r_chain);
5215 return const0_rtx;
5218 static rtx
5219 expand_builtin_adjust_trampoline (tree arglist)
5221 rtx tramp;
5223 if (!validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
5224 return NULL_RTX;
5226 tramp = expand_expr (TREE_VALUE (arglist), NULL_RTX, VOIDmode, 0);
5227 tramp = round_trampoline_addr (tramp);
5228 #ifdef TRAMPOLINE_ADJUST_ADDRESS
5229 TRAMPOLINE_ADJUST_ADDRESS (tramp);
5230 #endif
5232 return tramp;
5235 /* Expand a call to the built-in signbit, signbitf or signbitl function.
5236 Return NULL_RTX if a normal call should be emitted rather than expanding
5237 the function in-line. EXP is the expression that is a call to the builtin
5238 function; if convenient, the result should be placed in TARGET. */
5240 static rtx
5241 expand_builtin_signbit (tree exp, rtx target)
5243 const struct real_format *fmt;
5244 enum machine_mode fmode, imode, rmode;
5245 HOST_WIDE_INT hi, lo;
5246 tree arg, arglist;
5247 int bitpos;
5248 rtx temp;
5250 arglist = TREE_OPERAND (exp, 1);
5251 if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
5252 return 0;
5254 arg = TREE_VALUE (arglist);
5255 fmode = TYPE_MODE (TREE_TYPE (arg));
5256 rmode = TYPE_MODE (TREE_TYPE (exp));
5257 fmt = REAL_MODE_FORMAT (fmode);
5259 /* For floating point formats without a sign bit, implement signbit
5260 as "ARG < 0.0". */
5261 if (fmt->signbit < 0)
5263 /* But we can't do this if the format supports signed zero. */
5264 if (fmt->has_signed_zero && HONOR_SIGNED_ZEROS (fmode))
5265 return 0;
5267 arg = fold (build2 (LT_EXPR, TREE_TYPE (exp), arg,
5268 build_real (TREE_TYPE (arg), dconst0)));
5269 return expand_expr (arg, target, VOIDmode, EXPAND_NORMAL);
5272 imode = int_mode_for_mode (fmode);
5273 if (imode == BLKmode)
5274 return 0;
5276 bitpos = fmt->signbit;
5277 /* Handle targets with different FP word orders. */
5278 if (FLOAT_WORDS_BIG_ENDIAN != WORDS_BIG_ENDIAN)
5280 int nwords = GET_MODE_BITSIZE (fmode) / BITS_PER_WORD;
5281 int word = nwords - (bitpos / BITS_PER_WORD) - 1;
5282 bitpos = word * BITS_PER_WORD + bitpos % BITS_PER_WORD;
5285 /* If the sign bit is not in the lowpart and the floating point format
5286 is wider than an integer, check that is twice the size of an integer
5287 so that we can use gen_highpart below. */
5288 if (bitpos >= GET_MODE_BITSIZE (rmode)
5289 && GET_MODE_BITSIZE (imode) != 2 * GET_MODE_BITSIZE (rmode))
5290 return 0;
5292 temp = expand_expr (arg, NULL_RTX, VOIDmode, 0);
5293 temp = gen_lowpart (imode, temp);
5295 if (GET_MODE_BITSIZE (imode) > GET_MODE_BITSIZE (rmode))
5297 if (BYTES_BIG_ENDIAN)
5298 bitpos = GET_MODE_BITSIZE (imode) - 1 - bitpos;
5299 temp = copy_to_mode_reg (imode, temp);
5300 temp = extract_bit_field (temp, 1, bitpos, 1,
5301 NULL_RTX, rmode, rmode,
5302 GET_MODE_SIZE (imode));
5304 else
5306 if (GET_MODE_BITSIZE (imode) < GET_MODE_BITSIZE (rmode))
5307 temp = gen_lowpart (rmode, temp);
5308 if (bitpos < HOST_BITS_PER_WIDE_INT)
5310 hi = 0;
5311 lo = (HOST_WIDE_INT) 1 << bitpos;
5313 else
5315 hi = (HOST_WIDE_INT) 1 << (bitpos - HOST_BITS_PER_WIDE_INT);
5316 lo = 0;
5319 temp = force_reg (rmode, temp);
5320 temp = expand_binop (rmode, and_optab, temp,
5321 immed_double_const (lo, hi, rmode),
5322 target, 1, OPTAB_LIB_WIDEN);
5324 return temp;
5327 /* Expand fork or exec calls. TARGET is the desired target of the
5328 call. ARGLIST is the list of arguments of the call. FN is the
5329 identificator of the actual function. IGNORE is nonzero if the
5330 value is to be ignored. */
5332 static rtx
5333 expand_builtin_fork_or_exec (tree fn, tree arglist, rtx target, int ignore)
5335 tree id, decl;
5336 tree call;
5338 /* If we are not profiling, just call the function. */
5339 if (!profile_arc_flag)
5340 return NULL_RTX;
5342 /* Otherwise call the wrapper. This should be equivalent for the rest of
5343 compiler, so the code does not diverge, and the wrapper may run the
5344 code necessary for keeping the profiling sane. */
5346 switch (DECL_FUNCTION_CODE (fn))
5348 case BUILT_IN_FORK:
5349 id = get_identifier ("__gcov_fork");
5350 break;
5352 case BUILT_IN_EXECL:
5353 id = get_identifier ("__gcov_execl");
5354 break;
5356 case BUILT_IN_EXECV:
5357 id = get_identifier ("__gcov_execv");
5358 break;
5360 case BUILT_IN_EXECLP:
5361 id = get_identifier ("__gcov_execlp");
5362 break;
5364 case BUILT_IN_EXECLE:
5365 id = get_identifier ("__gcov_execle");
5366 break;
5368 case BUILT_IN_EXECVP:
5369 id = get_identifier ("__gcov_execvp");
5370 break;
5372 case BUILT_IN_EXECVE:
5373 id = get_identifier ("__gcov_execve");
5374 break;
5376 default:
5377 abort ();
5380 decl = build_decl (FUNCTION_DECL, id, TREE_TYPE (fn));
5381 DECL_EXTERNAL (decl) = 1;
5382 TREE_PUBLIC (decl) = 1;
5383 DECL_ARTIFICIAL (decl) = 1;
5384 TREE_NOTHROW (decl) = 1;
5385 call = build_function_call_expr (decl, arglist);
5387 return expand_call (call, target, ignore);
5390 /* Expand an expression EXP that calls a built-in function,
5391 with result going to TARGET if that's convenient
5392 (and in mode MODE if that's convenient).
5393 SUBTARGET may be used as the target for computing one of EXP's operands.
5394 IGNORE is nonzero if the value is to be ignored. */
5397 expand_builtin (tree exp, rtx target, rtx subtarget, enum machine_mode mode,
5398 int ignore)
5400 tree fndecl = get_callee_fndecl (exp);
5401 tree arglist = TREE_OPERAND (exp, 1);
5402 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
5403 enum machine_mode target_mode = TYPE_MODE (TREE_TYPE (exp));
5405 /* Perform postincrements before expanding builtin functions. */
5406 emit_queue ();
5408 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
5409 return targetm.expand_builtin (exp, target, subtarget, mode, ignore);
5411 /* When not optimizing, generate calls to library functions for a certain
5412 set of builtins. */
5413 if (!optimize
5414 && !CALLED_AS_BUILT_IN (fndecl)
5415 && DECL_ASSEMBLER_NAME_SET_P (fndecl)
5416 && fcode != BUILT_IN_ALLOCA)
5417 return expand_call (exp, target, ignore);
5419 /* The built-in function expanders test for target == const0_rtx
5420 to determine whether the function's result will be ignored. */
5421 if (ignore)
5422 target = const0_rtx;
5424 /* If the result of a pure or const built-in function is ignored, and
5425 none of its arguments are volatile, we can avoid expanding the
5426 built-in call and just evaluate the arguments for side-effects. */
5427 if (target == const0_rtx
5428 && (DECL_IS_PURE (fndecl) || TREE_READONLY (fndecl)))
5430 bool volatilep = false;
5431 tree arg;
5433 for (arg = arglist; arg; arg = TREE_CHAIN (arg))
5434 if (TREE_THIS_VOLATILE (TREE_VALUE (arg)))
5436 volatilep = true;
5437 break;
5440 if (! volatilep)
5442 for (arg = arglist; arg; arg = TREE_CHAIN (arg))
5443 expand_expr (TREE_VALUE (arg), const0_rtx,
5444 VOIDmode, EXPAND_NORMAL);
5445 return const0_rtx;
5449 switch (fcode)
5451 case BUILT_IN_ABS:
5452 case BUILT_IN_LABS:
5453 case BUILT_IN_LLABS:
5454 case BUILT_IN_IMAXABS:
5455 /* build_function_call changes these into ABS_EXPR. */
5456 abort ();
5458 case BUILT_IN_FABS:
5459 case BUILT_IN_FABSF:
5460 case BUILT_IN_FABSL:
5461 target = expand_builtin_fabs (arglist, target, subtarget);
5462 if (target)
5463 return target;
5464 break;
5466 case BUILT_IN_CABS:
5467 case BUILT_IN_CABSF:
5468 case BUILT_IN_CABSL:
5469 if (flag_unsafe_math_optimizations)
5471 target = expand_builtin_cabs (arglist, target);
5472 if (target)
5473 return target;
5475 break;
5477 case BUILT_IN_CONJ:
5478 case BUILT_IN_CONJF:
5479 case BUILT_IN_CONJL:
5480 case BUILT_IN_CREAL:
5481 case BUILT_IN_CREALF:
5482 case BUILT_IN_CREALL:
5483 case BUILT_IN_CIMAG:
5484 case BUILT_IN_CIMAGF:
5485 case BUILT_IN_CIMAGL:
5486 /* expand_tree_builtin changes these into CONJ_EXPR, REALPART_EXPR
5487 and IMAGPART_EXPR. */
5488 abort ();
5490 case BUILT_IN_EXP:
5491 case BUILT_IN_EXPF:
5492 case BUILT_IN_EXPL:
5493 case BUILT_IN_EXP10:
5494 case BUILT_IN_EXP10F:
5495 case BUILT_IN_EXP10L:
5496 case BUILT_IN_POW10:
5497 case BUILT_IN_POW10F:
5498 case BUILT_IN_POW10L:
5499 case BUILT_IN_EXP2:
5500 case BUILT_IN_EXP2F:
5501 case BUILT_IN_EXP2L:
5502 case BUILT_IN_EXPM1:
5503 case BUILT_IN_EXPM1F:
5504 case BUILT_IN_EXPM1L:
5505 case BUILT_IN_LOGB:
5506 case BUILT_IN_LOGBF:
5507 case BUILT_IN_LOGBL:
5508 case BUILT_IN_ILOGB:
5509 case BUILT_IN_ILOGBF:
5510 case BUILT_IN_ILOGBL:
5511 case BUILT_IN_LOG:
5512 case BUILT_IN_LOGF:
5513 case BUILT_IN_LOGL:
5514 case BUILT_IN_LOG10:
5515 case BUILT_IN_LOG10F:
5516 case BUILT_IN_LOG10L:
5517 case BUILT_IN_LOG2:
5518 case BUILT_IN_LOG2F:
5519 case BUILT_IN_LOG2L:
5520 case BUILT_IN_LOG1P:
5521 case BUILT_IN_LOG1PF:
5522 case BUILT_IN_LOG1PL:
5523 case BUILT_IN_TAN:
5524 case BUILT_IN_TANF:
5525 case BUILT_IN_TANL:
5526 case BUILT_IN_ASIN:
5527 case BUILT_IN_ASINF:
5528 case BUILT_IN_ASINL:
5529 case BUILT_IN_ACOS:
5530 case BUILT_IN_ACOSF:
5531 case BUILT_IN_ACOSL:
5532 case BUILT_IN_ATAN:
5533 case BUILT_IN_ATANF:
5534 case BUILT_IN_ATANL:
5535 /* Treat these like sqrt only if unsafe math optimizations are allowed,
5536 because of possible accuracy problems. */
5537 if (! flag_unsafe_math_optimizations)
5538 break;
5539 case BUILT_IN_SQRT:
5540 case BUILT_IN_SQRTF:
5541 case BUILT_IN_SQRTL:
5542 case BUILT_IN_FLOOR:
5543 case BUILT_IN_FLOORF:
5544 case BUILT_IN_FLOORL:
5545 case BUILT_IN_CEIL:
5546 case BUILT_IN_CEILF:
5547 case BUILT_IN_CEILL:
5548 case BUILT_IN_TRUNC:
5549 case BUILT_IN_TRUNCF:
5550 case BUILT_IN_TRUNCL:
5551 case BUILT_IN_ROUND:
5552 case BUILT_IN_ROUNDF:
5553 case BUILT_IN_ROUNDL:
5554 case BUILT_IN_NEARBYINT:
5555 case BUILT_IN_NEARBYINTF:
5556 case BUILT_IN_NEARBYINTL:
5557 target = expand_builtin_mathfn (exp, target, subtarget);
5558 if (target)
5559 return target;
5560 break;
5562 case BUILT_IN_POW:
5563 case BUILT_IN_POWF:
5564 case BUILT_IN_POWL:
5565 target = expand_builtin_pow (exp, target, subtarget);
5566 if (target)
5567 return target;
5568 break;
5570 case BUILT_IN_ATAN2:
5571 case BUILT_IN_ATAN2F:
5572 case BUILT_IN_ATAN2L:
5573 case BUILT_IN_FMOD:
5574 case BUILT_IN_FMODF:
5575 case BUILT_IN_FMODL:
5576 case BUILT_IN_DREM:
5577 case BUILT_IN_DREMF:
5578 case BUILT_IN_DREML:
5579 if (! flag_unsafe_math_optimizations)
5580 break;
5581 target = expand_builtin_mathfn_2 (exp, target, subtarget);
5582 if (target)
5583 return target;
5584 break;
5586 case BUILT_IN_SIN:
5587 case BUILT_IN_SINF:
5588 case BUILT_IN_SINL:
5589 case BUILT_IN_COS:
5590 case BUILT_IN_COSF:
5591 case BUILT_IN_COSL:
5592 if (! flag_unsafe_math_optimizations)
5593 break;
5594 target = expand_builtin_mathfn_3 (exp, target, subtarget);
5595 if (target)
5596 return target;
5597 break;
5599 case BUILT_IN_APPLY_ARGS:
5600 return expand_builtin_apply_args ();
5602 /* __builtin_apply (FUNCTION, ARGUMENTS, ARGSIZE) invokes
5603 FUNCTION with a copy of the parameters described by
5604 ARGUMENTS, and ARGSIZE. It returns a block of memory
5605 allocated on the stack into which is stored all the registers
5606 that might possibly be used for returning the result of a
5607 function. ARGUMENTS is the value returned by
5608 __builtin_apply_args. ARGSIZE is the number of bytes of
5609 arguments that must be copied. ??? How should this value be
5610 computed? We'll also need a safe worst case value for varargs
5611 functions. */
5612 case BUILT_IN_APPLY:
5613 if (!validate_arglist (arglist, POINTER_TYPE,
5614 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE)
5615 && !validate_arglist (arglist, REFERENCE_TYPE,
5616 POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
5617 return const0_rtx;
5618 else
5620 int i;
5621 tree t;
5622 rtx ops[3];
5624 for (t = arglist, i = 0; t; t = TREE_CHAIN (t), i++)
5625 ops[i] = expand_expr (TREE_VALUE (t), NULL_RTX, VOIDmode, 0);
5627 return expand_builtin_apply (ops[0], ops[1], ops[2]);
5630 /* __builtin_return (RESULT) causes the function to return the
5631 value described by RESULT. RESULT is address of the block of
5632 memory returned by __builtin_apply. */
5633 case BUILT_IN_RETURN:
5634 if (validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
5635 expand_builtin_return (expand_expr (TREE_VALUE (arglist),
5636 NULL_RTX, VOIDmode, 0));
5637 return const0_rtx;
5639 case BUILT_IN_SAVEREGS:
5640 return expand_builtin_saveregs ();
5642 case BUILT_IN_ARGS_INFO:
5643 return expand_builtin_args_info (arglist);
5645 /* Return the address of the first anonymous stack arg. */
5646 case BUILT_IN_NEXT_ARG:
5647 simplify_builtin_next_arg (arglist);
5648 return expand_builtin_next_arg (arglist);
5650 case BUILT_IN_CLASSIFY_TYPE:
5651 return expand_builtin_classify_type (arglist);
5653 case BUILT_IN_CONSTANT_P:
5654 return const0_rtx;
5656 case BUILT_IN_FRAME_ADDRESS:
5657 case BUILT_IN_RETURN_ADDRESS:
5658 return expand_builtin_frame_address (fndecl, arglist);
5660 /* Returns the address of the area where the structure is returned.
5661 0 otherwise. */
5662 case BUILT_IN_AGGREGATE_INCOMING_ADDRESS:
5663 if (arglist != 0
5664 || ! AGGREGATE_TYPE_P (TREE_TYPE (TREE_TYPE (current_function_decl)))
5665 || GET_CODE (DECL_RTL (DECL_RESULT (current_function_decl))) != MEM)
5666 return const0_rtx;
5667 else
5668 return XEXP (DECL_RTL (DECL_RESULT (current_function_decl)), 0);
5670 case BUILT_IN_ALLOCA:
5671 target = expand_builtin_alloca (arglist, target);
5672 if (target)
5673 return target;
5674 break;
5676 case BUILT_IN_STACK_ALLOC:
5677 expand_stack_alloc (TREE_VALUE (arglist),
5678 TREE_VALUE (TREE_CHAIN (arglist)));
5679 return const0_rtx;
5681 case BUILT_IN_STACK_SAVE:
5682 return expand_stack_save ();
5684 case BUILT_IN_STACK_RESTORE:
5685 expand_stack_restore (TREE_VALUE (arglist));
5686 return const0_rtx;
5688 case BUILT_IN_FFS:
5689 case BUILT_IN_FFSL:
5690 case BUILT_IN_FFSLL:
5691 target = expand_builtin_unop (target_mode, arglist, target,
5692 subtarget, ffs_optab);
5693 if (target)
5694 return target;
5695 break;
5697 case BUILT_IN_CLZ:
5698 case BUILT_IN_CLZL:
5699 case BUILT_IN_CLZLL:
5700 target = expand_builtin_unop (target_mode, arglist, target,
5701 subtarget, clz_optab);
5702 if (target)
5703 return target;
5704 break;
5706 case BUILT_IN_CTZ:
5707 case BUILT_IN_CTZL:
5708 case BUILT_IN_CTZLL:
5709 target = expand_builtin_unop (target_mode, arglist, target,
5710 subtarget, ctz_optab);
5711 if (target)
5712 return target;
5713 break;
5715 case BUILT_IN_POPCOUNT:
5716 case BUILT_IN_POPCOUNTL:
5717 case BUILT_IN_POPCOUNTLL:
5718 target = expand_builtin_unop (target_mode, arglist, target,
5719 subtarget, popcount_optab);
5720 if (target)
5721 return target;
5722 break;
5724 case BUILT_IN_PARITY:
5725 case BUILT_IN_PARITYL:
5726 case BUILT_IN_PARITYLL:
5727 target = expand_builtin_unop (target_mode, arglist, target,
5728 subtarget, parity_optab);
5729 if (target)
5730 return target;
5731 break;
5733 case BUILT_IN_STRLEN:
5734 target = expand_builtin_strlen (arglist, target, target_mode);
5735 if (target)
5736 return target;
5737 break;
5739 case BUILT_IN_STRCPY:
5740 target = expand_builtin_strcpy (arglist, target, mode);
5741 if (target)
5742 return target;
5743 break;
5745 case BUILT_IN_STRNCPY:
5746 target = expand_builtin_strncpy (arglist, target, mode);
5747 if (target)
5748 return target;
5749 break;
5751 case BUILT_IN_STPCPY:
5752 target = expand_builtin_stpcpy (arglist, target, mode);
5753 if (target)
5754 return target;
5755 break;
5757 case BUILT_IN_STRCAT:
5758 target = expand_builtin_strcat (arglist, target, mode);
5759 if (target)
5760 return target;
5761 break;
5763 case BUILT_IN_STRNCAT:
5764 target = expand_builtin_strncat (arglist, target, mode);
5765 if (target)
5766 return target;
5767 break;
5769 case BUILT_IN_STRSPN:
5770 target = expand_builtin_strspn (arglist, target, mode);
5771 if (target)
5772 return target;
5773 break;
5775 case BUILT_IN_STRCSPN:
5776 target = expand_builtin_strcspn (arglist, target, mode);
5777 if (target)
5778 return target;
5779 break;
5781 case BUILT_IN_STRSTR:
5782 target = expand_builtin_strstr (arglist, target, mode);
5783 if (target)
5784 return target;
5785 break;
5787 case BUILT_IN_STRPBRK:
5788 target = expand_builtin_strpbrk (arglist, target, mode);
5789 if (target)
5790 return target;
5791 break;
5793 case BUILT_IN_INDEX:
5794 case BUILT_IN_STRCHR:
5795 target = expand_builtin_strchr (arglist, target, mode);
5796 if (target)
5797 return target;
5798 break;
5800 case BUILT_IN_RINDEX:
5801 case BUILT_IN_STRRCHR:
5802 target = expand_builtin_strrchr (arglist, target, mode);
5803 if (target)
5804 return target;
5805 break;
5807 case BUILT_IN_MEMCPY:
5808 target = expand_builtin_memcpy (arglist, target, mode);
5809 if (target)
5810 return target;
5811 break;
5813 case BUILT_IN_MEMPCPY:
5814 target = expand_builtin_mempcpy (arglist, target, mode, /*endp=*/ 1);
5815 if (target)
5816 return target;
5817 break;
5819 case BUILT_IN_MEMMOVE:
5820 target = expand_builtin_memmove (arglist, target, mode);
5821 if (target)
5822 return target;
5823 break;
5825 case BUILT_IN_BCOPY:
5826 target = expand_builtin_bcopy (arglist);
5827 if (target)
5828 return target;
5829 break;
5831 case BUILT_IN_MEMSET:
5832 target = expand_builtin_memset (arglist, target, mode);
5833 if (target)
5834 return target;
5835 break;
5837 case BUILT_IN_BZERO:
5838 target = expand_builtin_bzero (arglist);
5839 if (target)
5840 return target;
5841 break;
5843 case BUILT_IN_STRCMP:
5844 target = expand_builtin_strcmp (exp, target, mode);
5845 if (target)
5846 return target;
5847 break;
5849 case BUILT_IN_STRNCMP:
5850 target = expand_builtin_strncmp (exp, target, mode);
5851 if (target)
5852 return target;
5853 break;
5855 case BUILT_IN_BCMP:
5856 case BUILT_IN_MEMCMP:
5857 target = expand_builtin_memcmp (exp, arglist, target, mode);
5858 if (target)
5859 return target;
5860 break;
5862 case BUILT_IN_SETJMP:
5863 target = expand_builtin_setjmp (arglist, target);
5864 if (target)
5865 return target;
5866 break;
5868 /* __builtin_longjmp is passed a pointer to an array of five words.
5869 It's similar to the C library longjmp function but works with
5870 __builtin_setjmp above. */
5871 case BUILT_IN_LONGJMP:
5872 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
5873 break;
5874 else
5876 rtx buf_addr = expand_expr (TREE_VALUE (arglist), subtarget,
5877 VOIDmode, 0);
5878 rtx value = expand_expr (TREE_VALUE (TREE_CHAIN (arglist)),
5879 NULL_RTX, VOIDmode, 0);
5881 if (value != const1_rtx)
5883 error ("__builtin_longjmp second argument must be 1");
5884 return const0_rtx;
5887 expand_builtin_longjmp (buf_addr, value);
5888 return const0_rtx;
5891 case BUILT_IN_NONLOCAL_GOTO:
5892 target = expand_builtin_nonlocal_goto (arglist);
5893 if (target)
5894 return target;
5895 break;
5897 /* This updates the setjmp buffer that is its argument with the value
5898 of the current stack pointer. */
5899 case BUILT_IN_UPDATE_SETJMP_BUF:
5900 if (validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
5902 rtx buf_addr
5903 = expand_expr (TREE_VALUE (arglist), NULL_RTX, VOIDmode, 0);
5905 expand_builtin_update_setjmp_buf (buf_addr);
5906 return const0_rtx;
5908 break;
5910 case BUILT_IN_TRAP:
5911 expand_builtin_trap ();
5912 return const0_rtx;
5914 case BUILT_IN_PRINTF:
5915 target = expand_builtin_printf (arglist, target, mode, false);
5916 if (target)
5917 return target;
5918 break;
5920 case BUILT_IN_PRINTF_UNLOCKED:
5921 target = expand_builtin_printf (arglist, target, mode, true);
5922 if (target)
5923 return target;
5924 break;
5926 case BUILT_IN_FPUTS:
5927 target = expand_builtin_fputs (arglist, target, false);
5928 if (target)
5929 return target;
5930 break;
5931 case BUILT_IN_FPUTS_UNLOCKED:
5932 target = expand_builtin_fputs (arglist, target, true);
5933 if (target)
5934 return target;
5935 break;
5937 case BUILT_IN_FPRINTF:
5938 target = expand_builtin_fprintf (arglist, target, mode, false);
5939 if (target)
5940 return target;
5941 break;
5943 case BUILT_IN_FPRINTF_UNLOCKED:
5944 target = expand_builtin_fprintf (arglist, target, mode, true);
5945 if (target)
5946 return target;
5947 break;
5949 case BUILT_IN_SPRINTF:
5950 target = expand_builtin_sprintf (arglist, target, mode);
5951 if (target)
5952 return target;
5953 break;
5955 case BUILT_IN_SIGNBIT:
5956 case BUILT_IN_SIGNBITF:
5957 case BUILT_IN_SIGNBITL:
5958 target = expand_builtin_signbit (exp, target);
5959 if (target)
5960 return target;
5961 break;
5963 /* Various hooks for the DWARF 2 __throw routine. */
5964 case BUILT_IN_UNWIND_INIT:
5965 expand_builtin_unwind_init ();
5966 return const0_rtx;
5967 case BUILT_IN_DWARF_CFA:
5968 return virtual_cfa_rtx;
5969 #ifdef DWARF2_UNWIND_INFO
5970 case BUILT_IN_DWARF_SP_COLUMN:
5971 return expand_builtin_dwarf_sp_column ();
5972 case BUILT_IN_INIT_DWARF_REG_SIZES:
5973 expand_builtin_init_dwarf_reg_sizes (TREE_VALUE (arglist));
5974 return const0_rtx;
5975 #endif
5976 case BUILT_IN_FROB_RETURN_ADDR:
5977 return expand_builtin_frob_return_addr (TREE_VALUE (arglist));
5978 case BUILT_IN_EXTRACT_RETURN_ADDR:
5979 return expand_builtin_extract_return_addr (TREE_VALUE (arglist));
5980 case BUILT_IN_EH_RETURN:
5981 expand_builtin_eh_return (TREE_VALUE (arglist),
5982 TREE_VALUE (TREE_CHAIN (arglist)));
5983 return const0_rtx;
5984 #ifdef EH_RETURN_DATA_REGNO
5985 case BUILT_IN_EH_RETURN_DATA_REGNO:
5986 return expand_builtin_eh_return_data_regno (arglist);
5987 #endif
5988 case BUILT_IN_EXTEND_POINTER:
5989 return expand_builtin_extend_pointer (TREE_VALUE (arglist));
5991 case BUILT_IN_VA_START:
5992 case BUILT_IN_STDARG_START:
5993 return expand_builtin_va_start (arglist);
5994 case BUILT_IN_VA_END:
5995 return expand_builtin_va_end (arglist);
5996 case BUILT_IN_VA_COPY:
5997 return expand_builtin_va_copy (arglist);
5998 case BUILT_IN_EXPECT:
5999 return expand_builtin_expect (arglist, target);
6000 case BUILT_IN_PREFETCH:
6001 expand_builtin_prefetch (arglist);
6002 return const0_rtx;
6004 case BUILT_IN_PROFILE_FUNC_ENTER:
6005 return expand_builtin_profile_func (false);
6006 case BUILT_IN_PROFILE_FUNC_EXIT:
6007 return expand_builtin_profile_func (true);
6009 case BUILT_IN_INIT_TRAMPOLINE:
6010 return expand_builtin_init_trampoline (arglist);
6011 case BUILT_IN_ADJUST_TRAMPOLINE:
6012 return expand_builtin_adjust_trampoline (arglist);
6014 case BUILT_IN_FORK:
6015 case BUILT_IN_EXECL:
6016 case BUILT_IN_EXECV:
6017 case BUILT_IN_EXECLP:
6018 case BUILT_IN_EXECLE:
6019 case BUILT_IN_EXECVP:
6020 case BUILT_IN_EXECVE:
6021 target = expand_builtin_fork_or_exec (fndecl, arglist, target, ignore);
6022 if (target)
6023 return target;
6024 break;
6026 default: /* just do library call, if unknown builtin */
6027 if (!DECL_ASSEMBLER_NAME_SET_P (fndecl))
6028 error ("built-in function `%s' not currently supported",
6029 IDENTIFIER_POINTER (DECL_NAME (fndecl)));
6032 /* The switch statement above can drop through to cause the function
6033 to be called normally. */
6034 return expand_call (exp, target, ignore);
6037 /* Determine whether a tree node represents a call to a built-in
6038 function. If the tree T is a call to a built-in function with
6039 the right number of arguments of the appropriate types, return
6040 the DECL_FUNCTION_CODE of the call, e.g. BUILT_IN_SQRT.
6041 Otherwise the return value is END_BUILTINS. */
6043 enum built_in_function
6044 builtin_mathfn_code (tree t)
6046 tree fndecl, arglist, parmlist;
6047 tree argtype, parmtype;
6049 if (TREE_CODE (t) != CALL_EXPR
6050 || TREE_CODE (TREE_OPERAND (t, 0)) != ADDR_EXPR)
6051 return END_BUILTINS;
6053 fndecl = get_callee_fndecl (t);
6054 if (fndecl == NULL_TREE
6055 || TREE_CODE (fndecl) != FUNCTION_DECL
6056 || ! DECL_BUILT_IN (fndecl)
6057 || DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
6058 return END_BUILTINS;
6060 arglist = TREE_OPERAND (t, 1);
6061 parmlist = TYPE_ARG_TYPES (TREE_TYPE (fndecl));
6062 for (; parmlist; parmlist = TREE_CHAIN (parmlist))
6064 /* If a function doesn't take a variable number of arguments,
6065 the last element in the list will have type `void'. */
6066 parmtype = TREE_VALUE (parmlist);
6067 if (VOID_TYPE_P (parmtype))
6069 if (arglist)
6070 return END_BUILTINS;
6071 return DECL_FUNCTION_CODE (fndecl);
6074 if (! arglist)
6075 return END_BUILTINS;
6077 argtype = TREE_TYPE (TREE_VALUE (arglist));
6079 if (SCALAR_FLOAT_TYPE_P (parmtype))
6081 if (! SCALAR_FLOAT_TYPE_P (argtype))
6082 return END_BUILTINS;
6084 else if (COMPLEX_FLOAT_TYPE_P (parmtype))
6086 if (! COMPLEX_FLOAT_TYPE_P (argtype))
6087 return END_BUILTINS;
6089 else if (POINTER_TYPE_P (parmtype))
6091 if (! POINTER_TYPE_P (argtype))
6092 return END_BUILTINS;
6094 else if (INTEGRAL_TYPE_P (parmtype))
6096 if (! INTEGRAL_TYPE_P (argtype))
6097 return END_BUILTINS;
6099 else
6100 return END_BUILTINS;
6102 arglist = TREE_CHAIN (arglist);
6105 /* Variable-length argument list. */
6106 return DECL_FUNCTION_CODE (fndecl);
6109 /* Fold a call to __builtin_constant_p, if we know it will evaluate to a
6110 constant. ARGLIST is the argument list of the call. */
6112 static tree
6113 fold_builtin_constant_p (tree arglist)
6115 if (arglist == 0)
6116 return 0;
6118 arglist = TREE_VALUE (arglist);
6120 /* We return 1 for a numeric type that's known to be a constant
6121 value at compile-time or for an aggregate type that's a
6122 literal constant. */
6123 STRIP_NOPS (arglist);
6125 /* If we know this is a constant, emit the constant of one. */
6126 if (TREE_CODE_CLASS (TREE_CODE (arglist)) == 'c'
6127 || (TREE_CODE (arglist) == CONSTRUCTOR
6128 && TREE_CONSTANT (arglist))
6129 || (TREE_CODE (arglist) == ADDR_EXPR
6130 && TREE_CODE (TREE_OPERAND (arglist, 0)) == STRING_CST))
6131 return integer_one_node;
6133 /* If this expression has side effects, show we don't know it to be a
6134 constant. Likewise if it's a pointer or aggregate type since in
6135 those case we only want literals, since those are only optimized
6136 when generating RTL, not later.
6137 And finally, if we are compiling an initializer, not code, we
6138 need to return a definite result now; there's not going to be any
6139 more optimization done. */
6140 if (TREE_SIDE_EFFECTS (arglist)
6141 || AGGREGATE_TYPE_P (TREE_TYPE (arglist))
6142 || POINTER_TYPE_P (TREE_TYPE (arglist))
6143 || cfun == 0)
6144 return integer_zero_node;
6146 return 0;
6149 /* Fold a call to __builtin_expect, if we expect that a comparison against
6150 the argument will fold to a constant. In practice, this means a true
6151 constant or the address of a non-weak symbol. ARGLIST is the argument
6152 list of the call. */
6154 static tree
6155 fold_builtin_expect (tree arglist)
6157 tree arg, inner;
6159 if (arglist == 0)
6160 return 0;
6162 arg = TREE_VALUE (arglist);
6164 /* If the argument isn't invariant, then there's nothing we can do. */
6165 if (!TREE_INVARIANT (arg))
6166 return 0;
6168 /* If we're looking at an address of a weak decl, then do not fold. */
6169 inner = arg;
6170 STRIP_NOPS (inner);
6171 if (TREE_CODE (inner) == ADDR_EXPR)
6175 inner = TREE_OPERAND (inner, 0);
6177 while (TREE_CODE (inner) == COMPONENT_REF
6178 || TREE_CODE (inner) == ARRAY_REF);
6179 if (DECL_P (inner) && DECL_WEAK (inner))
6180 return 0;
6183 /* Otherwise, ARG already has the proper type for the return value. */
6184 return arg;
6187 /* Fold a call to __builtin_classify_type. */
6189 static tree
6190 fold_builtin_classify_type (tree arglist)
6192 if (arglist == 0)
6193 return build_int_2 (no_type_class, 0);
6195 return build_int_2 (type_to_class (TREE_TYPE (TREE_VALUE (arglist))), 0);
6198 /* Fold a call to __builtin_inf or __builtin_huge_val. */
6200 static tree
6201 fold_builtin_inf (tree type, int warn)
6203 REAL_VALUE_TYPE real;
6205 if (!MODE_HAS_INFINITIES (TYPE_MODE (type)) && warn)
6206 warning ("target format does not support infinity");
6208 real_inf (&real);
6209 return build_real (type, real);
6212 /* Fold a call to __builtin_nan or __builtin_nans. */
6214 static tree
6215 fold_builtin_nan (tree arglist, tree type, int quiet)
6217 REAL_VALUE_TYPE real;
6218 const char *str;
6220 if (!validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
6221 return 0;
6222 str = c_getstr (TREE_VALUE (arglist));
6223 if (!str)
6224 return 0;
6226 if (!real_nan (&real, str, quiet, TYPE_MODE (type)))
6227 return 0;
6229 return build_real (type, real);
6232 /* Return true if the floating point expression T has an integer value.
6233 We also allow +Inf, -Inf and NaN to be considered integer values. */
6235 static bool
6236 integer_valued_real_p (tree t)
6238 switch (TREE_CODE (t))
6240 case FLOAT_EXPR:
6241 return true;
6243 case ABS_EXPR:
6244 case SAVE_EXPR:
6245 case NON_LVALUE_EXPR:
6246 return integer_valued_real_p (TREE_OPERAND (t, 0));
6248 case COMPOUND_EXPR:
6249 case MODIFY_EXPR:
6250 case BIND_EXPR:
6251 return integer_valued_real_p (TREE_OPERAND (t, 1));
6253 case PLUS_EXPR:
6254 case MINUS_EXPR:
6255 case MULT_EXPR:
6256 case MIN_EXPR:
6257 case MAX_EXPR:
6258 return integer_valued_real_p (TREE_OPERAND (t, 0))
6259 && integer_valued_real_p (TREE_OPERAND (t, 1));
6261 case COND_EXPR:
6262 return integer_valued_real_p (TREE_OPERAND (t, 1))
6263 && integer_valued_real_p (TREE_OPERAND (t, 2));
6265 case REAL_CST:
6266 if (! TREE_CONSTANT_OVERFLOW (t))
6268 REAL_VALUE_TYPE c, cint;
6270 c = TREE_REAL_CST (t);
6271 real_trunc (&cint, TYPE_MODE (TREE_TYPE (t)), &c);
6272 return real_identical (&c, &cint);
6275 case NOP_EXPR:
6277 tree type = TREE_TYPE (TREE_OPERAND (t, 0));
6278 if (TREE_CODE (type) == INTEGER_TYPE)
6279 return true;
6280 if (TREE_CODE (type) == REAL_TYPE)
6281 return integer_valued_real_p (TREE_OPERAND (t, 0));
6282 break;
6285 case CALL_EXPR:
6286 switch (builtin_mathfn_code (t))
6288 case BUILT_IN_CEIL:
6289 case BUILT_IN_CEILF:
6290 case BUILT_IN_CEILL:
6291 case BUILT_IN_FLOOR:
6292 case BUILT_IN_FLOORF:
6293 case BUILT_IN_FLOORL:
6294 case BUILT_IN_NEARBYINT:
6295 case BUILT_IN_NEARBYINTF:
6296 case BUILT_IN_NEARBYINTL:
6297 case BUILT_IN_RINT:
6298 case BUILT_IN_RINTF:
6299 case BUILT_IN_RINTL:
6300 case BUILT_IN_ROUND:
6301 case BUILT_IN_ROUNDF:
6302 case BUILT_IN_ROUNDL:
6303 case BUILT_IN_TRUNC:
6304 case BUILT_IN_TRUNCF:
6305 case BUILT_IN_TRUNCL:
6306 return true;
6308 default:
6309 break;
6311 break;
6313 default:
6314 break;
6316 return false;
6319 /* EXP is assumed to be builtin call where truncation can be propagated
6320 across (for instance floor((double)f) == (double)floorf (f).
6321 Do the transformation. */
6323 static tree
6324 fold_trunc_transparent_mathfn (tree exp)
6326 tree fndecl = get_callee_fndecl (exp);
6327 tree arglist = TREE_OPERAND (exp, 1);
6328 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
6329 tree arg;
6331 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6332 return 0;
6334 arg = TREE_VALUE (arglist);
6335 /* Integer rounding functions are idempotent. */
6336 if (fcode == builtin_mathfn_code (arg))
6337 return arg;
6339 /* If argument is already integer valued, and we don't need to worry
6340 about setting errno, there's no need to perform rounding. */
6341 if (! flag_errno_math && integer_valued_real_p (arg))
6342 return arg;
6344 if (optimize)
6346 tree arg0 = strip_float_extensions (arg);
6347 tree ftype = TREE_TYPE (exp);
6348 tree newtype = TREE_TYPE (arg0);
6349 tree decl;
6351 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
6352 && (decl = mathfn_built_in (newtype, fcode)))
6354 arglist =
6355 build_tree_list (NULL_TREE, fold_convert (newtype, arg0));
6356 return fold_convert (ftype,
6357 build_function_call_expr (decl, arglist));
6360 return 0;
6363 /* EXP is assumed to be builtin call which can narrow the FP type of
6364 the argument, for instance lround((double)f) -> lroundf (f). */
6366 static tree
6367 fold_fixed_mathfn (tree exp)
6369 tree fndecl = get_callee_fndecl (exp);
6370 tree arglist = TREE_OPERAND (exp, 1);
6371 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
6372 tree arg;
6374 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6375 return 0;
6377 arg = TREE_VALUE (arglist);
6379 /* If argument is already integer valued, and we don't need to worry
6380 about setting errno, there's no need to perform rounding. */
6381 if (! flag_errno_math && integer_valued_real_p (arg))
6382 return fold (build1 (FIX_TRUNC_EXPR, TREE_TYPE (exp), arg));
6384 if (optimize)
6386 tree ftype = TREE_TYPE (arg);
6387 tree arg0 = strip_float_extensions (arg);
6388 tree newtype = TREE_TYPE (arg0);
6389 tree decl;
6391 if (TYPE_PRECISION (newtype) < TYPE_PRECISION (ftype)
6392 && (decl = mathfn_built_in (newtype, fcode)))
6394 arglist =
6395 build_tree_list (NULL_TREE, fold_convert (newtype, arg0));
6396 return build_function_call_expr (decl, arglist);
6399 return 0;
6402 /* Fold function call to builtin cabs, cabsf or cabsl. ARGLIST
6403 is the argument list and TYPE is the return type. Return
6404 NULL_TREE if no if no simplification can be made. */
6406 static tree
6407 fold_builtin_cabs (tree arglist, tree type)
6409 tree arg;
6411 if (!arglist || TREE_CHAIN (arglist))
6412 return NULL_TREE;
6414 arg = TREE_VALUE (arglist);
6415 if (TREE_CODE (TREE_TYPE (arg)) != COMPLEX_TYPE
6416 || TREE_CODE (TREE_TYPE (TREE_TYPE (arg))) != REAL_TYPE)
6417 return NULL_TREE;
6419 /* Evaluate cabs of a constant at compile-time. */
6420 if (flag_unsafe_math_optimizations
6421 && TREE_CODE (arg) == COMPLEX_CST
6422 && TREE_CODE (TREE_REALPART (arg)) == REAL_CST
6423 && TREE_CODE (TREE_IMAGPART (arg)) == REAL_CST
6424 && ! TREE_CONSTANT_OVERFLOW (TREE_REALPART (arg))
6425 && ! TREE_CONSTANT_OVERFLOW (TREE_IMAGPART (arg)))
6427 REAL_VALUE_TYPE r, i;
6429 r = TREE_REAL_CST (TREE_REALPART (arg));
6430 i = TREE_REAL_CST (TREE_IMAGPART (arg));
6432 real_arithmetic (&r, MULT_EXPR, &r, &r);
6433 real_arithmetic (&i, MULT_EXPR, &i, &i);
6434 real_arithmetic (&r, PLUS_EXPR, &r, &i);
6435 if (real_sqrt (&r, TYPE_MODE (type), &r)
6436 || ! flag_trapping_math)
6437 return build_real (type, r);
6440 /* If either part is zero, cabs is fabs of the other. */
6441 if (TREE_CODE (arg) == COMPLEX_EXPR
6442 && real_zerop (TREE_OPERAND (arg, 0)))
6443 return fold (build1 (ABS_EXPR, type, TREE_OPERAND (arg, 1)));
6444 if (TREE_CODE (arg) == COMPLEX_EXPR
6445 && real_zerop (TREE_OPERAND (arg, 1)))
6446 return fold (build1 (ABS_EXPR, type, TREE_OPERAND (arg, 0)));
6448 if (flag_unsafe_math_optimizations)
6450 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
6452 if (sqrtfn != NULL_TREE)
6454 tree rpart, ipart, result, arglist;
6456 arg = builtin_save_expr (arg);
6458 rpart = fold (build1 (REALPART_EXPR, type, arg));
6459 ipart = fold (build1 (IMAGPART_EXPR, type, arg));
6461 rpart = builtin_save_expr (rpart);
6462 ipart = builtin_save_expr (ipart);
6464 result = fold (build2 (PLUS_EXPR, type,
6465 fold (build2 (MULT_EXPR, type,
6466 rpart, rpart)),
6467 fold (build2 (MULT_EXPR, type,
6468 ipart, ipart))));
6470 arglist = build_tree_list (NULL_TREE, result);
6471 return build_function_call_expr (sqrtfn, arglist);
6475 return NULL_TREE;
6478 /* Fold function call to builtin trunc, truncf or truncl. Return
6479 NULL_TREE if no simplification can be made. */
6481 static tree
6482 fold_builtin_trunc (tree exp)
6484 tree arglist = TREE_OPERAND (exp, 1);
6485 tree arg;
6487 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6488 return 0;
6490 /* Optimize trunc of constant value. */
6491 arg = TREE_VALUE (arglist);
6492 if (TREE_CODE (arg) == REAL_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6494 REAL_VALUE_TYPE r, x;
6495 tree type = TREE_TYPE (exp);
6497 x = TREE_REAL_CST (arg);
6498 real_trunc (&r, TYPE_MODE (type), &x);
6499 return build_real (type, r);
6502 return fold_trunc_transparent_mathfn (exp);
6505 /* Fold function call to builtin floor, floorf or floorl. Return
6506 NULL_TREE if no simplification can be made. */
6508 static tree
6509 fold_builtin_floor (tree exp)
6511 tree arglist = TREE_OPERAND (exp, 1);
6512 tree arg;
6514 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6515 return 0;
6517 /* Optimize floor of constant value. */
6518 arg = TREE_VALUE (arglist);
6519 if (TREE_CODE (arg) == REAL_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6521 REAL_VALUE_TYPE x;
6523 x = TREE_REAL_CST (arg);
6524 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
6526 tree type = TREE_TYPE (exp);
6527 REAL_VALUE_TYPE r;
6529 real_floor (&r, TYPE_MODE (type), &x);
6530 return build_real (type, r);
6534 return fold_trunc_transparent_mathfn (exp);
6537 /* Fold function call to builtin ceil, ceilf or ceill. Return
6538 NULL_TREE if no simplification can be made. */
6540 static tree
6541 fold_builtin_ceil (tree exp)
6543 tree arglist = TREE_OPERAND (exp, 1);
6544 tree arg;
6546 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6547 return 0;
6549 /* Optimize ceil of constant value. */
6550 arg = TREE_VALUE (arglist);
6551 if (TREE_CODE (arg) == REAL_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6553 REAL_VALUE_TYPE x;
6555 x = TREE_REAL_CST (arg);
6556 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
6558 tree type = TREE_TYPE (exp);
6559 REAL_VALUE_TYPE r;
6561 real_ceil (&r, TYPE_MODE (type), &x);
6562 return build_real (type, r);
6566 return fold_trunc_transparent_mathfn (exp);
6569 /* Fold function call to builtin round, roundf or roundl. Return
6570 NULL_TREE if no simplification can be made. */
6572 static tree
6573 fold_builtin_round (tree exp)
6575 tree arglist = TREE_OPERAND (exp, 1);
6576 tree arg;
6578 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6579 return 0;
6581 /* Optimize round of constant value. */
6582 arg = TREE_VALUE (arglist);
6583 if (TREE_CODE (arg) == REAL_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6585 REAL_VALUE_TYPE x;
6587 x = TREE_REAL_CST (arg);
6588 if (! REAL_VALUE_ISNAN (x) || ! flag_errno_math)
6590 tree type = TREE_TYPE (exp);
6591 REAL_VALUE_TYPE r;
6593 real_round (&r, TYPE_MODE (type), &x);
6594 return build_real (type, r);
6598 return fold_trunc_transparent_mathfn (exp);
6601 /* Fold function call to builtin lround, lroundf or lroundl (or the
6602 corresponding long long versions). Return NULL_TREE if no
6603 simplification can be made. */
6605 static tree
6606 fold_builtin_lround (tree exp)
6608 tree arglist = TREE_OPERAND (exp, 1);
6609 tree arg;
6611 if (! validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6612 return 0;
6614 /* Optimize lround of constant value. */
6615 arg = TREE_VALUE (arglist);
6616 if (TREE_CODE (arg) == REAL_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6618 const REAL_VALUE_TYPE x = TREE_REAL_CST (arg);
6620 if (! REAL_VALUE_ISNAN (x) && ! REAL_VALUE_ISINF (x))
6622 tree itype = TREE_TYPE (exp), ftype = TREE_TYPE (arg), result;
6623 HOST_WIDE_INT hi, lo;
6624 REAL_VALUE_TYPE r;
6626 real_round (&r, TYPE_MODE (ftype), &x);
6627 REAL_VALUE_TO_INT (&lo, &hi, r);
6628 result = build_int_2 (lo, hi);
6629 if (int_fits_type_p (result, itype))
6630 return fold_convert (itype, result);
6634 return fold_fixed_mathfn (exp);
6637 /* Fold function call to builtin ffs, clz, ctz, popcount and parity
6638 and their long and long long variants (i.e. ffsl and ffsll).
6639 Return NULL_TREE if no simplification can be made. */
6641 static tree
6642 fold_builtin_bitop (tree exp)
6644 tree fndecl = get_callee_fndecl (exp);
6645 tree arglist = TREE_OPERAND (exp, 1);
6646 tree arg;
6648 if (! validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
6649 return NULL_TREE;
6651 /* Optimize for constant argument. */
6652 arg = TREE_VALUE (arglist);
6653 if (TREE_CODE (arg) == INTEGER_CST && ! TREE_CONSTANT_OVERFLOW (arg))
6655 HOST_WIDE_INT hi, width, result;
6656 unsigned HOST_WIDE_INT lo;
6657 tree type, t;
6659 type = TREE_TYPE (arg);
6660 width = TYPE_PRECISION (type);
6661 lo = TREE_INT_CST_LOW (arg);
6663 /* Clear all the bits that are beyond the type's precision. */
6664 if (width > HOST_BITS_PER_WIDE_INT)
6666 hi = TREE_INT_CST_HIGH (arg);
6667 if (width < 2 * HOST_BITS_PER_WIDE_INT)
6668 hi &= ~((HOST_WIDE_INT) (-1) >> (width - HOST_BITS_PER_WIDE_INT));
6670 else
6672 hi = 0;
6673 if (width < HOST_BITS_PER_WIDE_INT)
6674 lo &= ~((unsigned HOST_WIDE_INT) (-1) << width);
6677 switch (DECL_FUNCTION_CODE (fndecl))
6679 case BUILT_IN_FFS:
6680 case BUILT_IN_FFSL:
6681 case BUILT_IN_FFSLL:
6682 if (lo != 0)
6683 result = exact_log2 (lo & -lo) + 1;
6684 else if (hi != 0)
6685 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi) + 1;
6686 else
6687 result = 0;
6688 break;
6690 case BUILT_IN_CLZ:
6691 case BUILT_IN_CLZL:
6692 case BUILT_IN_CLZLL:
6693 if (hi != 0)
6694 result = width - floor_log2 (hi) - 1 - HOST_BITS_PER_WIDE_INT;
6695 else if (lo != 0)
6696 result = width - floor_log2 (lo) - 1;
6697 else if (! CLZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
6698 result = width;
6699 break;
6701 case BUILT_IN_CTZ:
6702 case BUILT_IN_CTZL:
6703 case BUILT_IN_CTZLL:
6704 if (lo != 0)
6705 result = exact_log2 (lo & -lo);
6706 else if (hi != 0)
6707 result = HOST_BITS_PER_WIDE_INT + exact_log2 (hi & -hi);
6708 else if (! CTZ_DEFINED_VALUE_AT_ZERO (TYPE_MODE (type), result))
6709 result = width;
6710 break;
6712 case BUILT_IN_POPCOUNT:
6713 case BUILT_IN_POPCOUNTL:
6714 case BUILT_IN_POPCOUNTLL:
6715 result = 0;
6716 while (lo)
6717 result++, lo &= lo - 1;
6718 while (hi)
6719 result++, hi &= hi - 1;
6720 break;
6722 case BUILT_IN_PARITY:
6723 case BUILT_IN_PARITYL:
6724 case BUILT_IN_PARITYLL:
6725 result = 0;
6726 while (lo)
6727 result++, lo &= lo - 1;
6728 while (hi)
6729 result++, hi &= hi - 1;
6730 result &= 1;
6731 break;
6733 default:
6734 abort();
6737 t = build_int_2 (result, 0);
6738 TREE_TYPE (t) = TREE_TYPE (exp);
6739 return t;
6742 return NULL_TREE;
6745 /* Return true if EXPR is the real constant contained in VALUE. */
6747 static bool
6748 real_dconstp (tree expr, const REAL_VALUE_TYPE *value)
6750 STRIP_NOPS (expr);
6752 return ((TREE_CODE (expr) == REAL_CST
6753 && ! TREE_CONSTANT_OVERFLOW (expr)
6754 && REAL_VALUES_EQUAL (TREE_REAL_CST (expr), *value))
6755 || (TREE_CODE (expr) == COMPLEX_CST
6756 && real_dconstp (TREE_REALPART (expr), value)
6757 && real_zerop (TREE_IMAGPART (expr))));
6760 /* A subroutine of fold_builtin to fold the various logarithmic
6761 functions. EXP is the CALL_EXPR of a call to a builtin logN
6762 function. VALUE is the base of the logN function. */
6764 static tree
6765 fold_builtin_logarithm (tree exp, const REAL_VALUE_TYPE *value)
6767 tree arglist = TREE_OPERAND (exp, 1);
6769 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6771 tree fndecl = get_callee_fndecl (exp);
6772 tree type = TREE_TYPE (TREE_TYPE (fndecl));
6773 tree arg = TREE_VALUE (arglist);
6774 const enum built_in_function fcode = builtin_mathfn_code (arg);
6776 /* Optimize logN(1.0) = 0.0. */
6777 if (real_onep (arg))
6778 return build_real (type, dconst0);
6780 /* Optimize logN(N) = 1.0. If N can't be truncated to MODE
6781 exactly, then only do this if flag_unsafe_math_optimizations. */
6782 if (exact_real_truncate (TYPE_MODE (type), value)
6783 || flag_unsafe_math_optimizations)
6785 const REAL_VALUE_TYPE value_truncate =
6786 real_value_truncate (TYPE_MODE (type), *value);
6787 if (real_dconstp (arg, &value_truncate))
6788 return build_real (type, dconst1);
6791 /* Special case, optimize logN(expN(x)) = x. */
6792 if (flag_unsafe_math_optimizations
6793 && ((value == &dconste
6794 && (fcode == BUILT_IN_EXP
6795 || fcode == BUILT_IN_EXPF
6796 || fcode == BUILT_IN_EXPL))
6797 || (value == &dconst2
6798 && (fcode == BUILT_IN_EXP2
6799 || fcode == BUILT_IN_EXP2F
6800 || fcode == BUILT_IN_EXP2L))
6801 || (value == &dconst10 && (BUILTIN_EXP10_P (fcode)))))
6802 return fold_convert (type, TREE_VALUE (TREE_OPERAND (arg, 1)));
6804 /* Optimize logN(func()) for various exponential functions. We
6805 want to determine the value "x" and the power "exponent" in
6806 order to transform logN(x**exponent) into exponent*logN(x). */
6807 if (flag_unsafe_math_optimizations)
6809 tree exponent = 0, x = 0;
6811 switch (fcode)
6813 case BUILT_IN_EXP:
6814 case BUILT_IN_EXPF:
6815 case BUILT_IN_EXPL:
6816 /* Prepare to do logN(exp(exponent) -> exponent*logN(e). */
6817 x = build_real (type,
6818 real_value_truncate (TYPE_MODE (type), dconste));
6819 exponent = TREE_VALUE (TREE_OPERAND (arg, 1));
6820 break;
6821 case BUILT_IN_EXP2:
6822 case BUILT_IN_EXP2F:
6823 case BUILT_IN_EXP2L:
6824 /* Prepare to do logN(exp2(exponent) -> exponent*logN(2). */
6825 x = build_real (type, dconst2);
6826 exponent = TREE_VALUE (TREE_OPERAND (arg, 1));
6827 break;
6828 case BUILT_IN_EXP10:
6829 case BUILT_IN_EXP10F:
6830 case BUILT_IN_EXP10L:
6831 case BUILT_IN_POW10:
6832 case BUILT_IN_POW10F:
6833 case BUILT_IN_POW10L:
6834 /* Prepare to do logN(exp10(exponent) -> exponent*logN(10). */
6835 x = build_real (type, dconst10);
6836 exponent = TREE_VALUE (TREE_OPERAND (arg, 1));
6837 break;
6838 case BUILT_IN_SQRT:
6839 case BUILT_IN_SQRTF:
6840 case BUILT_IN_SQRTL:
6841 /* Prepare to do logN(sqrt(x) -> 0.5*logN(x). */
6842 x = TREE_VALUE (TREE_OPERAND (arg, 1));
6843 exponent = build_real (type, dconsthalf);
6844 break;
6845 case BUILT_IN_CBRT:
6846 case BUILT_IN_CBRTF:
6847 case BUILT_IN_CBRTL:
6848 /* Prepare to do logN(cbrt(x) -> (1/3)*logN(x). */
6849 x = TREE_VALUE (TREE_OPERAND (arg, 1));
6850 exponent = build_real (type, real_value_truncate (TYPE_MODE (type),
6851 dconstthird));
6852 break;
6853 case BUILT_IN_POW:
6854 case BUILT_IN_POWF:
6855 case BUILT_IN_POWL:
6856 /* Prepare to do logN(pow(x,exponent) -> exponent*logN(x). */
6857 x = TREE_VALUE (TREE_OPERAND (arg, 1));
6858 exponent = TREE_VALUE (TREE_CHAIN (TREE_OPERAND (arg, 1)));
6859 break;
6860 default:
6861 break;
6864 /* Now perform the optimization. */
6865 if (x && exponent)
6867 tree logfn;
6868 arglist = build_tree_list (NULL_TREE, x);
6869 logfn = build_function_call_expr (fndecl, arglist);
6870 return fold (build2 (MULT_EXPR, type, exponent, logfn));
6875 return 0;
6878 /* A subroutine of fold_builtin to fold the various exponent
6879 functions. EXP is the CALL_EXPR of a call to a builtin function.
6880 VALUE is the value which will be raised to a power. */
6882 static tree
6883 fold_builtin_exponent (tree exp, const REAL_VALUE_TYPE *value)
6885 tree arglist = TREE_OPERAND (exp, 1);
6887 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
6889 tree fndecl = get_callee_fndecl (exp);
6890 tree type = TREE_TYPE (TREE_TYPE (fndecl));
6891 tree arg = TREE_VALUE (arglist);
6893 /* Optimize exp*(0.0) = 1.0. */
6894 if (real_zerop (arg))
6895 return build_real (type, dconst1);
6897 /* Optimize expN(1.0) = N. */
6898 if (real_onep (arg))
6900 REAL_VALUE_TYPE cst;
6902 real_convert (&cst, TYPE_MODE (type), value);
6903 return build_real (type, cst);
6906 /* Attempt to evaluate expN(integer) at compile-time. */
6907 if (flag_unsafe_math_optimizations
6908 && TREE_CODE (arg) == REAL_CST
6909 && ! TREE_CONSTANT_OVERFLOW (arg))
6911 REAL_VALUE_TYPE cint;
6912 REAL_VALUE_TYPE c;
6913 HOST_WIDE_INT n;
6915 c = TREE_REAL_CST (arg);
6916 n = real_to_integer (&c);
6917 real_from_integer (&cint, VOIDmode, n,
6918 n < 0 ? -1 : 0, 0);
6919 if (real_identical (&c, &cint))
6921 REAL_VALUE_TYPE x;
6923 real_powi (&x, TYPE_MODE (type), value, n);
6924 return build_real (type, x);
6928 /* Optimize expN(logN(x)) = x. */
6929 if (flag_unsafe_math_optimizations)
6931 const enum built_in_function fcode = builtin_mathfn_code (arg);
6933 if ((value == &dconste
6934 && (fcode == BUILT_IN_LOG
6935 || fcode == BUILT_IN_LOGF
6936 || fcode == BUILT_IN_LOGL))
6937 || (value == &dconst2
6938 && (fcode == BUILT_IN_LOG2
6939 || fcode == BUILT_IN_LOG2F
6940 || fcode == BUILT_IN_LOG2L))
6941 || (value == &dconst10
6942 && (fcode == BUILT_IN_LOG10
6943 || fcode == BUILT_IN_LOG10F
6944 || fcode == BUILT_IN_LOG10L)))
6945 return fold_convert (type, TREE_VALUE (TREE_OPERAND (arg, 1)));
6949 return 0;
6952 /* Fold function call to builtin memcpy. Return
6953 NULL_TREE if no simplification can be made. */
6955 static tree
6956 fold_builtin_memcpy (tree exp)
6958 tree arglist = TREE_OPERAND (exp, 1);
6959 tree dest, src, len;
6961 if (!validate_arglist (arglist,
6962 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
6963 return 0;
6965 dest = TREE_VALUE (arglist);
6966 src = TREE_VALUE (TREE_CHAIN (arglist));
6967 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
6969 /* If the LEN parameter is zero, return DEST. */
6970 if (integer_zerop (len))
6971 return omit_one_operand (TREE_TYPE (exp), dest, src);
6973 /* If SRC and DEST are the same (and not volatile), return DEST. */
6974 if (operand_equal_p (src, dest, 0))
6975 return omit_one_operand (TREE_TYPE (exp), dest, len);
6977 return 0;
6980 /* Fold function call to builtin mempcpy. Return
6981 NULL_TREE if no simplification can be made. */
6983 static tree
6984 fold_builtin_mempcpy (tree exp)
6986 tree arglist = TREE_OPERAND (exp, 1);
6987 tree dest, src, len;
6989 if (!validate_arglist (arglist,
6990 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
6991 return 0;
6993 dest = TREE_VALUE (arglist);
6994 src = TREE_VALUE (TREE_CHAIN (arglist));
6995 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
6997 /* If the LEN parameter is zero, return DEST. */
6998 if (integer_zerop (len))
6999 return omit_one_operand (TREE_TYPE (exp), dest, src);
7001 /* If SRC and DEST are the same (and not volatile), return DEST+LEN. */
7002 if (operand_equal_p (src, dest, 0))
7004 tree temp = fold_convert (TREE_TYPE (dest), len);
7005 temp = fold (build2 (PLUS_EXPR, TREE_TYPE (dest), dest, temp));
7006 return fold_convert (TREE_TYPE (exp), temp);
7009 return 0;
7012 /* Fold function call to builtin memmove. Return
7013 NULL_TREE if no simplification can be made. */
7015 static tree
7016 fold_builtin_memmove (tree exp)
7018 tree arglist = TREE_OPERAND (exp, 1);
7019 tree dest, src, len;
7021 if (!validate_arglist (arglist,
7022 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
7023 return 0;
7025 dest = TREE_VALUE (arglist);
7026 src = TREE_VALUE (TREE_CHAIN (arglist));
7027 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7029 /* If the LEN parameter is zero, return DEST. */
7030 if (integer_zerop (len))
7031 return omit_one_operand (TREE_TYPE (exp), dest, src);
7033 /* If SRC and DEST are the same (and not volatile), return DEST. */
7034 if (operand_equal_p (src, dest, 0))
7035 return omit_one_operand (TREE_TYPE (exp), dest, len);
7037 return 0;
7040 /* Fold function call to builtin strcpy. Return
7041 NULL_TREE if no simplification can be made. */
7043 static tree
7044 fold_builtin_strcpy (tree exp)
7046 tree arglist = TREE_OPERAND (exp, 1);
7047 tree dest, src;
7049 if (!validate_arglist (arglist,
7050 POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
7051 return 0;
7053 dest = TREE_VALUE (arglist);
7054 src = TREE_VALUE (TREE_CHAIN (arglist));
7056 /* If SRC and DEST are the same (and not volatile), return DEST. */
7057 if (operand_equal_p (src, dest, 0))
7058 return fold_convert (TREE_TYPE (exp), dest);
7060 return 0;
7063 /* Fold function call to builtin strncpy. Return
7064 NULL_TREE if no simplification can be made. */
7066 static tree
7067 fold_builtin_strncpy (tree exp)
7069 tree arglist = TREE_OPERAND (exp, 1);
7070 tree dest, src, len;
7072 if (!validate_arglist (arglist,
7073 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
7074 return 0;
7076 dest = TREE_VALUE (arglist);
7077 src = TREE_VALUE (TREE_CHAIN (arglist));
7078 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7080 /* If the LEN parameter is zero, return DEST. */
7081 if (integer_zerop (len))
7082 return omit_one_operand (TREE_TYPE (exp), dest, src);
7084 return 0;
7087 /* Fold function call to builtin memcmp. Return
7088 NULL_TREE if no simplification can be made. */
7090 static tree
7091 fold_builtin_memcmp (tree exp)
7093 tree arglist = TREE_OPERAND (exp, 1);
7094 tree arg1, arg2, len;
7096 if (!validate_arglist (arglist,
7097 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
7098 return 0;
7100 arg1 = TREE_VALUE (arglist);
7101 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
7102 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7104 /* If the LEN parameter is zero, return zero. */
7105 if (integer_zerop (len))
7107 tree temp = omit_one_operand (TREE_TYPE (exp), integer_zero_node, arg2);
7108 return omit_one_operand (TREE_TYPE (exp), temp, arg1);
7111 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
7112 if (operand_equal_p (arg1, arg2, 0))
7113 return omit_one_operand (TREE_TYPE (exp), integer_zero_node, len);
7115 return 0;
7118 /* Fold function call to builtin strcmp. Return
7119 NULL_TREE if no simplification can be made. */
7121 static tree
7122 fold_builtin_strcmp (tree exp)
7124 tree arglist = TREE_OPERAND (exp, 1);
7125 tree arg1, arg2;
7126 const char *p1, *p2;
7128 if (!validate_arglist (arglist,
7129 POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
7130 return 0;
7132 arg1 = TREE_VALUE (arglist);
7133 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
7135 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
7136 if (operand_equal_p (arg1, arg2, 0))
7137 return fold_convert (TREE_TYPE (exp), integer_zero_node);
7139 p1 = c_getstr (arg1);
7140 p2 = c_getstr (arg2);
7142 if (p1 && p2)
7144 tree temp;
7145 const int i = strcmp (p1, p2);
7146 if (i < 0)
7147 temp = integer_minus_one_node;
7148 else if (i > 0)
7149 temp = integer_one_node;
7150 else
7151 temp = integer_zero_node;
7152 return fold_convert (TREE_TYPE (exp), temp);
7155 return 0;
7158 /* Fold function call to builtin strncmp. Return
7159 NULL_TREE if no simplification can be made. */
7161 static tree
7162 fold_builtin_strncmp (tree exp)
7164 tree arglist = TREE_OPERAND (exp, 1);
7165 tree arg1, arg2, len;
7166 const char *p1, *p2;
7168 if (!validate_arglist (arglist,
7169 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
7170 return 0;
7172 arg1 = TREE_VALUE (arglist);
7173 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
7174 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
7176 /* If the LEN parameter is zero, return zero. */
7177 if (integer_zerop (len))
7179 tree temp = omit_one_operand (TREE_TYPE (exp), integer_zero_node, arg2);
7180 return omit_one_operand (TREE_TYPE (exp), temp, arg1);
7183 /* If ARG1 and ARG2 are the same (and not volatile), return zero. */
7184 if (operand_equal_p (arg1, arg2, 0))
7185 return omit_one_operand (TREE_TYPE (exp), integer_zero_node, len);
7187 p1 = c_getstr (arg1);
7188 p2 = c_getstr (arg2);
7190 if (host_integerp (len, 1) && p1 && p2)
7192 tree temp;
7193 const int i = strncmp (p1, p2, tree_low_cst (len, 1));
7194 if (i < 0)
7195 temp = integer_minus_one_node;
7196 else if (i > 0)
7197 temp = integer_one_node;
7198 else
7199 temp = integer_zero_node;
7200 return fold_convert (TREE_TYPE (exp), temp);
7203 return 0;
7206 /* Fold function call to builtin signbit, signbitf or signbitl. Return
7207 NULL_TREE if no simplification can be made. */
7209 static tree
7210 fold_builtin_signbit (tree exp)
7212 tree arglist = TREE_OPERAND (exp, 1);
7213 tree arg, temp;
7215 if (!validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7216 return NULL_TREE;
7218 arg = TREE_VALUE (arglist);
7220 /* If ARG is a compile-time constant, determine the result. */
7221 if (TREE_CODE (arg) == REAL_CST
7222 && !TREE_CONSTANT_OVERFLOW (arg))
7224 REAL_VALUE_TYPE c;
7226 c = TREE_REAL_CST (arg);
7227 temp = REAL_VALUE_NEGATIVE (c) ? integer_one_node : integer_zero_node;
7228 return fold_convert (TREE_TYPE (exp), temp);
7231 /* If ARG is non-negative, the result is always zero. */
7232 if (tree_expr_nonnegative_p (arg))
7233 return omit_one_operand (TREE_TYPE (exp), integer_zero_node, arg);
7235 /* If ARG's format doesn't have signed zeros, return "arg < 0.0". */
7236 if (!HONOR_SIGNED_ZEROS (TYPE_MODE (TREE_TYPE (arg))))
7237 return fold (build2 (LT_EXPR, TREE_TYPE (exp), arg,
7238 build_real (TREE_TYPE (arg), dconst0)));
7240 return NULL_TREE;
7243 /* Fold a call to builtin isascii. */
7245 static tree
7246 fold_builtin_isascii (tree arglist)
7248 if (! validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
7249 return 0;
7250 else
7252 /* Transform isascii(c) -> ((c & ~0x7f) == 0). */
7253 tree arg = TREE_VALUE (arglist);
7255 arg = fold (build2 (EQ_EXPR, integer_type_node,
7256 build2 (BIT_AND_EXPR, integer_type_node, arg,
7257 build_int_2 (~ (unsigned HOST_WIDE_INT) 0x7f,
7258 ~ (HOST_WIDE_INT) 0)),
7259 integer_zero_node));
7261 if (in_gimple_form && !TREE_CONSTANT (arg))
7262 return NULL_TREE;
7263 else
7264 return arg;
7268 /* Fold a call to builtin toascii. */
7270 static tree
7271 fold_builtin_toascii (tree arglist)
7273 if (! validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
7274 return 0;
7275 else
7277 /* Transform toascii(c) -> (c & 0x7f). */
7278 tree arg = TREE_VALUE (arglist);
7280 return fold (build2 (BIT_AND_EXPR, integer_type_node, arg,
7281 build_int_2 (0x7f, 0)));
7285 /* Fold a call to builtin isdigit. */
7287 static tree
7288 fold_builtin_isdigit (tree arglist)
7290 if (! validate_arglist (arglist, INTEGER_TYPE, VOID_TYPE))
7291 return 0;
7292 else
7294 /* Transform isdigit(c) -> (unsigned)(c) - '0' <= 9. */
7295 /* According to the C standard, isdigit is unaffected by locale. */
7296 tree arg = TREE_VALUE (arglist);
7297 arg = fold_convert (unsigned_type_node, arg);
7298 arg = build2 (MINUS_EXPR, unsigned_type_node, arg,
7299 fold_convert (unsigned_type_node,
7300 build_int_2 (TARGET_DIGIT0, 0)));
7301 arg = build2 (LE_EXPR, integer_type_node, arg,
7302 fold_convert (unsigned_type_node, build_int_2 (9, 0)));
7303 arg = fold (arg);
7304 if (in_gimple_form && !TREE_CONSTANT (arg))
7305 return NULL_TREE;
7306 else
7307 return arg;
7311 /* Used by constant folding to eliminate some builtin calls early. EXP is
7312 the CALL_EXPR of a call to a builtin function. */
7314 static tree
7315 fold_builtin_1 (tree exp)
7317 tree fndecl = get_callee_fndecl (exp);
7318 tree arglist = TREE_OPERAND (exp, 1);
7319 tree type = TREE_TYPE (TREE_TYPE (fndecl));
7321 if (DECL_BUILT_IN_CLASS (fndecl) == BUILT_IN_MD)
7322 return 0;
7324 switch (DECL_FUNCTION_CODE (fndecl))
7326 case BUILT_IN_CONSTANT_P:
7327 return fold_builtin_constant_p (arglist);
7329 case BUILT_IN_EXPECT:
7330 return fold_builtin_expect (arglist);
7332 case BUILT_IN_CLASSIFY_TYPE:
7333 return fold_builtin_classify_type (arglist);
7335 case BUILT_IN_STRLEN:
7336 if (validate_arglist (arglist, POINTER_TYPE, VOID_TYPE))
7338 tree len = c_strlen (TREE_VALUE (arglist), 0);
7339 if (len)
7341 /* Convert from the internal "sizetype" type to "size_t". */
7342 if (size_type_node)
7343 len = fold_convert (size_type_node, len);
7344 return len;
7347 break;
7349 case BUILT_IN_FABS:
7350 case BUILT_IN_FABSF:
7351 case BUILT_IN_FABSL:
7352 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7353 return fold (build1 (ABS_EXPR, type, TREE_VALUE (arglist)));
7354 break;
7356 case BUILT_IN_CABS:
7357 case BUILT_IN_CABSF:
7358 case BUILT_IN_CABSL:
7359 return fold_builtin_cabs (arglist, type);
7361 case BUILT_IN_SQRT:
7362 case BUILT_IN_SQRTF:
7363 case BUILT_IN_SQRTL:
7364 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7366 enum built_in_function fcode;
7367 tree arg = TREE_VALUE (arglist);
7369 /* Optimize sqrt of constant value. */
7370 if (TREE_CODE (arg) == REAL_CST
7371 && ! TREE_CONSTANT_OVERFLOW (arg))
7373 REAL_VALUE_TYPE r, x;
7375 x = TREE_REAL_CST (arg);
7376 if (real_sqrt (&r, TYPE_MODE (type), &x)
7377 || (!flag_trapping_math && !flag_errno_math))
7378 return build_real (type, r);
7381 /* Optimize sqrt(expN(x)) = expN(x*0.5). */
7382 fcode = builtin_mathfn_code (arg);
7383 if (flag_unsafe_math_optimizations && BUILTIN_EXPONENT_P (fcode))
7385 tree expfn = TREE_OPERAND (TREE_OPERAND (arg, 0), 0);
7386 arg = fold (build2 (MULT_EXPR, type,
7387 TREE_VALUE (TREE_OPERAND (arg, 1)),
7388 build_real (type, dconsthalf)));
7389 arglist = build_tree_list (NULL_TREE, arg);
7390 return build_function_call_expr (expfn, arglist);
7393 /* Optimize sqrt(Nroot(x)) -> pow(x,1/(2*N)). */
7394 if (flag_unsafe_math_optimizations && BUILTIN_ROOT_P (fcode))
7396 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7398 if (powfn)
7400 tree arg0 = TREE_VALUE (TREE_OPERAND (arg, 1));
7401 tree tree_root;
7402 /* The inner root was either sqrt or cbrt. */
7403 REAL_VALUE_TYPE dconstroot =
7404 BUILTIN_SQRT_P (fcode) ? dconsthalf : dconstthird;
7406 /* Adjust for the outer root. */
7407 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7408 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7409 tree_root = build_real (type, dconstroot);
7410 arglist = tree_cons (NULL_TREE, arg0,
7411 build_tree_list (NULL_TREE, tree_root));
7412 return build_function_call_expr (powfn, arglist);
7416 /* Optimize sqrt(pow(x,y)) = pow(x,y*0.5). */
7417 if (flag_unsafe_math_optimizations
7418 && (fcode == BUILT_IN_POW
7419 || fcode == BUILT_IN_POWF
7420 || fcode == BUILT_IN_POWL))
7422 tree powfn = TREE_OPERAND (TREE_OPERAND (arg, 0), 0);
7423 tree arg0 = TREE_VALUE (TREE_OPERAND (arg, 1));
7424 tree arg1 = TREE_VALUE (TREE_CHAIN (TREE_OPERAND (arg, 1)));
7425 tree narg1 = fold (build2 (MULT_EXPR, type, arg1,
7426 build_real (type, dconsthalf)));
7427 arglist = tree_cons (NULL_TREE, arg0,
7428 build_tree_list (NULL_TREE, narg1));
7429 return build_function_call_expr (powfn, arglist);
7432 break;
7434 case BUILT_IN_CBRT:
7435 case BUILT_IN_CBRTF:
7436 case BUILT_IN_CBRTL:
7437 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7439 tree arg = TREE_VALUE (arglist);
7440 const enum built_in_function fcode = builtin_mathfn_code (arg);
7442 /* Optimize cbrt of constant value. */
7443 if (real_zerop (arg) || real_onep (arg) || real_minus_onep (arg))
7444 return arg;
7446 /* Optimize cbrt(expN(x)) -> expN(x/3). */
7447 if (flag_unsafe_math_optimizations && BUILTIN_EXPONENT_P (fcode))
7449 tree expfn = TREE_OPERAND (TREE_OPERAND (arg, 0), 0);
7450 const REAL_VALUE_TYPE third_trunc =
7451 real_value_truncate (TYPE_MODE (type), dconstthird);
7452 arg = fold (build2 (MULT_EXPR, type,
7453 TREE_VALUE (TREE_OPERAND (arg, 1)),
7454 build_real (type, third_trunc)));
7455 arglist = build_tree_list (NULL_TREE, arg);
7456 return build_function_call_expr (expfn, arglist);
7459 /* Optimize cbrt(sqrt(x)) -> pow(x,1/6). */
7460 /* We don't optimize cbrt(cbrt(x)) -> pow(x,1/9) because if
7461 x is negative pow will error but cbrt won't. */
7462 if (flag_unsafe_math_optimizations && BUILTIN_SQRT_P (fcode))
7464 tree powfn = mathfn_built_in (type, BUILT_IN_POW);
7466 if (powfn)
7468 tree arg0 = TREE_VALUE (TREE_OPERAND (arg, 1));
7469 tree tree_root;
7470 REAL_VALUE_TYPE dconstroot = dconstthird;
7472 SET_REAL_EXP (&dconstroot, REAL_EXP (&dconstroot) - 1);
7473 dconstroot = real_value_truncate (TYPE_MODE (type), dconstroot);
7474 tree_root = build_real (type, dconstroot);
7475 arglist = tree_cons (NULL_TREE, arg0,
7476 build_tree_list (NULL_TREE, tree_root));
7477 return build_function_call_expr (powfn, arglist);
7482 break;
7484 case BUILT_IN_SIN:
7485 case BUILT_IN_SINF:
7486 case BUILT_IN_SINL:
7487 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7489 tree arg = TREE_VALUE (arglist);
7491 /* Optimize sin(0.0) = 0.0. */
7492 if (real_zerop (arg))
7493 return arg;
7495 break;
7497 case BUILT_IN_COS:
7498 case BUILT_IN_COSF:
7499 case BUILT_IN_COSL:
7500 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7502 tree arg = TREE_VALUE (arglist);
7504 /* Optimize cos(0.0) = 1.0. */
7505 if (real_zerop (arg))
7506 return build_real (type, dconst1);
7508 /* Optimize cos(-x) into cos(x). */
7509 if (TREE_CODE (arg) == NEGATE_EXPR)
7511 tree arglist = build_tree_list (NULL_TREE,
7512 TREE_OPERAND (arg, 0));
7513 return build_function_call_expr (fndecl, arglist);
7516 break;
7518 case BUILT_IN_EXP:
7519 case BUILT_IN_EXPF:
7520 case BUILT_IN_EXPL:
7521 return fold_builtin_exponent (exp, &dconste);
7522 case BUILT_IN_EXP2:
7523 case BUILT_IN_EXP2F:
7524 case BUILT_IN_EXP2L:
7525 return fold_builtin_exponent (exp, &dconst2);
7526 case BUILT_IN_EXP10:
7527 case BUILT_IN_EXP10F:
7528 case BUILT_IN_EXP10L:
7529 case BUILT_IN_POW10:
7530 case BUILT_IN_POW10F:
7531 case BUILT_IN_POW10L:
7532 return fold_builtin_exponent (exp, &dconst10);
7533 case BUILT_IN_LOG:
7534 case BUILT_IN_LOGF:
7535 case BUILT_IN_LOGL:
7536 return fold_builtin_logarithm (exp, &dconste);
7537 break;
7538 case BUILT_IN_LOG2:
7539 case BUILT_IN_LOG2F:
7540 case BUILT_IN_LOG2L:
7541 return fold_builtin_logarithm (exp, &dconst2);
7542 break;
7543 case BUILT_IN_LOG10:
7544 case BUILT_IN_LOG10F:
7545 case BUILT_IN_LOG10L:
7546 return fold_builtin_logarithm (exp, &dconst10);
7547 break;
7549 case BUILT_IN_TAN:
7550 case BUILT_IN_TANF:
7551 case BUILT_IN_TANL:
7552 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7554 enum built_in_function fcode;
7555 tree arg = TREE_VALUE (arglist);
7557 /* Optimize tan(0.0) = 0.0. */
7558 if (real_zerop (arg))
7559 return arg;
7561 /* Optimize tan(atan(x)) = x. */
7562 fcode = builtin_mathfn_code (arg);
7563 if (flag_unsafe_math_optimizations
7564 && (fcode == BUILT_IN_ATAN
7565 || fcode == BUILT_IN_ATANF
7566 || fcode == BUILT_IN_ATANL))
7567 return TREE_VALUE (TREE_OPERAND (arg, 1));
7569 break;
7571 case BUILT_IN_ATAN:
7572 case BUILT_IN_ATANF:
7573 case BUILT_IN_ATANL:
7574 if (validate_arglist (arglist, REAL_TYPE, VOID_TYPE))
7576 tree arg = TREE_VALUE (arglist);
7578 /* Optimize atan(0.0) = 0.0. */
7579 if (real_zerop (arg))
7580 return arg;
7582 /* Optimize atan(1.0) = pi/4. */
7583 if (real_onep (arg))
7585 REAL_VALUE_TYPE cst;
7587 real_convert (&cst, TYPE_MODE (type), &dconstpi);
7588 SET_REAL_EXP (&cst, REAL_EXP (&cst) - 2);
7589 return build_real (type, cst);
7592 break;
7594 case BUILT_IN_POW:
7595 case BUILT_IN_POWF:
7596 case BUILT_IN_POWL:
7597 if (validate_arglist (arglist, REAL_TYPE, REAL_TYPE, VOID_TYPE))
7599 enum built_in_function fcode;
7600 tree arg0 = TREE_VALUE (arglist);
7601 tree arg1 = TREE_VALUE (TREE_CHAIN (arglist));
7603 /* Optimize pow(1.0,y) = 1.0. */
7604 if (real_onep (arg0))
7605 return omit_one_operand (type, build_real (type, dconst1), arg1);
7607 if (TREE_CODE (arg1) == REAL_CST
7608 && ! TREE_CONSTANT_OVERFLOW (arg1))
7610 REAL_VALUE_TYPE c;
7611 c = TREE_REAL_CST (arg1);
7613 /* Optimize pow(x,0.0) = 1.0. */
7614 if (REAL_VALUES_EQUAL (c, dconst0))
7615 return omit_one_operand (type, build_real (type, dconst1),
7616 arg0);
7618 /* Optimize pow(x,1.0) = x. */
7619 if (REAL_VALUES_EQUAL (c, dconst1))
7620 return arg0;
7622 /* Optimize pow(x,-1.0) = 1.0/x. */
7623 if (REAL_VALUES_EQUAL (c, dconstm1))
7624 return fold (build2 (RDIV_EXPR, type,
7625 build_real (type, dconst1), arg0));
7627 /* Optimize pow(x,0.5) = sqrt(x). */
7628 if (flag_unsafe_math_optimizations
7629 && REAL_VALUES_EQUAL (c, dconsthalf))
7631 tree sqrtfn = mathfn_built_in (type, BUILT_IN_SQRT);
7633 if (sqrtfn != NULL_TREE)
7635 tree arglist = build_tree_list (NULL_TREE, arg0);
7636 return build_function_call_expr (sqrtfn, arglist);
7640 /* Attempt to evaluate pow at compile-time. */
7641 if (TREE_CODE (arg0) == REAL_CST
7642 && ! TREE_CONSTANT_OVERFLOW (arg0))
7644 REAL_VALUE_TYPE cint;
7645 HOST_WIDE_INT n;
7647 n = real_to_integer (&c);
7648 real_from_integer (&cint, VOIDmode, n,
7649 n < 0 ? -1 : 0, 0);
7650 if (real_identical (&c, &cint))
7652 REAL_VALUE_TYPE x;
7653 bool inexact;
7655 x = TREE_REAL_CST (arg0);
7656 inexact = real_powi (&x, TYPE_MODE (type), &x, n);
7657 if (flag_unsafe_math_optimizations || !inexact)
7658 return build_real (type, x);
7663 /* Optimize pow(expN(x),y) = expN(x*y). */
7664 fcode = builtin_mathfn_code (arg0);
7665 if (flag_unsafe_math_optimizations && BUILTIN_EXPONENT_P (fcode))
7667 tree expfn = TREE_OPERAND (TREE_OPERAND (arg0, 0), 0);
7668 tree arg = TREE_VALUE (TREE_OPERAND (arg0, 1));
7669 arg = fold (build2 (MULT_EXPR, type, arg, arg1));
7670 arglist = build_tree_list (NULL_TREE, arg);
7671 return build_function_call_expr (expfn, arglist);
7674 /* Optimize pow(sqrt(x),y) = pow(x,y*0.5). */
7675 if (flag_unsafe_math_optimizations && BUILTIN_SQRT_P (fcode))
7677 tree narg0 = TREE_VALUE (TREE_OPERAND (arg0, 1));
7678 tree narg1 = fold (build2 (MULT_EXPR, type, arg1,
7679 build_real (type, dconsthalf)));
7681 arglist = tree_cons (NULL_TREE, narg0,
7682 build_tree_list (NULL_TREE, narg1));
7683 return build_function_call_expr (fndecl, arglist);
7686 /* Optimize pow(pow(x,y),z) = pow(x,y*z). */
7687 if (flag_unsafe_math_optimizations
7688 && (fcode == BUILT_IN_POW
7689 || fcode == BUILT_IN_POWF
7690 || fcode == BUILT_IN_POWL))
7692 tree arg00 = TREE_VALUE (TREE_OPERAND (arg0, 1));
7693 tree arg01 = TREE_VALUE (TREE_CHAIN (TREE_OPERAND (arg0, 1)));
7694 tree narg1 = fold (build2 (MULT_EXPR, type, arg01, arg1));
7695 arglist = tree_cons (NULL_TREE, arg00,
7696 build_tree_list (NULL_TREE, narg1));
7697 return build_function_call_expr (fndecl, arglist);
7700 break;
7702 case BUILT_IN_INF:
7703 case BUILT_IN_INFF:
7704 case BUILT_IN_INFL:
7705 return fold_builtin_inf (type, true);
7707 case BUILT_IN_HUGE_VAL:
7708 case BUILT_IN_HUGE_VALF:
7709 case BUILT_IN_HUGE_VALL:
7710 return fold_builtin_inf (type, false);
7712 case BUILT_IN_NAN:
7713 case BUILT_IN_NANF:
7714 case BUILT_IN_NANL:
7715 return fold_builtin_nan (arglist, type, true);
7717 case BUILT_IN_NANS:
7718 case BUILT_IN_NANSF:
7719 case BUILT_IN_NANSL:
7720 return fold_builtin_nan (arglist, type, false);
7722 case BUILT_IN_FLOOR:
7723 case BUILT_IN_FLOORF:
7724 case BUILT_IN_FLOORL:
7725 return fold_builtin_floor (exp);
7727 case BUILT_IN_CEIL:
7728 case BUILT_IN_CEILF:
7729 case BUILT_IN_CEILL:
7730 return fold_builtin_ceil (exp);
7732 case BUILT_IN_TRUNC:
7733 case BUILT_IN_TRUNCF:
7734 case BUILT_IN_TRUNCL:
7735 return fold_builtin_trunc (exp);
7737 case BUILT_IN_ROUND:
7738 case BUILT_IN_ROUNDF:
7739 case BUILT_IN_ROUNDL:
7740 return fold_builtin_round (exp);
7742 case BUILT_IN_NEARBYINT:
7743 case BUILT_IN_NEARBYINTF:
7744 case BUILT_IN_NEARBYINTL:
7745 case BUILT_IN_RINT:
7746 case BUILT_IN_RINTF:
7747 case BUILT_IN_RINTL:
7748 return fold_trunc_transparent_mathfn (exp);
7750 case BUILT_IN_LROUND:
7751 case BUILT_IN_LROUNDF:
7752 case BUILT_IN_LROUNDL:
7753 case BUILT_IN_LLROUND:
7754 case BUILT_IN_LLROUNDF:
7755 case BUILT_IN_LLROUNDL:
7756 return fold_builtin_lround (exp);
7758 case BUILT_IN_LRINT:
7759 case BUILT_IN_LRINTF:
7760 case BUILT_IN_LRINTL:
7761 case BUILT_IN_LLRINT:
7762 case BUILT_IN_LLRINTF:
7763 case BUILT_IN_LLRINTL:
7764 return fold_fixed_mathfn (exp);
7766 case BUILT_IN_FFS:
7767 case BUILT_IN_FFSL:
7768 case BUILT_IN_FFSLL:
7769 case BUILT_IN_CLZ:
7770 case BUILT_IN_CLZL:
7771 case BUILT_IN_CLZLL:
7772 case BUILT_IN_CTZ:
7773 case BUILT_IN_CTZL:
7774 case BUILT_IN_CTZLL:
7775 case BUILT_IN_POPCOUNT:
7776 case BUILT_IN_POPCOUNTL:
7777 case BUILT_IN_POPCOUNTLL:
7778 case BUILT_IN_PARITY:
7779 case BUILT_IN_PARITYL:
7780 case BUILT_IN_PARITYLL:
7781 return fold_builtin_bitop (exp);
7783 case BUILT_IN_MEMCPY:
7784 return fold_builtin_memcpy (exp);
7786 case BUILT_IN_MEMPCPY:
7787 return fold_builtin_mempcpy (exp);
7789 case BUILT_IN_MEMMOVE:
7790 return fold_builtin_memmove (exp);
7792 case BUILT_IN_STRCPY:
7793 return fold_builtin_strcpy (exp);
7795 case BUILT_IN_STRNCPY:
7796 return fold_builtin_strncpy (exp);
7798 case BUILT_IN_MEMCMP:
7799 return fold_builtin_memcmp (exp);
7801 case BUILT_IN_STRCMP:
7802 return fold_builtin_strcmp (exp);
7804 case BUILT_IN_STRNCMP:
7805 return fold_builtin_strncmp (exp);
7807 case BUILT_IN_SIGNBIT:
7808 case BUILT_IN_SIGNBITF:
7809 case BUILT_IN_SIGNBITL:
7810 return fold_builtin_signbit (exp);
7812 case BUILT_IN_ISASCII:
7813 return fold_builtin_isascii (arglist);
7815 case BUILT_IN_TOASCII:
7816 return fold_builtin_toascii (arglist);
7818 case BUILT_IN_ISDIGIT:
7819 return fold_builtin_isdigit (arglist);
7821 default:
7822 break;
7825 return 0;
7828 /* A wrapper function for builtin folding that prevents warnings for
7829 "statement without effect" and the like, caused by removing the
7830 call node earlier than the warning is generated. */
7832 tree
7833 fold_builtin (tree exp)
7835 exp = fold_builtin_1 (exp);
7836 if (exp)
7838 /* ??? Don't clobber shared nodes such as integer_zero_node. */
7839 if (TREE_CODE_CLASS (TREE_CODE (exp)) == 'c')
7840 exp = build1 (NOP_EXPR, TREE_TYPE (exp), exp);
7841 TREE_NO_WARNING (exp) = 1;
7843 return exp;
7846 /* Conveniently construct a function call expression. */
7848 tree
7849 build_function_call_expr (tree fn, tree arglist)
7851 tree call_expr;
7853 call_expr = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (fn)), fn);
7854 call_expr = build3 (CALL_EXPR, TREE_TYPE (TREE_TYPE (fn)),
7855 call_expr, arglist, NULL_TREE);
7856 return fold (call_expr);
7859 /* This function validates the types of a function call argument list
7860 represented as a tree chain of parameters against a specified list
7861 of tree_codes. If the last specifier is a 0, that represents an
7862 ellipses, otherwise the last specifier must be a VOID_TYPE. */
7864 static int
7865 validate_arglist (tree arglist, ...)
7867 enum tree_code code;
7868 int res = 0;
7869 va_list ap;
7871 va_start (ap, arglist);
7875 code = va_arg (ap, enum tree_code);
7876 switch (code)
7878 case 0:
7879 /* This signifies an ellipses, any further arguments are all ok. */
7880 res = 1;
7881 goto end;
7882 case VOID_TYPE:
7883 /* This signifies an endlink, if no arguments remain, return
7884 true, otherwise return false. */
7885 res = arglist == 0;
7886 goto end;
7887 default:
7888 /* If no parameters remain or the parameter's code does not
7889 match the specified code, return false. Otherwise continue
7890 checking any remaining arguments. */
7891 if (arglist == 0
7892 || code != TREE_CODE (TREE_TYPE (TREE_VALUE (arglist))))
7893 goto end;
7894 break;
7896 arglist = TREE_CHAIN (arglist);
7898 while (1);
7900 /* We need gotos here since we can only have one VA_CLOSE in a
7901 function. */
7902 end: ;
7903 va_end (ap);
7905 return res;
7908 /* Default target-specific builtin expander that does nothing. */
7911 default_expand_builtin (tree exp ATTRIBUTE_UNUSED,
7912 rtx target ATTRIBUTE_UNUSED,
7913 rtx subtarget ATTRIBUTE_UNUSED,
7914 enum machine_mode mode ATTRIBUTE_UNUSED,
7915 int ignore ATTRIBUTE_UNUSED)
7917 return NULL_RTX;
7920 /* Returns true is EXP represents data that would potentially reside
7921 in a readonly section. */
7923 static bool
7924 readonly_data_expr (tree exp)
7926 STRIP_NOPS (exp);
7928 if (TREE_CODE (exp) == ADDR_EXPR)
7929 return decl_readonly_section (TREE_OPERAND (exp, 0), 0);
7930 else
7931 return false;
7934 /* Front-end to the simplify_builtin_XXX routines.
7936 EXP is a call to a builtin function. If possible try to simplify
7937 that into a constant, expression or call to a more efficient
7938 builtin function.
7940 If IGNORE is nonzero, then the result of this builtin function
7941 call is ignored.
7943 If simplification is possible, return the simplified tree, otherwise
7944 return NULL_TREE. */
7946 tree
7947 simplify_builtin (tree exp, int ignore)
7949 tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
7950 tree arglist = TREE_OPERAND (exp, 1);
7951 enum built_in_function fcode = DECL_FUNCTION_CODE (fndecl);
7952 tree val;
7954 switch (fcode)
7956 case BUILT_IN_FPUTS:
7957 val = simplify_builtin_fputs (arglist, ignore, 0, NULL_TREE);
7958 break;
7959 case BUILT_IN_FPUTS_UNLOCKED:
7960 val = simplify_builtin_fputs (arglist, ignore, 1, NULL_TREE);
7961 break;
7962 case BUILT_IN_STRSTR:
7963 val = simplify_builtin_strstr (arglist);
7964 break;
7965 case BUILT_IN_STRCAT:
7966 val = simplify_builtin_strcat (arglist);
7967 break;
7968 case BUILT_IN_STRNCAT:
7969 val = simplify_builtin_strncat (arglist);
7970 break;
7971 case BUILT_IN_STRSPN:
7972 val = simplify_builtin_strspn (arglist);
7973 break;
7974 case BUILT_IN_STRCSPN:
7975 val = simplify_builtin_strcspn (arglist);
7976 break;
7977 case BUILT_IN_STRCHR:
7978 case BUILT_IN_INDEX:
7979 val = simplify_builtin_strchr (arglist);
7980 break;
7981 case BUILT_IN_STRRCHR:
7982 case BUILT_IN_RINDEX:
7983 val = simplify_builtin_strrchr (arglist);
7984 break;
7985 case BUILT_IN_STRCPY:
7986 val = simplify_builtin_strcpy (arglist, NULL_TREE);
7987 break;
7988 case BUILT_IN_STRNCPY:
7989 val = simplify_builtin_strncpy (arglist, NULL_TREE);
7990 break;
7991 case BUILT_IN_STRCMP:
7992 val = simplify_builtin_strcmp (arglist);
7993 break;
7994 case BUILT_IN_STRNCMP:
7995 val = simplify_builtin_strncmp (arglist);
7996 break;
7997 case BUILT_IN_STRPBRK:
7998 val = simplify_builtin_strpbrk (arglist);
7999 break;
8000 case BUILT_IN_BCMP:
8001 case BUILT_IN_MEMCMP:
8002 val = simplify_builtin_memcmp (arglist);
8003 break;
8004 case BUILT_IN_VA_START:
8005 simplify_builtin_va_start (arglist);
8006 val = NULL_TREE;
8007 break;
8008 case BUILT_IN_SPRINTF:
8009 val = simplify_builtin_sprintf (arglist, ignore);
8010 break;
8011 case BUILT_IN_CONSTANT_P:
8012 val = fold_builtin_constant_p (arglist);
8013 /* Gimplification will pull the CALL_EXPR for the builtin out of
8014 an if condition. When not optimizing, we'll not CSE it back.
8015 To avoid link error types of regressions, return false now. */
8016 if (!val && !optimize)
8017 val = integer_zero_node;
8018 break;
8019 default:
8020 val = NULL_TREE;
8021 break;
8024 if (val)
8025 val = fold_convert (TREE_TYPE (exp), val);
8026 return val;
8029 /* Simplify a call to the strstr builtin.
8031 Return 0 if no simplification was possible, otherwise return the
8032 simplified form of the call as a tree.
8034 The simplified form may be a constant or other expression which
8035 computes the same value, but in a more efficient manner (including
8036 calls to other builtin functions).
8038 The call may contain arguments which need to be evaluated, but
8039 which are not useful to determine the result of the call. In
8040 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8041 COMPOUND_EXPR will be an argument which must be evaluated.
8042 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8043 COMPOUND_EXPR in the chain will contain the tree for the simplified
8044 form of the builtin function call. */
8046 static tree
8047 simplify_builtin_strstr (tree arglist)
8049 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8050 return 0;
8051 else
8053 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8054 tree fn;
8055 const char *p1, *p2;
8057 p2 = c_getstr (s2);
8058 if (p2 == NULL)
8059 return 0;
8061 p1 = c_getstr (s1);
8062 if (p1 != NULL)
8064 const char *r = strstr (p1, p2);
8066 if (r == NULL)
8067 return fold_convert (TREE_TYPE (s1), integer_zero_node);
8069 /* Return an offset into the constant string argument. */
8070 return fold (build2 (PLUS_EXPR, TREE_TYPE (s1),
8071 s1, fold_convert (TREE_TYPE (s1),
8072 ssize_int (r - p1))));
8075 if (p2[0] == '\0')
8076 return s1;
8078 if (p2[1] != '\0')
8079 return 0;
8081 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
8082 if (!fn)
8083 return 0;
8085 /* New argument list transforming strstr(s1, s2) to
8086 strchr(s1, s2[0]). */
8087 arglist = build_tree_list (NULL_TREE, build_int_2 (p2[0], 0));
8088 arglist = tree_cons (NULL_TREE, s1, arglist);
8089 return build_function_call_expr (fn, arglist);
8093 /* Simplify a call to the strstr builtin.
8095 Return 0 if no simplification was possible, otherwise return the
8096 simplified form of the call as a tree.
8098 The simplified form may be a constant or other expression which
8099 computes the same value, but in a more efficient manner (including
8100 calls to other builtin functions).
8102 The call may contain arguments which need to be evaluated, but
8103 which are not useful to determine the result of the call. In
8104 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8105 COMPOUND_EXPR will be an argument which must be evaluated.
8106 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8107 COMPOUND_EXPR in the chain will contain the tree for the simplified
8108 form of the builtin function call. */
8110 static tree
8111 simplify_builtin_strchr (tree arglist)
8113 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8114 return 0;
8115 else
8117 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8118 const char *p1;
8120 if (TREE_CODE (s2) != INTEGER_CST)
8121 return 0;
8123 p1 = c_getstr (s1);
8124 if (p1 != NULL)
8126 char c;
8127 const char *r;
8129 if (target_char_cast (s2, &c))
8130 return 0;
8132 r = strchr (p1, c);
8134 if (r == NULL)
8135 return fold_convert (TREE_TYPE (s1), integer_zero_node);
8137 /* Return an offset into the constant string argument. */
8138 return fold (build2 (PLUS_EXPR, TREE_TYPE (s1),
8139 s1, fold_convert (TREE_TYPE (s1),
8140 ssize_int (r - p1))));
8143 /* FIXME: Should use here strchrM optab so that ports can optimize
8144 this. */
8145 return 0;
8149 /* Simplify a call to the strrchr builtin.
8151 Return 0 if no simplification was possible, otherwise return the
8152 simplified form of the call as a tree.
8154 The simplified form may be a constant or other expression which
8155 computes the same value, but in a more efficient manner (including
8156 calls to other builtin functions).
8158 The call may contain arguments which need to be evaluated, but
8159 which are not useful to determine the result of the call. In
8160 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8161 COMPOUND_EXPR will be an argument which must be evaluated.
8162 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8163 COMPOUND_EXPR in the chain will contain the tree for the simplified
8164 form of the builtin function call. */
8166 static tree
8167 simplify_builtin_strrchr (tree arglist)
8169 if (!validate_arglist (arglist, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8170 return 0;
8171 else
8173 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8174 tree fn;
8175 const char *p1;
8177 if (TREE_CODE (s2) != INTEGER_CST)
8178 return 0;
8180 p1 = c_getstr (s1);
8181 if (p1 != NULL)
8183 char c;
8184 const char *r;
8186 if (target_char_cast (s2, &c))
8187 return 0;
8189 r = strrchr (p1, c);
8191 if (r == NULL)
8192 return fold_convert (TREE_TYPE (s1), integer_zero_node);
8194 /* Return an offset into the constant string argument. */
8195 return fold (build2 (PLUS_EXPR, TREE_TYPE (s1),
8196 s1, fold_convert (TREE_TYPE (s1),
8197 ssize_int (r - p1))));
8200 if (! integer_zerop (s2))
8201 return 0;
8203 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
8204 if (!fn)
8205 return 0;
8207 /* Transform strrchr(s1, '\0') to strchr(s1, '\0'). */
8208 return build_function_call_expr (fn, arglist);
8212 /* Simplify a call to the strpbrk builtin.
8214 Return 0 if no simplification was possible, otherwise return the
8215 simplified form of the call as a tree.
8217 The simplified form may be a constant or other expression which
8218 computes the same value, but in a more efficient manner (including
8219 calls to other builtin functions).
8221 The call may contain arguments which need to be evaluated, but
8222 which are not useful to determine the result of the call. In
8223 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8224 COMPOUND_EXPR will be an argument which must be evaluated.
8225 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8226 COMPOUND_EXPR in the chain will contain the tree for the simplified
8227 form of the builtin function call. */
8229 static tree
8230 simplify_builtin_strpbrk (tree arglist)
8232 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8233 return 0;
8234 else
8236 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8237 tree fn;
8238 const char *p1, *p2;
8240 p2 = c_getstr (s2);
8241 if (p2 == NULL)
8242 return 0;
8244 p1 = c_getstr (s1);
8245 if (p1 != NULL)
8247 const char *r = strpbrk (p1, p2);
8249 if (r == NULL)
8250 return fold_convert (TREE_TYPE (s1), integer_zero_node);
8252 /* Return an offset into the constant string argument. */
8253 return fold (build2 (PLUS_EXPR, TREE_TYPE (s1),
8254 s1, fold_convert (TREE_TYPE (s1),
8255 ssize_int (r - p1))));
8258 if (p2[0] == '\0')
8259 /* strpbrk(x, "") == NULL.
8260 Evaluate and ignore s1 in case it had side-effects. */
8261 return omit_one_operand (TREE_TYPE (s1), integer_zero_node, s1);
8263 if (p2[1] != '\0')
8264 return 0; /* Really call strpbrk. */
8266 fn = implicit_built_in_decls[BUILT_IN_STRCHR];
8267 if (!fn)
8268 return 0;
8270 /* New argument list transforming strpbrk(s1, s2) to
8271 strchr(s1, s2[0]). */
8272 arglist =
8273 build_tree_list (NULL_TREE, build_int_2 (p2[0], 0));
8274 arglist = tree_cons (NULL_TREE, s1, arglist);
8275 return build_function_call_expr (fn, arglist);
8279 /* Simplify a call to the strcpy builtin.
8281 Return 0 if no simplification was possible, otherwise return the
8282 simplified form of the call as a tree.
8284 The simplified form may be a constant or other expression which
8285 computes the same value, but in a more efficient manner (including
8286 calls to other builtin functions).
8288 The call may contain arguments which need to be evaluated, but
8289 which are not useful to determine the result of the call. In
8290 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8291 COMPOUND_EXPR will be an argument which must be evaluated.
8292 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8293 COMPOUND_EXPR in the chain will contain the tree for the simplified
8294 form of the builtin function call. */
8296 tree
8297 simplify_builtin_strcpy (tree arglist, tree len)
8299 tree fn, src, dst;
8301 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8302 return 0;
8304 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8305 if (!fn)
8306 return 0;
8308 src = TREE_VALUE (TREE_CHAIN (arglist));
8309 dst = TREE_VALUE (arglist);
8311 if (!len)
8313 len = c_strlen (src, 1);
8314 if (!len || TREE_SIDE_EFFECTS (len))
8315 return 0;
8318 len = size_binop (PLUS_EXPR, len, ssize_int (1));
8319 arglist = build_tree_list (NULL_TREE, len);
8320 arglist = tree_cons (NULL_TREE, src, arglist);
8321 arglist = tree_cons (NULL_TREE, dst, arglist);
8322 return build_function_call_expr (fn, arglist);
8325 /* Simplify a call to the strncpy builtin.
8327 Return 0 if no simplification was possible, otherwise return the
8328 simplified form of the call as a tree.
8330 The simplified form may be a constant or other expression which
8331 computes the same value, but in a more efficient manner (including
8332 calls to other builtin functions).
8334 The call may contain arguments which need to be evaluated, but
8335 which are not useful to determine the result of the call. In
8336 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8337 COMPOUND_EXPR will be an argument which must be evaluated.
8338 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8339 COMPOUND_EXPR in the chain will contain the tree for the simplified
8340 form of the builtin function call. */
8342 tree
8343 simplify_builtin_strncpy (tree arglist, tree slen)
8345 if (!validate_arglist (arglist,
8346 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8347 return 0;
8348 else
8350 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
8351 tree fn;
8353 /* We must be passed a constant len parameter. */
8354 if (TREE_CODE (len) != INTEGER_CST)
8355 return 0;
8357 /* If the len parameter is zero, return the dst parameter. */
8358 if (integer_zerop (len))
8359 /* Evaluate and ignore the src argument in case it has
8360 side-effects and return the dst parameter. */
8361 return omit_one_operand (TREE_TYPE (TREE_VALUE (arglist)),
8362 TREE_VALUE (arglist),
8363 TREE_VALUE (TREE_CHAIN (arglist)));
8365 if (!slen)
8366 slen = c_strlen (TREE_VALUE (TREE_CHAIN (arglist)), 0);
8368 /* Now, we must be passed a constant src ptr parameter. */
8369 if (slen == 0 || TREE_CODE (slen) != INTEGER_CST)
8370 return 0;
8372 slen = size_binop (PLUS_EXPR, slen, ssize_int (1));
8374 /* We do not support simplification of this case, though we do
8375 support it when expanding trees into RTL. */
8376 /* FIXME: generate a call to __builtin_memset. */
8377 if (tree_int_cst_lt (slen, len))
8378 return 0;
8380 /* OK transform into builtin memcpy. */
8381 fn = implicit_built_in_decls[BUILT_IN_MEMCPY];
8382 if (!fn)
8383 return 0;
8384 return build_function_call_expr (fn, arglist);
8388 /* Simplify a call to the memcmp builtin.
8390 Return 0 if no simplification was possible, otherwise return the
8391 simplified form of the call as a tree.
8393 The simplified form may be a constant or other expression which
8394 computes the same value, but in a more efficient manner (including
8395 calls to other builtin functions).
8397 The call may contain arguments which need to be evaluated, but
8398 which are not useful to determine the result of the call. In
8399 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8400 COMPOUND_EXPR will be an argument which must be evaluated.
8401 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8402 COMPOUND_EXPR in the chain will contain the tree for the simplified
8403 form of the builtin function call. */
8405 static tree
8406 simplify_builtin_memcmp (tree arglist)
8408 tree arg1, arg2, len;
8409 const char *p1, *p2;
8411 if (!validate_arglist (arglist,
8412 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8413 return 0;
8415 arg1 = TREE_VALUE (arglist);
8416 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
8417 len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
8419 /* If the len parameter is zero, return zero. */
8420 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 0)
8422 /* Evaluate and ignore arg1 and arg2 in case they have
8423 side-effects. */
8424 return build2 (COMPOUND_EXPR, integer_type_node, arg1,
8425 build2 (COMPOUND_EXPR, integer_type_node,
8426 arg2, integer_zero_node));
8429 p1 = c_getstr (arg1);
8430 p2 = c_getstr (arg2);
8432 /* If all arguments are constant, and the value of len is not greater
8433 than the lengths of arg1 and arg2, evaluate at compile-time. */
8434 if (host_integerp (len, 1) && p1 && p2
8435 && compare_tree_int (len, strlen (p1) + 1) <= 0
8436 && compare_tree_int (len, strlen (p2) + 1) <= 0)
8438 const int r = memcmp (p1, p2, tree_low_cst (len, 1));
8440 return (r < 0
8441 ? integer_minus_one_node
8442 : (r > 0 ? integer_one_node : integer_zero_node));
8445 /* If len parameter is one, return an expression corresponding to
8446 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
8447 if (host_integerp (len, 1) && tree_low_cst (len, 1) == 1)
8449 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8450 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
8451 tree ind1 =
8452 fold (build1 (CONVERT_EXPR, integer_type_node,
8453 build1 (INDIRECT_REF, cst_uchar_node,
8454 build1 (NOP_EXPR, cst_uchar_ptr_node, arg1))));
8455 tree ind2 =
8456 fold (build1 (CONVERT_EXPR, integer_type_node,
8457 build1 (INDIRECT_REF, cst_uchar_node,
8458 build1 (NOP_EXPR, cst_uchar_ptr_node, arg2))));
8459 return fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
8462 return 0;
8465 /* Simplify a call to the strcmp builtin.
8467 Return 0 if no simplification was possible, otherwise return the
8468 simplified form of the call as a tree.
8470 The simplified form may be a constant or other expression which
8471 computes the same value, but in a more efficient manner (including
8472 calls to other builtin functions).
8474 The call may contain arguments which need to be evaluated, but
8475 which are not useful to determine the result of the call. In
8476 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8477 COMPOUND_EXPR will be an argument which must be evaluated.
8478 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8479 COMPOUND_EXPR in the chain will contain the tree for the simplified
8480 form of the builtin function call. */
8482 static tree
8483 simplify_builtin_strcmp (tree arglist)
8485 tree arg1, arg2;
8486 const char *p1, *p2;
8488 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8489 return 0;
8491 arg1 = TREE_VALUE (arglist);
8492 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
8494 /* If both arguments are equal (and not volatile), return zero. */
8495 if (operand_equal_p (arg1, arg2, 0))
8496 return integer_zero_node;
8498 p1 = c_getstr (arg1);
8499 p2 = c_getstr (arg2);
8501 if (p1 && p2)
8503 const int i = strcmp (p1, p2);
8504 return (i < 0
8505 ? integer_minus_one_node
8506 : (i > 0 ? integer_one_node : integer_zero_node));
8509 /* If either arg is "", return an expression corresponding to
8510 (*(const unsigned char*)arg1 - (const unsigned char*)arg2). */
8511 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
8513 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8514 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
8515 tree ind1 =
8516 fold (build1 (CONVERT_EXPR, integer_type_node,
8517 build1 (INDIRECT_REF, cst_uchar_node,
8518 build1 (NOP_EXPR, cst_uchar_ptr_node, arg1))));
8519 tree ind2 =
8520 fold (build1 (CONVERT_EXPR, integer_type_node,
8521 build1 (INDIRECT_REF, cst_uchar_node,
8522 build1 (NOP_EXPR, cst_uchar_ptr_node, arg2))));
8523 return fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
8526 return 0;
8529 /* Simplify a call to the strncmp builtin.
8531 Return 0 if no simplification was possible, otherwise return the
8532 simplified form of the call as a tree.
8534 The simplified form may be a constant or other expression which
8535 computes the same value, but in a more efficient manner (including
8536 calls to other builtin functions).
8538 The call may contain arguments which need to be evaluated, but
8539 which are not useful to determine the result of the call. In
8540 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8541 COMPOUND_EXPR will be an argument which must be evaluated.
8542 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8543 COMPOUND_EXPR in the chain will contain the tree for the simplified
8544 form of the builtin function call. */
8546 static tree
8547 simplify_builtin_strncmp (tree arglist)
8549 tree arg1, arg2, arg3;
8550 const char *p1, *p2;
8552 if (!validate_arglist (arglist,
8553 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8554 return 0;
8556 arg1 = TREE_VALUE (arglist);
8557 arg2 = TREE_VALUE (TREE_CHAIN (arglist));
8558 arg3 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
8560 /* If the len parameter is zero, return zero. */
8561 if (integer_zerop (arg3))
8563 /* Evaluate and ignore arg1 and arg2 in case they have
8564 side-effects. */
8565 return build2 (COMPOUND_EXPR, integer_type_node, arg1,
8566 build2 (COMPOUND_EXPR, integer_type_node,
8567 arg2, integer_zero_node));
8570 /* If arg1 and arg2 are equal (and not volatile), return zero. */
8571 if (operand_equal_p (arg1, arg2, 0))
8572 /* Evaluate and ignore arg3 in case it has side-effects. */
8573 return omit_one_operand (integer_type_node, integer_zero_node, arg3);
8575 p1 = c_getstr (arg1);
8576 p2 = c_getstr (arg2);
8578 /* If all arguments are constant, evaluate at compile-time. */
8579 if (host_integerp (arg3, 1) && p1 && p2)
8581 const int r = strncmp (p1, p2, tree_low_cst (arg3, 1));
8582 return (r < 0
8583 ? integer_minus_one_node
8584 : (r > 0 ? integer_one_node : integer_zero_node));
8587 /* If len == 1 or (either string parameter is "" and (len >= 1)),
8588 return (*(const u_char*)arg1 - *(const u_char*)arg2). */
8589 if (host_integerp (arg3, 1)
8590 && (tree_low_cst (arg3, 1) == 1
8591 || (tree_low_cst (arg3, 1) > 1
8592 && ((p1 && *p1 == '\0') || (p2 && *p2 == '\0')))))
8594 tree cst_uchar_node = build_type_variant (unsigned_char_type_node, 1, 0);
8595 tree cst_uchar_ptr_node = build_pointer_type (cst_uchar_node);
8596 tree ind1 =
8597 fold (build1 (CONVERT_EXPR, integer_type_node,
8598 build1 (INDIRECT_REF, cst_uchar_node,
8599 build1 (NOP_EXPR, cst_uchar_ptr_node, arg1))));
8600 tree ind2 =
8601 fold (build1 (CONVERT_EXPR, integer_type_node,
8602 build1 (INDIRECT_REF, cst_uchar_node,
8603 build1 (NOP_EXPR, cst_uchar_ptr_node, arg2))));
8604 return fold (build2 (MINUS_EXPR, integer_type_node, ind1, ind2));
8607 return 0;
8610 /* Simplify a call to the strcat builtin.
8612 Return 0 if no simplification was possible, otherwise return the
8613 simplified form of the call as a tree.
8615 The simplified form may be a constant or other expression which
8616 computes the same value, but in a more efficient manner (including
8617 calls to other builtin functions).
8619 The call may contain arguments which need to be evaluated, but
8620 which are not useful to determine the result of the call. In
8621 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8622 COMPOUND_EXPR will be an argument which must be evaluated.
8623 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8624 COMPOUND_EXPR in the chain will contain the tree for the simplified
8625 form of the builtin function call. */
8627 static tree
8628 simplify_builtin_strcat (tree arglist)
8630 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8631 return 0;
8632 else
8634 tree dst = TREE_VALUE (arglist),
8635 src = TREE_VALUE (TREE_CHAIN (arglist));
8636 const char *p = c_getstr (src);
8638 /* If the string length is zero, return the dst parameter. */
8639 if (p && *p == '\0')
8640 return dst;
8642 return 0;
8646 /* Simplify a call to the strncat builtin.
8648 Return 0 if no simplification was possible, otherwise return the
8649 simplified form of the call as a tree.
8651 The simplified form may be a constant or other expression which
8652 computes the same value, but in a more efficient manner (including
8653 calls to other builtin functions).
8655 The call may contain arguments which need to be evaluated, but
8656 which are not useful to determine the result of the call. In
8657 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8658 COMPOUND_EXPR will be an argument which must be evaluated.
8659 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8660 COMPOUND_EXPR in the chain will contain the tree for the simplified
8661 form of the builtin function call. */
8663 static tree
8664 simplify_builtin_strncat (tree arglist)
8666 if (!validate_arglist (arglist,
8667 POINTER_TYPE, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
8668 return 0;
8669 else
8671 tree dst = TREE_VALUE (arglist);
8672 tree src = TREE_VALUE (TREE_CHAIN (arglist));
8673 tree len = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
8674 const char *p = c_getstr (src);
8676 /* If the requested length is zero, or the src parameter string
8677 length is zero, return the dst parameter. */
8678 if (integer_zerop (len) || (p && *p == '\0'))
8679 return build2 (COMPOUND_EXPR, TREE_TYPE (dst), src,
8680 build2 (COMPOUND_EXPR, integer_type_node, len, dst));
8682 /* If the requested len is greater than or equal to the string
8683 length, call strcat. */
8684 if (TREE_CODE (len) == INTEGER_CST && p
8685 && compare_tree_int (len, strlen (p)) >= 0)
8687 tree newarglist
8688 = tree_cons (NULL_TREE, dst, build_tree_list (NULL_TREE, src));
8689 tree fn = implicit_built_in_decls[BUILT_IN_STRCAT];
8691 /* If the replacement _DECL isn't initialized, don't do the
8692 transformation. */
8693 if (!fn)
8694 return 0;
8696 return build_function_call_expr (fn, newarglist);
8698 return 0;
8702 /* Simplify a call to the strspn builtin.
8704 Return 0 if no simplification was possible, otherwise return the
8705 simplified form of the call as a tree.
8707 The simplified form may be a constant or other expression which
8708 computes the same value, but in a more efficient manner (including
8709 calls to other builtin functions).
8711 The call may contain arguments which need to be evaluated, but
8712 which are not useful to determine the result of the call. In
8713 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8714 COMPOUND_EXPR will be an argument which must be evaluated.
8715 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8716 COMPOUND_EXPR in the chain will contain the tree for the simplified
8717 form of the builtin function call. */
8719 static tree
8720 simplify_builtin_strspn (tree arglist)
8722 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8723 return 0;
8724 else
8726 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8727 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
8729 /* If both arguments are constants, evaluate at compile-time. */
8730 if (p1 && p2)
8732 const size_t r = strspn (p1, p2);
8733 return size_int (r);
8736 /* If either argument is "", return 0. */
8737 if ((p1 && *p1 == '\0') || (p2 && *p2 == '\0'))
8739 /* Evaluate and ignore both arguments in case either one has
8740 side-effects. */
8741 return build2 (COMPOUND_EXPR, integer_type_node, s1,
8742 build2 (COMPOUND_EXPR, integer_type_node,
8743 s2, integer_zero_node));
8745 return 0;
8749 /* Simplify a call to the strcspn builtin.
8751 Return 0 if no simplification was possible, otherwise return the
8752 simplified form of the call as a tree.
8754 The simplified form may be a constant or other expression which
8755 computes the same value, but in a more efficient manner (including
8756 calls to other builtin functions).
8758 The call may contain arguments which need to be evaluated, but
8759 which are not useful to determine the result of the call. In
8760 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8761 COMPOUND_EXPR will be an argument which must be evaluated.
8762 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8763 COMPOUND_EXPR in the chain will contain the tree for the simplified
8764 form of the builtin function call. */
8766 static tree
8767 simplify_builtin_strcspn (tree arglist)
8769 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8770 return 0;
8771 else
8773 tree s1 = TREE_VALUE (arglist), s2 = TREE_VALUE (TREE_CHAIN (arglist));
8774 const char *p1 = c_getstr (s1), *p2 = c_getstr (s2);
8776 /* If both arguments are constants, evaluate at compile-time. */
8777 if (p1 && p2)
8779 const size_t r = strcspn (p1, p2);
8780 return size_int (r);
8783 /* If the first argument is "", return 0. */
8784 if (p1 && *p1 == '\0')
8786 /* Evaluate and ignore argument s2 in case it has
8787 side-effects. */
8788 return omit_one_operand (integer_type_node,
8789 integer_zero_node, s2);
8792 /* If the second argument is "", return __builtin_strlen(s1). */
8793 if (p2 && *p2 == '\0')
8795 tree newarglist = build_tree_list (NULL_TREE, s1),
8796 fn = implicit_built_in_decls[BUILT_IN_STRLEN];
8798 /* If the replacement _DECL isn't initialized, don't do the
8799 transformation. */
8800 if (!fn)
8801 return 0;
8803 return build_function_call_expr (fn, newarglist);
8805 return 0;
8809 /* Simplify a call to the fputs builtin.
8811 Return 0 if no simplification was possible, otherwise return the
8812 simplified form of the call as a tree.
8814 The simplified form may be a constant or other expression which
8815 computes the same value, but in a more efficient manner (including
8816 calls to other builtin functions).
8818 The call may contain arguments which need to be evaluated, but
8819 which are not useful to determine the result of the call. In
8820 this case we return a chain of COMPOUND_EXPRs. The LHS of each
8821 COMPOUND_EXPR will be an argument which must be evaluated.
8822 COMPOUND_EXPRs are chained through their RHS. The RHS of the last
8823 COMPOUND_EXPR in the chain will contain the tree for the simplified
8824 form of the builtin function call.
8826 If KNOWN_LEN is non-NULL, it represents the known length of the string.
8827 This is determined by SSA-CCP in cases where the string itself is not
8828 known to be constant but its length is always the same constant. */
8830 tree
8831 simplify_builtin_fputs (tree arglist, int ignore, int unlocked, tree known_len)
8833 tree len, fn;
8834 tree fn_fputc = unlocked ? implicit_built_in_decls[BUILT_IN_FPUTC_UNLOCKED]
8835 : implicit_built_in_decls[BUILT_IN_FPUTC];
8836 tree fn_fwrite = unlocked ? implicit_built_in_decls[BUILT_IN_FWRITE_UNLOCKED]
8837 : implicit_built_in_decls[BUILT_IN_FWRITE];
8839 /* If the return value is used, or the replacement _DECL isn't
8840 initialized, don't do the transformation. */
8841 if (!ignore || !fn_fputc || !fn_fwrite)
8842 return 0;
8844 /* Verify the arguments in the original call. */
8845 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE))
8846 return 0;
8848 len = (known_len) ? known_len : c_strlen (TREE_VALUE (arglist), 0);
8850 /* Get the length of the string passed to fputs. If the length
8851 can't be determined, punt. */
8852 if (!len
8853 || TREE_CODE (len) != INTEGER_CST)
8854 return 0;
8856 switch (compare_tree_int (len, 1))
8858 case -1: /* length is 0, delete the call entirely . */
8859 return omit_one_operand (integer_type_node, integer_zero_node,
8860 TREE_VALUE (TREE_CHAIN (arglist)));
8862 case 0: /* length is 1, call fputc. */
8864 const char *p = c_getstr (TREE_VALUE (arglist));
8866 if (p != NULL)
8868 /* New argument list transforming fputs(string, stream) to
8869 fputc(string[0], stream). */
8870 arglist =
8871 build_tree_list (NULL_TREE, TREE_VALUE (TREE_CHAIN (arglist)));
8872 arglist =
8873 tree_cons (NULL_TREE, build_int_2 (p[0], 0), arglist);
8874 fn = fn_fputc;
8875 break;
8878 /* FALLTHROUGH */
8879 case 1: /* length is greater than 1, call fwrite. */
8881 tree string_arg;
8883 /* If optimizing for size keep fputs. */
8884 if (optimize_size)
8885 return 0;
8886 string_arg = TREE_VALUE (arglist);
8887 /* New argument list transforming fputs(string, stream) to
8888 fwrite(string, 1, len, stream). */
8889 arglist = build_tree_list (NULL_TREE, TREE_VALUE (TREE_CHAIN (arglist)));
8890 arglist = tree_cons (NULL_TREE, len, arglist);
8891 arglist = tree_cons (NULL_TREE, size_one_node, arglist);
8892 arglist = tree_cons (NULL_TREE, string_arg, arglist);
8893 fn = fn_fwrite;
8894 break;
8896 default:
8897 abort ();
8900 return build_function_call_expr (fn, arglist);
8903 static void
8904 simplify_builtin_va_start (tree arglist)
8906 tree chain = TREE_CHAIN (arglist);
8908 if (TREE_CHAIN (chain))
8909 error ("too many arguments to function `va_start'");
8911 simplify_builtin_next_arg (chain);
8914 static void
8915 simplify_builtin_next_arg (tree arglist)
8917 tree fntype = TREE_TYPE (current_function_decl);
8919 if (TYPE_ARG_TYPES (fntype) == 0
8920 || (TREE_VALUE (tree_last (TYPE_ARG_TYPES (fntype)))
8921 == void_type_node))
8922 error ("`va_start' used in function with fixed args");
8923 else if (arglist)
8925 tree last_parm = tree_last (DECL_ARGUMENTS (current_function_decl));
8926 tree arg = TREE_VALUE (arglist);
8928 /* Strip off all nops for the sake of the comparison. This
8929 is not quite the same as STRIP_NOPS. It does more.
8930 We must also strip off INDIRECT_EXPR for C++ reference
8931 parameters. */
8932 while (TREE_CODE (arg) == NOP_EXPR
8933 || TREE_CODE (arg) == CONVERT_EXPR
8934 || TREE_CODE (arg) == NON_LVALUE_EXPR
8935 || TREE_CODE (arg) == INDIRECT_REF)
8936 arg = TREE_OPERAND (arg, 0);
8937 if (arg != last_parm)
8938 warning ("second parameter of `va_start' not last named argument");
8939 TREE_VALUE (arglist) = arg;
8941 else
8942 /* Evidently an out of date version of <stdarg.h>; can't validate
8943 va_start's second argument, but can still work as intended. */
8944 warning ("`__builtin_next_arg' called without an argument");
8948 /* Simplify a call to the sprintf builtin.
8950 Return 0 if no simplification was possible, otherwise return the
8951 simplified form of the call as a tree. If IGNORED is true, it means that
8952 the caller does not use the returned value of the function. */
8954 static tree
8955 simplify_builtin_sprintf (tree arglist, int ignored)
8957 tree call, retval, dest, fmt;
8958 const char *fmt_str = NULL;
8960 /* Verify the required arguments in the original call. We deal with two
8961 types of sprintf() calls: 'sprintf (str, fmt)' and
8962 'sprintf (dest, "%s", orig)'. */
8963 if (!validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, VOID_TYPE)
8964 && !validate_arglist (arglist, POINTER_TYPE, POINTER_TYPE, POINTER_TYPE,
8965 VOID_TYPE))
8966 return NULL_TREE;
8968 /* Get the destination string and the format specifier. */
8969 dest = TREE_VALUE (arglist);
8970 fmt = TREE_VALUE (TREE_CHAIN (arglist));
8972 /* Check whether the format is a literal string constant. */
8973 fmt_str = c_getstr (fmt);
8974 if (fmt_str == NULL)
8975 return NULL_TREE;
8977 call = NULL_TREE;
8978 retval = NULL_TREE;
8980 /* If the format doesn't contain % args or %%, use strcpy. */
8981 if (strchr (fmt_str, '%') == NULL)
8983 tree fn = implicit_built_in_decls[BUILT_IN_STRCPY];
8985 if (!fn)
8986 return NULL_TREE;
8988 /* Convert sprintf (str, fmt) into strcpy (str, fmt) when
8989 'format' is known to contain no % formats. */
8990 arglist = build_tree_list (NULL_TREE, fmt);
8991 arglist = tree_cons (NULL_TREE, dest, arglist);
8992 call = build_function_call_expr (fn, arglist);
8993 if (!ignored)
8994 retval = build_int_2 (strlen (fmt_str), 0);
8997 /* If the format is "%s", use strcpy if the result isn't used. */
8998 else if (fmt_str && strcmp (fmt_str, "%s") == 0)
9000 tree fn, orig;
9001 fn = implicit_built_in_decls[BUILT_IN_STRCPY];
9003 if (!fn)
9004 return NULL_TREE;
9006 /* Convert sprintf (str1, "%s", str2) into strcpy (str1, str2). */
9007 orig = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
9008 arglist = build_tree_list (NULL_TREE, orig);
9009 arglist = tree_cons (NULL_TREE, dest, arglist);
9010 if (!ignored)
9012 retval = c_strlen (orig, 1);
9013 if (!retval || TREE_CODE (retval) != INTEGER_CST)
9014 return NULL_TREE;
9016 call = build_function_call_expr (fn, arglist);
9019 if (call && retval)
9021 retval = convert
9022 (TREE_TYPE (TREE_TYPE (implicit_built_in_decls[BUILT_IN_SPRINTF])),
9023 retval);
9024 return build2 (COMPOUND_EXPR, TREE_TYPE (retval), call, retval);
9026 else
9027 return call;