summaryrefslogtreecommitdiff
path: root/gcc/cp/decl.c
diff options
context:
space:
mode:
authormmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>2005-12-20 08:48:13 +0000
committermmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>2005-12-20 08:48:13 +0000
commitd14e9620e473a0eced65ca981e5fd2cceaf4bcff (patch)
treebe663b0ecc3d9eb125f8cd7f7af5c682c5c9353e /gcc/cp/decl.c
parent6c3d4e0b1eac6a102922dd35f1ce0fa5cf8a14e8 (diff)
downloadgcc-d14e9620e473a0eced65ca981e5fd2cceaf4bcff.tar.gz
PR c++/21228
* decl.c (use_eh_spec_block): New function. (store_parm_decls): Use it. (finish_function): Likewise. PR c++/21228 * g++.dg/warn/Wunreachable-code-2.C: New test. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@108851 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/cp/decl.c')
-rw-r--r--gcc/cp/decl.c41
1 files changed, 27 insertions, 14 deletions
diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c
index ffa5e336d9b..447e98dd0cc 100644
--- a/gcc/cp/decl.c
+++ b/gcc/cp/decl.c
@@ -10482,6 +10482,30 @@ start_function (cp_decl_specifier_seq *declspecs,
return 1;
}
+/* Returns true iff an EH_SPEC_BLOCK should be created in the body of
+ FN. */
+
+static bool
+use_eh_spec_block (tree fn)
+{
+ return (flag_exceptions && flag_enforce_eh_specs
+ && !processing_template_decl
+ && TYPE_RAISES_EXCEPTIONS (TREE_TYPE (fn))
+ /* We insert the EH_SPEC_BLOCK only in the original
+ function; then, it is copied automatically to the
+ clones. */
+ && !DECL_CLONED_FUNCTION_P (fn)
+ /* Implicitly-generated constructors and destructors have
+ exception specifications. However, those specifications
+ are the union of the possible exceptions specified by the
+ constructors/destructors for bases and members, so no
+ unallowed exception will ever reach this function. By
+ not creating the EH_SPEC_BLOCK we save a little memory,
+ and we avoid spurious warnings about unreachable
+ code. */
+ && !DECL_ARTIFICIAL (fn));
+}
+
/* Store the parameter declarations into the current function declaration.
This is called after parsing the parameter declarations, before
digesting the body of the function.
@@ -10552,16 +10576,8 @@ store_parm_decls (tree current_function_parms)
DECL_ARGUMENTS is not modified. */
current_binding_level->names = chainon (nonparms, DECL_ARGUMENTS (fndecl));
- /* For a cloned function, we've already got all the code we need;
- there's no need to add any extra bits. */
- if (!DECL_CLONED_FUNCTION_P (fndecl))
- {
- /* Do the starting of the exception specifications, if we have any. */
- if (flag_exceptions && !processing_template_decl
- && flag_enforce_eh_specs
- && TYPE_RAISES_EXCEPTIONS (TREE_TYPE (current_function_decl)))
- current_eh_spec_block = begin_eh_spec_block ();
- }
+ if (use_eh_spec_block (current_function_decl))
+ current_eh_spec_block = begin_eh_spec_block ();
}
@@ -10848,10 +10864,7 @@ finish_function (int flags)
#endif
}
- /* Finish dealing with exception specifiers. */
- if (flag_exceptions && !processing_template_decl
- && flag_enforce_eh_specs
- && TYPE_RAISES_EXCEPTIONS (TREE_TYPE (current_function_decl)))
+ if (use_eh_spec_block (current_function_decl))
finish_eh_spec_block (TYPE_RAISES_EXCEPTIONS
(TREE_TYPE (current_function_decl)),
current_eh_spec_block);