diff options
author | Mark Mitchell <mark@codesourcery.com> | 2004-03-30 23:45:00 +0000 |
---|---|---|
committer | Mark Mitchell <mmitchel@gcc.gnu.org> | 2004-03-30 23:45:00 +0000 |
commit | c6671cbbbc4bccc110b26c24a3eb706f596b7960 (patch) | |
tree | 04761024ef3f5044d3fc69d185c9e2024ebf24a9 /gcc | |
parent | 06ce772609f34249723fe45a49d9681827101aac (diff) | |
download | gcc-c6671cbbbc4bccc110b26c24a3eb706f596b7960.zip gcc-c6671cbbbc4bccc110b26c24a3eb706f596b7960.tar.gz gcc-c6671cbbbc4bccc110b26c24a3eb706f596b7960.tar.bz2 |
re PR c++/14724 (Destructor not called on backwards goto past initialization)
PR c++/14724
* decl.c (start_decl_1): Do not decide whether or not to create a
new cleanup level until after the type has been completed.
PR c++/14763
* pt.c (tsubst_default_argument): Clear current_function_decl.
PR c++/14724
* g++.dg/init/goto1.C: New test.
PR c++/14763
* g++.dg/template/defarg4.C: New test.
From-SVN: r80101
Diffstat (limited to 'gcc')
-rw-r--r-- | gcc/cp/ChangeLog | 9 | ||||
-rw-r--r-- | gcc/cp/decl.c | 10 | ||||
-rw-r--r-- | gcc/cp/pt.c | 4 | ||||
-rw-r--r-- | gcc/testsuite/ChangeLog | 8 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/init/goto1.C | 23 | ||||
-rw-r--r-- | gcc/testsuite/g++.dg/template/defarg4.C | 14 |
6 files changed, 66 insertions, 2 deletions
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 6e3f71a..6fba605 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,12 @@ +2004-03-30 Mark Mitchell <mark@codesourcery.com> + + PR c++/14724 + * decl.c (start_decl_1): Do not decide whether or not to create a + new cleanup level until after the type has been completed. + + PR c++/14763 + * pt.c (tsubst_default_argument): Clear current_function_decl. + 2004-03-30 Zack Weinberg <zack@codesourcery.com> * name-lookup.c, parser.c: Use new shorter form of GTY markers. diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index 0b802ff..ce530fa 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -3788,8 +3788,6 @@ start_decl_1 (tree decl) if (type == error_mark_node) return; - maybe_push_cleanup_level (type); - if (initialized) /* Is it valid for this decl to have an initializer at all? If not, set INITIALIZED to zero, which will indirectly @@ -3845,6 +3843,14 @@ start_decl_1 (tree decl) if (! initialized) DECL_INITIAL (decl) = NULL_TREE; + + /* Create a new scope to hold this declaration if necessary. + Whether or not a new scope is necessary cannot be determined + until after the type has been completed; if the type is a + specialization of a class template it is not until after + instantiation has occurred that TYPE_HAS_NONTRIVIAL_DESTRUCTOR + will be set correctly. */ + maybe_push_cleanup_level (type); } /* Handle initialization of references. DECL, TYPE, and INIT have the diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c index 3e3d0e9..b096017 100644 --- a/gcc/cp/pt.c +++ b/gcc/cp/pt.c @@ -5902,6 +5902,10 @@ tsubst_default_argument (tree fn, tree type, tree arg) /* FN is already the desired FUNCTION_DECL. */ push_access_scope (fn); + /* The default argument expression should not be considered to be + within the scope of FN. Since push_access_scope sets + current_function_decl, we must explicitly clear it here. */ + current_function_decl = NULL_TREE; arg = tsubst_expr (arg, DECL_TI_ARGS (fn), tf_error | tf_warning, NULL_TREE); diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 6bba3d5..416128f 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,11 @@ +2004-03-30 Mark Mitchell <mark@codesourcery.com> + + PR c++/14724 + * g++.dg/init/goto1.C: New test. + + PR c++/14763 + * g++.dg/template/defarg4.C: New test. + 2004-03-30 Hartmut Penner <hpenner@de.ibm.com> * gcc.dg/altivec-11.c: Extend test for more valid cases. diff --git a/gcc/testsuite/g++.dg/init/goto1.C b/gcc/testsuite/g++.dg/init/goto1.C new file mode 100644 index 0000000..b0a0c52 --- /dev/null +++ b/gcc/testsuite/g++.dg/init/goto1.C @@ -0,0 +1,23 @@ +// PR c++/14724 +// { dg-do run } + +int j; + +template <class T> +struct C { + C() { ++j; } + ~C() { --j; } +}; + +int main(int, char **) { + { + int i = 0; + again: + C<int> v; + if (++i < 10) + goto again; + } + + return j; +} + diff --git a/gcc/testsuite/g++.dg/template/defarg4.C b/gcc/testsuite/g++.dg/template/defarg4.C new file mode 100644 index 0000000..293538a --- /dev/null +++ b/gcc/testsuite/g++.dg/template/defarg4.C @@ -0,0 +1,14 @@ +// PR c++/14763 + +struct A { + int get() const {} + static A *foo(); +}; + +template<bool> struct S { + S(unsigned int = A::foo()->get()) ; +}; + +void foo() throw() { + S<false> f; +} |