diff options
author | Douglas Gregor <dgregor@apple.com> | 2012-04-16 18:27:27 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2012-04-16 18:27:27 +0000 |
commit | 74e2fc332e07c76d4e69ccbd0e9e47a0bafd3908 (patch) | |
tree | e13935dca7e6eaa9e934215f7517e99dd591fcb4 /lib/Parse/ParseDecl.cpp | |
parent | 0f90590c96375052c67116f620fafa2b1eadb41e (diff) |
Implement the last part of C++ [class.mem]p2, delaying the parsing of
exception specifications on member functions until after the closing
'}' for the containing class. This allows, for example, a member
function to throw an instance of its own class. Fixes PR12564 and a
fairly embarassing oversight in our C++98/03 support.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@154844 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Parse/ParseDecl.cpp')
-rw-r--r-- | lib/Parse/ParseDecl.cpp | 17 |
1 files changed, 12 insertions, 5 deletions
diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp index 16c90e9b71..932ffb440f 100644 --- a/lib/Parse/ParseDecl.cpp +++ b/lib/Parse/ParseDecl.cpp @@ -4197,6 +4197,7 @@ void Parser::ParseFunctionDeclarator(Declarator &D, SmallVector<ParsedType, 2> DynamicExceptions; SmallVector<SourceRange, 2> DynamicExceptionRanges; ExprResult NoexceptExpr; + CachedTokens *ExceptionSpecTokens = 0; ParsedAttributes FnAttrs(AttrFactory); ParsedType TrailingReturnType; @@ -4265,10 +4266,16 @@ void Parser::ParseFunctionDeclarator(Declarator &D, IsCXX11MemberFunction); // Parse exception-specification[opt]. - ESpecType = MaybeParseExceptionSpecification(ESpecRange, - DynamicExceptions, - DynamicExceptionRanges, - NoexceptExpr); + bool Delayed = (D.getContext() == Declarator::MemberContext && + D.getDeclSpec().getStorageClassSpec() + != DeclSpec::SCS_typedef && + !D.getDeclSpec().isFriendSpecified()); + ESpecType = tryParseExceptionSpecification(Delayed, + ESpecRange, + DynamicExceptions, + DynamicExceptionRanges, + NoexceptExpr, + ExceptionSpecTokens); if (ESpecType != EST_None) EndLoc = ESpecRange.getEnd(); @@ -4303,6 +4310,7 @@ void Parser::ParseFunctionDeclarator(Declarator &D, DynamicExceptions.size(), NoexceptExpr.isUsable() ? NoexceptExpr.get() : 0, + ExceptionSpecTokens, Tracker.getOpenLocation(), EndLoc, D, TrailingReturnType), @@ -4504,7 +4512,6 @@ void Parser::ParseParameterDeclarationClause( // If we're inside a class definition, cache the tokens // corresponding to the default argument. We'll actually parse // them when we see the end of the class definition. - // FIXME: Templates will require something similar. // FIXME: Can we use a smart pointer for Toks? DefArgToks = new CachedTokens; |