Test to ensure the function does not have an unresolved or unevaluated exception specification before testing whether the function throws or not. Fixes PR25574.
llvm-svn: 253598
This commit is contained in:
		
							parent
							
								
									014fb55711
								
							
						
					
					
						commit
						f71c9661df
					
				| 
						 | 
				
			
			@ -19,9 +19,12 @@ AST_MATCHER(CXXConstructorDecl, isNoThrowCopyConstructor) {
 | 
			
		|||
  if (!Node.isCopyConstructor())
 | 
			
		||||
    return false;
 | 
			
		||||
 | 
			
		||||
  if (const auto *FnTy = Node.getType()->getAs<FunctionProtoType>())
 | 
			
		||||
  const auto *FnTy = Node.getType()->getAs<FunctionProtoType>();
 | 
			
		||||
  // Assume the best for any unresolved exception specification.
 | 
			
		||||
  if (isUnresolvedExceptionSpec(FnTy->getExceptionSpecType()))
 | 
			
		||||
    return true;
 | 
			
		||||
 | 
			
		||||
  return FnTy->isNothrow(Node.getASTContext());
 | 
			
		||||
  llvm_unreachable("Copy constructor with no prototype");
 | 
			
		||||
}
 | 
			
		||||
} // end namespace
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -36,7 +39,6 @@ void ThrownExceptionTypeCheck::registerMatchers(MatchFinder *Finder) {
 | 
			
		|||
              isCopyConstructor(), unless(isNoThrowCopyConstructor()))))
 | 
			
		||||
          .bind("expr"))),
 | 
			
		||||
      this);
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
void ThrownExceptionTypeCheck::check(const MatchFinder::MatchResult &Result) {
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -108,5 +108,20 @@ void f() {
 | 
			
		|||
  throw Allocates(); // match, copy constructor throws
 | 
			
		||||
  // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: thrown exception type is not nothrow copy constructible
 | 
			
		||||
  throw OptionallyAllocates(); // ok
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
namespace PR25574 {
 | 
			
		||||
struct B {
 | 
			
		||||
  B(const B&) noexcept;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
struct D : B {
 | 
			
		||||
  D();
 | 
			
		||||
  virtual ~D() noexcept;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
template <typename T>
 | 
			
		||||
void f() {
 | 
			
		||||
  throw D();
 | 
			
		||||
}
 | 
			
		||||
}
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
		Loading…
	
		Reference in New Issue