OSDN Git Service

Give credit, where credit is due.
[pf3gnuchains/gcc-fork.git] / gcc / cp / except.c
1 /* Handle exceptional things in C++.
2    Copyright (C) 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
3    2000, 2001, 2002, 2003, 2004, 2005  Free Software Foundation, Inc.
4    Contributed by Michael Tiemann <tiemann@cygnus.com>
5    Rewritten by Mike Stump <mrs@cygnus.com>, based upon an
6    initial re-implementation courtesy Tad Hunt.
7
8 This file is part of GCC.
9
10 GCC is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2, or (at your option)
13 any later version.
14
15 GCC is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 GNU General Public License for more details.
19
20 You should have received a copy of the GNU General Public License
21 along with GCC; see the file COPYING.  If not, write to
22 the Free Software Foundation, 59 Temple Place - Suite 330,
23 Boston, MA 02111-1307, USA.  */
24
25
26 #include "config.h"
27 #include "system.h"
28 #include "coretypes.h"
29 #include "tm.h"
30 #include "tree.h"
31 #include "rtl.h"
32 #include "expr.h"
33 #include "libfuncs.h"
34 #include "cp-tree.h"
35 #include "flags.h"
36 #include "output.h"
37 #include "except.h"
38 #include "toplev.h"
39 #include "tree-inline.h"
40 #include "tree-iterator.h"
41
42 static void push_eh_cleanup (tree);
43 static tree prepare_eh_type (tree);
44 static tree build_eh_type_type (tree);
45 static tree do_begin_catch (void);
46 static int dtor_nothrow (tree);
47 static tree do_end_catch (tree);
48 static bool decl_is_java_type (tree decl, int err);
49 static void initialize_handler_parm (tree, tree);
50 static tree do_allocate_exception (tree);
51 static tree wrap_cleanups_r (tree *, int *, void *);
52 static int complete_ptr_ref_or_void_ptr_p (tree, tree);
53 static bool is_admissible_throw_operand (tree);
54 static int can_convert_eh (tree, tree);
55 static tree cp_protect_cleanup_actions (void);
56
57 /* Sets up all the global eh stuff that needs to be initialized at the
58    start of compilation.  */
59
60 void
61 init_exception_processing (void)
62 {
63   tree tmp;
64
65   /* void std::terminate (); */
66   push_namespace (std_identifier);
67   tmp = build_function_type (void_type_node, void_list_node);
68   terminate_node = build_cp_library_fn_ptr ("terminate", tmp);
69   TREE_THIS_VOLATILE (terminate_node) = 1;
70   TREE_NOTHROW (terminate_node) = 1;
71   pop_namespace ();
72
73   /* void __cxa_call_unexpected(void *); */
74   tmp = tree_cons (NULL_TREE, ptr_type_node, void_list_node);
75   tmp = build_function_type (void_type_node, tmp);
76   call_unexpected_node
77     = push_throw_library_fn (get_identifier ("__cxa_call_unexpected"), tmp);
78
79   eh_personality_libfunc = init_one_libfunc (USING_SJLJ_EXCEPTIONS
80                                              ? "__gxx_personality_sj0"
81                                              : "__gxx_personality_v0");
82
83   lang_eh_runtime_type = build_eh_type_type;
84   lang_protect_cleanup_actions = &cp_protect_cleanup_actions;
85 }
86
87 /* Returns an expression to be executed if an unhandled exception is
88    propagated out of a cleanup region.  */
89
90 static tree
91 cp_protect_cleanup_actions (void)
92 {
93   /* [except.terminate]
94
95      When the destruction of an object during stack unwinding exits
96      using an exception ... void terminate(); is called.  */
97   return build_call (terminate_node, NULL_TREE);
98 }     
99
100 static tree
101 prepare_eh_type (tree type)
102 {
103   if (type == NULL_TREE)
104     return type;
105   if (type == error_mark_node)
106     return error_mark_node;
107
108   /* peel back references, so they match.  */
109   type = non_reference (type);
110
111   /* Peel off cv qualifiers.  */
112   type = TYPE_MAIN_VARIANT (type);
113
114   return type;
115 }
116
117 /* Return the type info for TYPE as used by EH machinery.  */
118 tree
119 eh_type_info (tree type)
120 {
121   tree exp;
122
123   if (type == NULL_TREE || type == error_mark_node)
124     return type;
125
126   if (decl_is_java_type (type, 0))
127     exp = build_java_class_ref (TREE_TYPE (type));
128   else
129     exp = get_tinfo_decl (type);
130
131   return exp;
132 }
133
134 /* Build the address of a typeinfo decl for use in the runtime
135    matching field of the exception model.  */
136
137 static tree
138 build_eh_type_type (tree type)
139 {
140   tree exp = eh_type_info (type);
141
142   if (!exp)
143     return NULL;
144
145   mark_used (exp);
146
147   return convert (ptr_type_node, build_address (exp));
148 }
149
150 tree
151 build_exc_ptr (void)
152 {
153   return build0 (EXC_PTR_EXPR, ptr_type_node);
154 }
155
156 /* Build up a call to __cxa_get_exception_ptr so that we can build a
157    copy constructor for the thrown object.  */
158
159 static tree
160 do_get_exception_ptr (void)
161 {
162   tree fn;
163
164   fn = get_identifier ("__cxa_get_exception_ptr");
165   if (!get_global_value_if_present (fn, &fn))
166     {
167       /* Declare void* __cxa_get_exception_ptr (void *).  */
168       tree tmp = tree_cons (NULL_TREE, ptr_type_node, void_list_node);
169       fn = push_library_fn (fn, build_function_type (ptr_type_node, tmp));
170     }
171
172   return build_function_call (fn, tree_cons (NULL_TREE, build_exc_ptr (),
173                                              NULL_TREE));
174 }
175
176 /* Build up a call to __cxa_begin_catch, to tell the runtime that the
177    exception has been handled.  */
178
179 static tree
180 do_begin_catch (void)
181 {
182   tree fn;
183
184   fn = get_identifier ("__cxa_begin_catch");
185   if (!get_global_value_if_present (fn, &fn))
186     {
187       /* Declare void* __cxa_begin_catch (void *).  */
188       tree tmp = tree_cons (NULL_TREE, ptr_type_node, void_list_node);
189       fn = push_library_fn (fn, build_function_type (ptr_type_node, tmp));
190     }
191
192   return build_function_call (fn, tree_cons (NULL_TREE, build_exc_ptr (),
193                                              NULL_TREE));
194 }
195
196 /* Returns nonzero if cleaning up an exception of type TYPE (which can be
197    NULL_TREE for a ... handler) will not throw an exception.  */
198
199 static int
200 dtor_nothrow (tree type)
201 {
202   if (type == NULL_TREE)
203     return 0;
204
205   if (!CLASS_TYPE_P (type))
206     return 1;
207
208   if (CLASSTYPE_LAZY_DESTRUCTOR (type))
209     lazily_declare_fn (sfk_destructor, type);
210
211   return TREE_NOTHROW (CLASSTYPE_DESTRUCTORS (type));
212 }
213
214 /* Build up a call to __cxa_end_catch, to destroy the exception object
215    for the current catch block if no others are currently using it.  */
216
217 static tree
218 do_end_catch (tree type)
219 {
220   tree fn, cleanup;
221
222   fn = get_identifier ("__cxa_end_catch");
223   if (!get_global_value_if_present (fn, &fn))
224     {
225       /* Declare void __cxa_end_catch ().  */
226       fn = push_void_library_fn (fn, void_list_node);
227       /* This can throw if the destructor for the exception throws.  */
228       TREE_NOTHROW (fn) = 0;
229     }
230
231   cleanup = build_function_call (fn, NULL_TREE);
232   TREE_NOTHROW (cleanup) = dtor_nothrow (type);
233
234   return cleanup;
235 }
236
237 /* This routine creates the cleanup for the current exception.  */
238
239 static void
240 push_eh_cleanup (tree type)
241 {
242   finish_decl_cleanup (NULL_TREE, do_end_catch (type));
243 }
244
245 /* Return nonzero value if DECL is a Java type suitable for catch or
246    throw.  */
247
248 static bool
249 decl_is_java_type (tree decl, int err)
250 {
251   bool r = (TREE_CODE (decl) == POINTER_TYPE
252             && TREE_CODE (TREE_TYPE (decl)) == RECORD_TYPE
253             && TYPE_FOR_JAVA (TREE_TYPE (decl)));
254
255   if (err)
256     {
257       if (TREE_CODE (decl) == REFERENCE_TYPE
258           && TREE_CODE (TREE_TYPE (decl)) == RECORD_TYPE
259           && TYPE_FOR_JAVA (TREE_TYPE (decl)))
260         {
261           /* Can't throw a reference.  */
262           error ("type %qT is disallowed in Java %<throw%> or %<catch%>",
263                  decl);
264         }
265
266       if (r)
267         {
268           tree jthrow_node
269             = IDENTIFIER_GLOBAL_VALUE (get_identifier ("jthrowable"));
270
271           if (jthrow_node == NULL_TREE)
272             fatal_error
273               ("call to Java %<catch%> or %<throw%> with %<jthrowable%> undefined");
274
275           jthrow_node = TREE_TYPE (TREE_TYPE (jthrow_node));
276
277           if (! DERIVED_FROM_P (jthrow_node, TREE_TYPE (decl)))
278             {
279               /* Thrown object must be a Throwable.  */
280               error ("type %qT is not derived from %<java::lang::Throwable%>",
281                      TREE_TYPE (decl));
282             }
283         }
284     }
285
286   return r;
287 }
288
289 /* Select the personality routine to be used for exception handling,
290    or issue an error if we need two different ones in the same
291    translation unit.
292    ??? At present eh_personality_libfunc is set to
293    __gxx_personality_(sj|v)0 in init_exception_processing - should it
294    be done here instead?  */
295 void
296 choose_personality_routine (enum languages lang)
297 {
298   static enum {
299     chose_none,
300     chose_cpp,
301     chose_java,
302     gave_error
303   } state;
304
305   switch (state)
306     {
307     case gave_error:
308       return;
309
310     case chose_cpp:
311       if (lang != lang_cplusplus)
312         goto give_error;
313       return;
314
315     case chose_java:
316       if (lang != lang_java)
317         goto give_error;
318       return;
319
320     case chose_none:
321       ; /* Proceed to language selection.  */
322     }
323
324   switch (lang)
325     {
326     case lang_cplusplus:
327       state = chose_cpp;
328       break;
329
330     case lang_java:
331       state = chose_java;
332       eh_personality_libfunc = init_one_libfunc (USING_SJLJ_EXCEPTIONS
333                                                  ? "__gcj_personality_sj0"
334                                                  : "__gcj_personality_v0");
335       break;
336
337     default:
338       gcc_unreachable ();
339     }
340   return;
341
342  give_error:
343   error ("mixing C++ and Java catches in a single translation unit");
344   state = gave_error;
345 }
346
347 /* Initialize the catch parameter DECL.  */
348
349 static void 
350 initialize_handler_parm (tree decl, tree exp)
351 {
352   tree init;
353   tree init_type;
354
355   /* Make sure we mark the catch param as used, otherwise we'll get a
356      warning about an unused ((anonymous)).  */
357   TREE_USED (decl) = 1;
358
359   /* Figure out the type that the initializer is.  Pointers are returned
360      adjusted by value from __cxa_begin_catch.  Others are returned by 
361      reference.  */
362   init_type = TREE_TYPE (decl);
363   if (!POINTER_TYPE_P (init_type))
364     init_type = build_reference_type (init_type);
365
366   choose_personality_routine (decl_is_java_type (init_type, 0)
367                               ? lang_java : lang_cplusplus);
368
369   /* Since pointers are passed by value, initialize a reference to
370      pointer catch parm with the address of the temporary.  */
371   if (TREE_CODE (init_type) == REFERENCE_TYPE
372       && TYPE_PTR_P (TREE_TYPE (init_type)))
373     exp = build_unary_op (ADDR_EXPR, exp, 1);
374
375   exp = ocp_convert (init_type, exp, CONV_IMPLICIT|CONV_FORCE_TEMP, 0);
376
377   init = convert_from_reference (exp);
378
379   /* If the constructor for the catch parm exits via an exception, we
380      must call terminate.  See eh23.C.  */
381   if (TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
382     {
383       /* Generate the copy constructor call directly so we can wrap it.
384          See also expand_default_init.  */
385       init = ocp_convert (TREE_TYPE (decl), init,
386                           CONV_IMPLICIT|CONV_FORCE_TEMP, 0);
387       init = build1 (MUST_NOT_THROW_EXPR, TREE_TYPE (init), init);
388     }
389
390   /* Let `cp_finish_decl' know that this initializer is ok.  */
391   DECL_INITIAL (decl) = error_mark_node;
392   decl = pushdecl (decl);
393
394   start_decl_1 (decl);
395   cp_finish_decl (decl, init, NULL_TREE,
396                   LOOKUP_ONLYCONVERTING|DIRECT_BIND);
397 }
398
399 /* Call this to start a catch block.  DECL is the catch parameter.  */
400
401 tree
402 expand_start_catch_block (tree decl)
403 {
404   tree exp;
405   tree type;
406
407   if (! doing_eh (1))
408     return NULL_TREE;
409
410   /* Make sure this declaration is reasonable.  */
411   if (decl && !complete_ptr_ref_or_void_ptr_p (TREE_TYPE (decl), NULL_TREE))
412     decl = NULL_TREE;
413
414   if (decl)
415     type = prepare_eh_type (TREE_TYPE (decl));
416   else
417     type = NULL_TREE;
418
419   if (decl && decl_is_java_type (type, 1))
420     {
421       /* Java only passes object via pointer and doesn't require
422          adjusting.  The java object is immediately before the
423          generic exception header.  */
424       exp = build_exc_ptr ();
425       exp = build1 (NOP_EXPR, build_pointer_type (type), exp);
426       exp = build2 (MINUS_EXPR, TREE_TYPE (exp), exp,
427                     TYPE_SIZE_UNIT (TREE_TYPE (exp)));
428       exp = build_indirect_ref (exp, NULL);
429       initialize_handler_parm (decl, exp);
430       return type;
431     }
432
433   /* Call __cxa_end_catch at the end of processing the exception.  */
434   push_eh_cleanup (type);
435
436   /* If there's no decl at all, then all we need to do is make sure
437      to tell the runtime that we've begun handling the exception.  */
438   if (decl == NULL)
439     finish_expr_stmt (do_begin_catch ());
440
441   /* If the C++ object needs constructing, we need to do that before
442      calling __cxa_begin_catch, so that std::uncaught_exception gets
443      the right value during the copy constructor.  */
444   else if (TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (decl)))
445     {
446       exp = do_get_exception_ptr ();
447       initialize_handler_parm (decl, exp);
448       finish_expr_stmt (do_begin_catch ());
449     }
450
451   /* Otherwise the type uses a bitwise copy, and we don't have to worry
452      about the value of std::uncaught_exception and therefore can do the
453      copy with the return value of __cxa_end_catch instead.  */
454   else
455     {
456       tree init = do_begin_catch ();
457       exp = create_temporary_var (ptr_type_node);
458       DECL_REGISTER (exp) = 1;
459       cp_finish_decl (exp, init, NULL_TREE, LOOKUP_ONLYCONVERTING);
460       finish_expr_stmt (build_modify_expr (exp, INIT_EXPR, init));
461       initialize_handler_parm (decl, exp);
462     }
463
464   return type;
465 }
466
467
468 /* Call this to end a catch block.  Its responsible for emitting the
469    code to handle jumping back to the correct place, and for emitting
470    the label to jump to if this catch block didn't match.  */
471
472 void
473 expand_end_catch_block (void)
474 {
475   if (! doing_eh (1))
476     return;
477
478   /* The exception being handled is rethrown if control reaches the end of
479      a handler of the function-try-block of a constructor or destructor.  */
480   if (in_function_try_handler
481       && (DECL_CONSTRUCTOR_P (current_function_decl)
482           || DECL_DESTRUCTOR_P (current_function_decl)))
483     finish_expr_stmt (build_throw (NULL_TREE));
484 }
485
486 tree
487 begin_eh_spec_block (void)
488 {
489   tree r = build_stmt (EH_SPEC_BLOCK, NULL_TREE, NULL_TREE);
490   add_stmt (r);
491   EH_SPEC_STMTS (r) = push_stmt_list ();
492   return r;
493 }
494
495 void
496 finish_eh_spec_block (tree raw_raises, tree eh_spec_block)
497 {
498   tree raises;
499
500   EH_SPEC_STMTS (eh_spec_block) = pop_stmt_list (EH_SPEC_STMTS (eh_spec_block));
501
502   /* Strip cv quals, etc, from the specification types.  */
503   for (raises = NULL_TREE;
504        raw_raises && TREE_VALUE (raw_raises);
505        raw_raises = TREE_CHAIN (raw_raises))
506     {
507       tree type = prepare_eh_type (TREE_VALUE (raw_raises));
508       tree tinfo = eh_type_info (type);
509
510       mark_used (tinfo);
511       raises = tree_cons (NULL_TREE, type, raises);
512     }
513
514   EH_SPEC_RAISES (eh_spec_block) = raises;
515 }
516
517 /* Return a pointer to a buffer for an exception object of type TYPE.  */
518
519 static tree
520 do_allocate_exception (tree type)
521 {
522   tree fn;
523
524   fn = get_identifier ("__cxa_allocate_exception");
525   if (!get_global_value_if_present (fn, &fn))
526     {
527       /* Declare void *__cxa_allocate_exception(size_t).  */
528       tree tmp = tree_cons (NULL_TREE, size_type_node, void_list_node);
529       fn = push_library_fn (fn, build_function_type (ptr_type_node, tmp));
530     }
531   
532   return build_function_call (fn, tree_cons (NULL_TREE, size_in_bytes (type),
533                                              NULL_TREE));
534 }
535
536 /* Call __cxa_free_exception from a cleanup.  This is never invoked
537    directly, but see the comment for stabilize_throw_expr.  */
538
539 static tree
540 do_free_exception (tree ptr)
541 {
542   tree fn;
543
544   fn = get_identifier ("__cxa_free_exception");
545   if (!get_global_value_if_present (fn, &fn))
546     {
547       /* Declare void __cxa_free_exception (void *).  */
548       fn = push_void_library_fn (fn, tree_cons (NULL_TREE, ptr_type_node,
549                                                 void_list_node));
550     }
551
552   return build_function_call (fn, tree_cons (NULL_TREE, ptr, NULL_TREE));
553 }
554
555 /* Wrap all cleanups for TARGET_EXPRs in MUST_NOT_THROW_EXPR.
556    Called from build_throw via walk_tree_without_duplicates.  */
557
558 static tree
559 wrap_cleanups_r (tree *tp, int *walk_subtrees ATTRIBUTE_UNUSED,
560                  void *data ATTRIBUTE_UNUSED)
561 {
562   tree exp = *tp;
563   tree cleanup;
564
565   /* Don't walk into types.  */
566   if (TYPE_P (exp))
567     {
568       *walk_subtrees = 0;
569       return NULL_TREE;
570     }
571   if (TREE_CODE (exp) != TARGET_EXPR)
572     return NULL_TREE;
573
574   cleanup = TARGET_EXPR_CLEANUP (exp);
575   if (cleanup)
576     {
577       cleanup = build1 (MUST_NOT_THROW_EXPR, void_type_node, cleanup);
578       TARGET_EXPR_CLEANUP (exp) = cleanup;
579     }
580
581   /* Keep iterating.  */
582   return NULL_TREE;
583 }
584
585 /* Build a throw expression.  */
586
587 tree
588 build_throw (tree exp)
589 {
590   tree fn;
591
592   if (exp == error_mark_node)
593     return exp;
594
595   if (processing_template_decl)
596     {
597       current_function_returns_abnormally = 1;
598       return build_min (THROW_EXPR, void_type_node, exp);
599     }
600
601   if (exp == null_node)
602     warning (0, "throwing NULL, which has integral, not pointer type");
603   
604   if (exp != NULL_TREE)
605     {
606       if (!is_admissible_throw_operand (exp))
607         return error_mark_node;
608     }
609
610   if (! doing_eh (1))
611     return error_mark_node;
612
613   if (exp && decl_is_java_type (TREE_TYPE (exp), 1))
614     {
615       tree fn = get_identifier ("_Jv_Throw");
616       if (!get_global_value_if_present (fn, &fn))
617         {
618           /* Declare void _Jv_Throw (void *).  */
619           tree tmp = tree_cons (NULL_TREE, ptr_type_node, void_list_node);
620           tmp = build_function_type (ptr_type_node, tmp);
621           fn = push_throw_library_fn (fn, tmp);
622         }
623       else if (really_overloaded_fn (fn))
624         {
625           error ("%qD should never be overloaded", fn);
626           return error_mark_node;
627         }
628       fn = OVL_CURRENT (fn);
629       exp = build_function_call (fn, tree_cons (NULL_TREE, exp, NULL_TREE));
630     }
631   else if (exp)
632     {
633       tree throw_type;
634       tree cleanup;
635       tree object, ptr;
636       tree tmp;
637       tree temp_expr, allocate_expr;
638       bool elided;
639
640       /* The CLEANUP_TYPE is the internal type of a destructor.  */
641       if (!cleanup_type)
642         {
643           tmp = void_list_node;
644           tmp = tree_cons (NULL_TREE, ptr_type_node, tmp);
645           tmp = build_function_type (void_type_node, tmp);
646           cleanup_type = build_pointer_type (tmp);
647         }
648       
649       fn = get_identifier ("__cxa_throw");
650       if (!get_global_value_if_present (fn, &fn))
651         {
652           /* Declare void __cxa_throw (void*, void*, void (*)(void*)).  */
653           /* ??? Second argument is supposed to be "std::type_info*".  */
654           tmp = void_list_node;
655           tmp = tree_cons (NULL_TREE, cleanup_type, tmp);
656           tmp = tree_cons (NULL_TREE, ptr_type_node, tmp);
657           tmp = tree_cons (NULL_TREE, ptr_type_node, tmp);
658           tmp = build_function_type (void_type_node, tmp);
659           fn = push_throw_library_fn (fn, tmp);
660         }
661       
662       /* throw expression */
663       /* First, decay it.  */
664       exp = decay_conversion (exp);
665
666       /* OK, this is kind of wacky.  The standard says that we call
667          terminate when the exception handling mechanism, after
668          completing evaluation of the expression to be thrown but
669          before the exception is caught (_except.throw_), calls a
670          user function that exits via an uncaught exception.
671
672          So we have to protect the actual initialization of the
673          exception object with terminate(), but evaluate the
674          expression first.  Since there could be temps in the
675          expression, we need to handle that, too.  We also expand
676          the call to __cxa_allocate_exception first (which doesn't
677          matter, since it can't throw).  */
678
679       /* Allocate the space for the exception.  */
680       allocate_expr = do_allocate_exception (TREE_TYPE (exp));
681       allocate_expr = get_target_expr (allocate_expr);
682       ptr = TARGET_EXPR_SLOT (allocate_expr);
683       object = build1 (NOP_EXPR, build_pointer_type (TREE_TYPE (exp)), ptr);
684       object = build_indirect_ref (object, NULL);
685
686       elided = (TREE_CODE (exp) == TARGET_EXPR);
687
688       /* And initialize the exception object.  */
689       exp = build_init (object, exp, LOOKUP_ONLYCONVERTING);
690       if (exp == error_mark_node)
691         {
692           error ("  in thrown expression");
693           return error_mark_node;
694         }
695
696       /* Pre-evaluate the thrown expression first, since if we allocated
697          the space first we would have to deal with cleaning it up if
698          evaluating this expression throws.
699
700          The case where EXP the initializer is a call to a constructor or a
701          function returning a class is a bit of a grey area in the
702          standard; it's unclear whether or not it should be allowed to
703          throw.  We used to say no, as that allowed us to optimize this
704          case without worrying about deallocating the exception object if
705          it does.  But that conflicted with expectations (PR 13944) and the
706          EDG compiler; now we wrap the initialization in a TRY_CATCH_EXPR
707          to call do_free_exception rather than in a MUST_NOT_THROW_EXPR,
708          for this case only.
709
710          Note that we don't check the return value from stabilize_init
711          because it will only return false in cases where elided is true,
712          and therefore we don't need to work around the failure to
713          preevaluate.  */
714       temp_expr = NULL_TREE;
715       stabilize_init (exp, &temp_expr);
716
717       if (elided)
718         exp = build2 (TRY_CATCH_EXPR, void_type_node, exp,
719                       do_free_exception (ptr));
720       else
721         exp = build1 (MUST_NOT_THROW_EXPR, void_type_node, exp);
722
723       /* Prepend the allocation.  */
724       exp = build2 (COMPOUND_EXPR, TREE_TYPE (exp), allocate_expr, exp);
725       if (temp_expr)
726         {
727           /* Prepend the calculation of the throw expression.  Also, force
728              any cleanups from the expression to be evaluated here so that
729              we don't have to do them during unwinding.  But first wrap
730              them in MUST_NOT_THROW_EXPR, since they are run after the
731              exception object is initialized.  */
732           walk_tree_without_duplicates (&temp_expr, wrap_cleanups_r, 0);
733           exp = build2 (COMPOUND_EXPR, TREE_TYPE (exp), temp_expr, exp);
734           exp = build1 (CLEANUP_POINT_EXPR, TREE_TYPE (exp), exp);
735         }
736
737       throw_type = build_eh_type_type (prepare_eh_type (TREE_TYPE (object)));
738
739       if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (TREE_TYPE (object)))
740         {
741           cleanup = lookup_fnfields (TYPE_BINFO (TREE_TYPE (object)),
742                                      complete_dtor_identifier, 0);
743           cleanup = BASELINK_FUNCTIONS (cleanup);
744           mark_used (cleanup);
745           cxx_mark_addressable (cleanup);
746           /* Pretend it's a normal function.  */
747           cleanup = build1 (ADDR_EXPR, cleanup_type, cleanup);
748         }
749       else
750         cleanup = build_int_cst (cleanup_type, 0);
751         
752       tmp = tree_cons (NULL_TREE, cleanup, NULL_TREE);
753       tmp = tree_cons (NULL_TREE, throw_type, tmp);
754       tmp = tree_cons (NULL_TREE, ptr, tmp);
755       /* ??? Indicate that this function call throws throw_type.  */
756       tmp = build_function_call (fn, tmp);
757
758       /* Tack on the initialization stuff.  */
759       exp = build2 (COMPOUND_EXPR, TREE_TYPE (tmp), exp, tmp);
760     }
761   else
762     {
763       /* Rethrow current exception.  */
764
765       tree fn = get_identifier ("__cxa_rethrow");
766       if (!get_global_value_if_present (fn, &fn))
767         {
768           /* Declare void __cxa_rethrow (void).  */
769           fn = push_throw_library_fn
770             (fn, build_function_type (void_type_node, void_list_node));
771         }
772
773       /* ??? Indicate that this function call allows exceptions of the type
774          of the enclosing catch block (if known).  */    
775       exp = build_function_call (fn, NULL_TREE);
776     }
777
778   exp = build1 (THROW_EXPR, void_type_node, exp);
779
780   return exp;
781 }
782
783 /* Make sure TYPE is complete, pointer to complete, reference to
784    complete, or pointer to cv void. Issue diagnostic on failure.
785    Return the zero on failure and nonzero on success. FROM can be
786    the expr or decl from whence TYPE came, if available.  */
787
788 static int
789 complete_ptr_ref_or_void_ptr_p (tree type, tree from)
790 {
791   int is_ptr;
792   
793   /* Check complete.  */
794   type = complete_type_or_else (type, from);
795   if (!type)
796     return 0;
797   
798   /* Or a pointer or ref to one, or cv void *.  */
799   is_ptr = TREE_CODE (type) == POINTER_TYPE;
800   if (is_ptr || TREE_CODE (type) == REFERENCE_TYPE)
801     {
802       tree core = TREE_TYPE (type);
803   
804       if (is_ptr && VOID_TYPE_P (core))
805         /* OK */;
806       else if (!complete_type_or_else (core, from))
807         return 0;
808     }
809   return 1;
810 }
811
812 /* Return truth-value if EXPRESSION is admissible in throw-expression,
813    i.e. if it is not of incomplete type or a pointer/reference to such
814    a type or of an abstract class type.  */
815
816 static bool
817 is_admissible_throw_operand (tree expr)
818 {
819   tree type = TREE_TYPE (expr);
820
821   /* 15.1/4 [...] The type of the throw-expression shall not be an
822             incomplete type, or a pointer or a reference to an incomplete
823             type, other than void*, const void*, volatile void*, or
824             const volatile void*.  Except for these restriction and the
825             restrictions on type matching mentioned in 15.3, the operand
826             of throw is treated exactly as a function argument in a call
827             (5.2.2) or the operand of a return statement.  */
828   if (!complete_ptr_ref_or_void_ptr_p (type, expr))
829     return false;
830
831   /* 10.4/3 An abstract class shall not be used as a parameter type,
832             as a function return type or as type of an explicit
833             conversion.  */
834   else if (CLASS_TYPE_P (type) && CLASSTYPE_PURE_VIRTUALS (type))
835     {
836       error ("expression %qE of abstract class type %qT cannot "
837              "be used in throw-expression", expr, type);
838       return false;
839     }
840
841   return true;
842 }
843
844 /* Returns nonzero if FN is a declaration of a standard C library
845    function which is known not to throw.
846
847    [lib.res.on.exception.handling]: None of the functions from the
848    Standard C library shall report an error by throwing an
849    exception, unless it calls a program-supplied function that
850    throws an exception.  */
851
852 #include "cfns.h"
853
854 int
855 nothrow_libfn_p (tree fn)
856 {
857   tree id;
858
859   if (TREE_PUBLIC (fn)
860       && DECL_EXTERNAL (fn)
861       && DECL_NAMESPACE_SCOPE_P (fn)
862       && DECL_EXTERN_C_P (fn))
863     /* OK */;
864   else
865     /* Can't be a C library function.  */
866     return 0;
867
868   /* Being a C library function, DECL_ASSEMBLER_NAME == DECL_NAME
869      unless the system headers are playing rename tricks, and if
870      they are, we don't want to be confused by them.  */
871   id = DECL_NAME (fn);
872   return !!libc_name_p (IDENTIFIER_POINTER (id), IDENTIFIER_LENGTH (id));
873 }
874
875 /* Returns nonzero if an exception of type FROM will be caught by a
876    handler for type TO, as per [except.handle].  */
877
878 static int
879 can_convert_eh (tree to, tree from)
880 {
881   to = non_reference (to);
882   from = non_reference (from);
883
884   if (TREE_CODE (to) == POINTER_TYPE && TREE_CODE (from) == POINTER_TYPE)
885     {
886       to = TREE_TYPE (to);
887       from = TREE_TYPE (from);
888
889       if (! at_least_as_qualified_p (to, from))
890         return 0;
891
892       if (TREE_CODE (to) == VOID_TYPE)
893         return 1;
894
895       /* Else fall through.  */
896     }
897
898   if (CLASS_TYPE_P (to) && CLASS_TYPE_P (from)
899       && PUBLICLY_UNIQUELY_DERIVED_P (to, from))
900     return 1;
901
902   return 0;
903 }
904
905 /* Check whether any of the handlers in I are shadowed by another handler
906    accepting TYPE.  Note that the shadowing may not be complete; even if
907    an exception of type B would be caught by a handler for A, there could
908    be a derived class C for which A is an ambiguous base but B is not, so
909    the handler for B would catch an exception of type C.  */
910
911 static void
912 check_handlers_1 (tree master, tree_stmt_iterator i)
913 {
914   tree type = TREE_TYPE (master);
915
916   for (; !tsi_end_p (i); tsi_next (&i))
917     {
918       tree handler = tsi_stmt (i);
919       if (TREE_TYPE (handler) && can_convert_eh (type, TREE_TYPE (handler)))
920         {
921           warning (0, "%Hexception of type %qT will be caught",
922                    EXPR_LOCUS (handler), TREE_TYPE (handler));
923           warning (0, "%H   by earlier handler for %qT",
924                    EXPR_LOCUS (master), type);
925           break;
926         }
927     }
928 }
929
930 /* Given a STATEMENT_LIST of HANDLERs, make sure that they're OK.  */
931
932 void
933 check_handlers (tree handlers)
934 {
935   tree_stmt_iterator i;
936
937   /* If we don't have a STATEMENT_LIST, then we've just got one
938      handler, and thus nothing to warn about.  */
939   if (TREE_CODE (handlers) != STATEMENT_LIST)
940     return;
941
942   i = tsi_start (handlers);
943   if (!tsi_end_p (i))
944     while (1)
945       {
946         tree handler = tsi_stmt (i);
947         tsi_next (&i);
948
949         /* No more handlers; nothing to shadow.  */
950         if (tsi_end_p (i))
951           break;
952         if (TREE_TYPE (handler) == NULL_TREE)
953           pedwarn ("%H%<...%> handler must be the last handler for"
954                    " its try block", EXPR_LOCUS (handler));
955         else
956           check_handlers_1 (handler, i);
957       }
958 }