1 /* Convert language-specific tree expression to rtl instructions,
3 Copyright (C) 1988, 1992, 1993, 1994, 1995 Free Software Foundation, Inc.
5 This file is part of GNU CC.
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING. If not, write to
19 the Free Software Foundation, 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA. */
33 /* Hook used by expand_expr to expand language-specific tree codes. */
36 cplus_expand_expr (exp
, target
, tmode
, modifier
)
39 enum machine_mode tmode
;
40 enum expand_modifier modifier
;
42 tree type
= TREE_TYPE (exp
);
43 register enum machine_mode mode
= TYPE_MODE (type
);
44 register enum tree_code code
= TREE_CODE (exp
);
45 rtx original_target
= target
;
46 int ignore
= target
== const0_rtx
;
49 target
= 0, original_target
= 0;
51 /* No sense saving up arithmetic to be done
52 if it's all in the wrong mode to form part of an address.
53 And force_operand won't know whether to sign-extend or zero-extend. */
55 if (mode
!= Pmode
&& modifier
== EXPAND_SUM
)
56 modifier
= EXPAND_NORMAL
;
62 /* Something needs to be initialized, but we didn't know
63 where that thing was when building the tree. For example,
64 it could be the return value of a function, or a parameter
65 to a function which lays down in the stack, or a temporary
66 variable which must be passed by reference.
68 Cleanups are handled in a language-specific way: they
69 might be run by the called function (true in GNU C++
70 for parameters with cleanups), or they might be
71 run by the caller, after the call (true in GNU C++
72 for other cleanup needs). */
74 tree func
= TREE_OPERAND (exp
, 0);
75 tree args
= TREE_OPERAND (exp
, 1);
76 tree type
= TREE_TYPE (exp
), slot
;
77 tree fn_type
= TREE_TYPE (TREE_TYPE (func
));
78 tree return_type
= TREE_TYPE (fn_type
);
80 rtx call_target
, return_target
;
81 int pcc_struct_return
= 0;
83 /* The expression `init' wants to initialize what
84 `target' represents. SLOT holds the slot for TARGET. */
85 slot
= TREE_OPERAND (exp
, 2);
89 /* Should always be called with a target in BLKmode case. */
90 my_friendly_assert (mode
!= BLKmode
, 205);
91 my_friendly_assert (DECL_RTL (slot
) != 0, 206);
93 target
= gen_reg_rtx (mode
);
96 /* The target the initializer will initialize (CALL_TARGET)
97 must now be directed to initialize the target we are
98 supposed to initialize (TARGET). The semantics for
99 choosing what CALL_TARGET is is language-specific,
100 as is building the call which will perform the
101 initialization. It is left here to show the choices that
104 if (TREE_CODE (func
) == ADDR_EXPR
105 && TREE_CODE (TREE_OPERAND (func
, 0)) == FUNCTION_DECL
106 && DECL_CONSTRUCTOR_P (TREE_OPERAND (func
, 0)))
108 type
= build_pointer_type (type
);
109 /* Don't clobber a value that might be part of a default
111 mark_addressable (slot
);
112 if (TREE_PERMANENT (args
))
113 args
= tree_cons (0, build1 (ADDR_EXPR
, type
, slot
),
116 TREE_VALUE (args
) = build1 (ADDR_EXPR
, type
, slot
);
119 else if (TREE_CODE (return_type
) == REFERENCE_TYPE
)
126 #ifdef PCC_STATIC_STRUCT_RETURN
127 pcc_struct_return
= 1;
130 call_target
= target
;
135 /* Make this a valid memory address now. The code below assumes
136 that it can compare rtx and make assumptions based on the
137 result. The assumptions are true only if the address was
138 valid to begin with. */
139 call_target
= validize_mem (call_target
);
141 /* If this is a reference to a symbol, expand_inline_function
142 will do this transformation and return a different target
143 than the one we gave it, though functionally equivalent. Do
144 the transformation here to avoid confusion. */
145 if (! cse_not_expected
&& GET_CODE (call_target
) == MEM
146 && GET_CODE (XEXP (call_target
, 0)) == SYMBOL_REF
)
148 call_target
= gen_rtx
149 (MEM
, mode
, memory_address (mode
, XEXP (call_target
, 0)));
150 MEM_IN_STRUCT_P (call_target
) = 1;
154 call_exp
= build (CALL_EXPR
, type
, func
, args
, NULL_TREE
);
155 TREE_SIDE_EFFECTS (call_exp
) = 1;
156 return_target
= expand_call (call_exp
, call_target
, ignore
);
157 if (call_target
== 0)
159 if (pcc_struct_return
)
161 extern int flag_access_control
;
162 int old_ac
= flag_access_control
;
164 tree init
= build_decl (VAR_DECL
, 0, type
);
165 TREE_ADDRESSABLE (init
) = 1;
166 DECL_RTL (init
) = return_target
;
168 flag_access_control
= 0;
169 expand_aggr_init (slot
, init
, 0, LOOKUP_ONLYCONVERTING
);
170 flag_access_control
= old_ac
;
172 if (TYPE_NEEDS_DESTRUCTOR (type
))
174 init
= build_decl (VAR_DECL
, 0,
175 build_reference_type (type
));
176 DECL_RTL (init
) = XEXP (return_target
, 0);
178 init
= maybe_build_cleanup (convert_from_reference (init
));
179 if (init
!= NULL_TREE
)
180 expand_expr (init
, const0_rtx
, VOIDmode
, 0);
182 call_target
= return_target
= DECL_RTL (slot
);
185 call_target
= return_target
;
188 if (call_target
!= return_target
)
190 my_friendly_assert (TYPE_HAS_TRIVIAL_INIT_REF (type
), 317);
191 if (GET_MODE (return_target
) == BLKmode
)
192 emit_block_move (call_target
, return_target
, expr_size (exp
),
193 TYPE_ALIGN (type
) / BITS_PER_UNIT
);
195 emit_move_insn (call_target
, return_target
);
198 if (TREE_CODE (return_type
) == REFERENCE_TYPE
)
202 if (GET_CODE (call_target
) == REG
203 && REGNO (call_target
) < FIRST_PSEUDO_REGISTER
)
204 my_friendly_abort (39);
206 type
= TREE_TYPE (exp
);
208 init
= build (RTL_EXPR
, return_type
, 0, call_target
);
209 /* We got back a reference to the type we want. Now initialize
211 expand_aggr_init (slot
, init
, 0, LOOKUP_ONLYCONVERTING
);
214 if (DECL_RTL (slot
) != target
)
215 emit_move_insn (DECL_RTL (slot
), target
);
216 return DECL_RTL (slot
);
222 return expand_expr (default_conversion (resolve_offset_ref (exp
)),
223 target
, tmode
, EXPAND_NORMAL
);
225 /* This is old crusty code, and does not handle all that the
226 resolve_offset_ref function does. (mrs) */
227 tree base
= build_unary_op (ADDR_EXPR
, TREE_OPERAND (exp
, 0), 0);
228 tree offset
= build_unary_op (ADDR_EXPR
, TREE_OPERAND (exp
, 1), 0);
229 return expand_expr (build (PLUS_EXPR
, TREE_TYPE (exp
), base
, offset
),
230 target
, tmode
, EXPAND_NORMAL
);
235 return DECL_RTL (exp
);
238 expand_throw (TREE_OPERAND (exp
, 0));
244 (NULL_TREE
, TREE_OPERAND (exp
, 0),
245 build_binary_op (MINUS_EXPR
, TREE_OPERAND (exp
, 2),
246 integer_one_node
, 1),
247 TREE_OPERAND (exp
, 1), 0), target
, tmode
, modifier
);
252 my_friendly_abort (40);
260 lang_expand_expr
= cplus_expand_expr
;
263 /* If DECL had its rtl moved from where callers expect it
264 to be, fix it up. RESULT is the nominal rtl for the RESULT_DECL,
265 which may be a pseudo instead of a hard register. */
268 fixup_result_decl (decl
, result
)
274 if (REGNO (result
) >= FIRST_PSEUDO_REGISTER
)
276 rtx real_decl_result
;
278 #ifdef FUNCTION_OUTGOING_VALUE
280 = FUNCTION_OUTGOING_VALUE (TREE_TYPE (decl
), current_function_decl
);
283 = FUNCTION_VALUE (TREE_TYPE (decl
), current_function_decl
);
285 REG_FUNCTION_VALUE_P (real_decl_result
) = 1;
286 result
= real_decl_result
;
288 store_expr (decl
, result
, 0);
289 emit_insn (gen_rtx (USE
, VOIDmode
, result
));
293 /* Expand this initialization inline and see if it's simple enough that
294 it can be done at compile-time. */
297 extract_aggr_init (decl
, init
)
304 extract_scalar_init (decl
, init
)
307 rtx value
, insns
, insn
;
308 extern struct obstack temporary_obstack
;
311 push_obstacks (&temporary_obstack
, &temporary_obstack
);
313 value
= expand_expr (init
, NULL_RTX
, VOIDmode
, 0);
314 insns
= get_insns ();
316 reg_scan (insns
, max_reg_num (), 0);
317 jump_optimize (insns
, 0, 0, 1);
320 for (insn
= insns
; insn
; insn
= NEXT_INSN (insn
))
324 if (GET_CODE (insn
) == NOTE
)
326 else if (GET_CODE (insn
) != INSN
)
330 if (GET_CODE (r
) != SET
)
335 if (! (to
== value
||
336 (GET_CODE (to
) == SUBREG
&& XEXP (to
, 0) == value
)))
341 switch (GET_CODE (r
))
344 t
= build_int_2 (XEXP (r
, 0), 0);
355 extract_init (decl
, init
)
361 if (IS_AGGR_TYPE (TREE_TYPE (decl
))
362 || TREE_CODE (TREE_TYPE (decl
)) == ARRAY_TYPE
)
363 init
= extract_aggr_init (decl
, init
);
365 init
= extract_scalar_init (decl
, init
);
367 if (init
== NULL_TREE
)
370 DECL_INITIAL (decl
) = init
;
379 tree value1
= NULL_TREE
, value2
= NULL_TREE
, label
;
381 if (start
!= NULL_TREE
&& TREE_TYPE (start
) != NULL_TREE
382 && POINTER_TYPE_P (TREE_TYPE (start
)))
383 error ("pointers are not permitted as case values");
386 pedwarn ("ANSI C++ forbids range expressions in switch statement");
388 if (processing_template_decl
)
390 add_tree (build_min_nt (CASE_LABEL
, start
, end
));
395 value1
= check_cp_case_value (start
);
397 value2
= check_cp_case_value (end
);
399 label
= build_decl (LABEL_DECL
, NULL_TREE
, NULL_TREE
);
401 if (value1
!= error_mark_node
402 && value2
!= error_mark_node
)
408 success
= pushcase_range (value1
, value2
, convert_and_check
,
411 success
= pushcase (value1
, convert_and_check
, label
, &duplicate
);
413 success
= pushcase (NULL_TREE
, 0, label
, &duplicate
);
418 error ("case label not within a switch statement");
420 cp_error ("case label `%E' not within a switch statement", start
);
422 error ("default label not within a switch statement");
424 else if (success
== 2)
428 error ("duplicate (or overlapping) case value");
429 cp_error_at ("this is the first entry overlapping that value",
434 cp_error ("duplicate case value `%E'", start
);
435 cp_error_at ("previously used here", duplicate
);
439 error ("multiple default labels in one switch");
440 cp_error_at ("this is the first default label", duplicate
);
443 else if (success
== 3)
444 warning ("case value out of range");
445 else if (success
== 4)
446 warning ("empty range specified");
447 else if (success
== 5)
450 error ("case label within scope of cleanup or variable array");
452 cp_error ("case label `%E' within scope of cleanup or variable array", start
);
456 define_case_label (label
);
458 define_case_label (NULL_TREE
);