From 80969754b73ceeeb350354eb97a67027c21862b6 Mon Sep 17 00:00:00 2001 From: Richard Smith Date: Tue, 10 Mar 2015 02:00:53 +0000 Subject: [PATCH] PR21687: when adding a redeclaration of a function with an implicit exception specification, update all prior declarations if the new one has an explicit exception specification and the prior ones don't. Patch by Vassil Vassilev! Some minor tweaking and test case by me. llvm-svn: 231738 --- clang/lib/Serialization/ASTReaderDecl.cpp | 21 +++++++++++++------ clang/test/Modules/Inputs/PR21687/a.h | 1 + clang/test/Modules/Inputs/PR21687/b.h | 2 ++ clang/test/Modules/Inputs/PR21687/c.h | 4 ++++ .../Modules/Inputs/PR21687/module.modulemap | 3 +++ clang/test/Modules/pr21687.cpp | 3 +++ 6 files changed, 28 insertions(+), 6 deletions(-) create mode 100644 clang/test/Modules/Inputs/PR21687/a.h create mode 100644 clang/test/Modules/Inputs/PR21687/b.h create mode 100644 clang/test/Modules/Inputs/PR21687/c.h create mode 100644 clang/test/Modules/Inputs/PR21687/module.modulemap create mode 100644 clang/test/Modules/pr21687.cpp diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp b/clang/lib/Serialization/ASTReaderDecl.cpp index 2a01d853c7c4..9a382c1659d9 100644 --- a/clang/lib/Serialization/ASTReaderDecl.cpp +++ b/clang/lib/Serialization/ASTReaderDecl.cpp @@ -2833,14 +2833,23 @@ void ASTDeclReader::attachPreviousDeclImpl(ASTReader &Reader, // If this declaration has an unresolved exception specification but the // previous declaration had a resolved one, resolve the exception - // specification now. + // specification now. If this declaration has a resolved exception + // specification but the previous declarations did not, apply our exception + // specification to all prior ones now. auto *FPT = FD->getType()->getAs(); auto *PrevFPT = PrevFD->getType()->getAs(); - if (FPT && PrevFPT && - isUnresolvedExceptionSpec(FPT->getExceptionSpecType()) && - !isUnresolvedExceptionSpec(PrevFPT->getExceptionSpecType())) { - Reader.Context.adjustExceptionSpec( - FD, PrevFPT->getExtProtoInfo().ExceptionSpec); + if (FPT && PrevFPT) { + bool WasUnresolved = isUnresolvedExceptionSpec(FPT->getExceptionSpecType()); + bool IsUnresolved = isUnresolvedExceptionSpec(PrevFPT->getExceptionSpecType()); + if (WasUnresolved && !IsUnresolved) { + Reader.Context.adjustExceptionSpec( + FD, PrevFPT->getExtProtoInfo().ExceptionSpec); + } else if (!WasUnresolved && IsUnresolved) { + FunctionProtoType::ExtProtoInfo EPI = FPT->getExtProtoInfo(); + for (FunctionDecl *PrevFDToUpdate = PrevFD; PrevFDToUpdate; + PrevFDToUpdate = PrevFDToUpdate->getPreviousDecl()) + Reader.Context.adjustExceptionSpec(PrevFDToUpdate, EPI.ExceptionSpec); + } } } } diff --git a/clang/test/Modules/Inputs/PR21687/a.h b/clang/test/Modules/Inputs/PR21687/a.h new file mode 100644 index 000000000000..023606eb35a7 --- /dev/null +++ b/clang/test/Modules/Inputs/PR21687/a.h @@ -0,0 +1 @@ +struct X { X(); virtual ~X(); }; diff --git a/clang/test/Modules/Inputs/PR21687/b.h b/clang/test/Modules/Inputs/PR21687/b.h new file mode 100644 index 000000000000..7085b1f67391 --- /dev/null +++ b/clang/test/Modules/Inputs/PR21687/b.h @@ -0,0 +1,2 @@ +#include "a.h" +X *n = new X; diff --git a/clang/test/Modules/Inputs/PR21687/c.h b/clang/test/Modules/Inputs/PR21687/c.h new file mode 100644 index 000000000000..5c5d555a3f07 --- /dev/null +++ b/clang/test/Modules/Inputs/PR21687/c.h @@ -0,0 +1,4 @@ +#include "a.h" +inline void f() { X x, y(x); } +#include "b.h" +X x, y(x); diff --git a/clang/test/Modules/Inputs/PR21687/module.modulemap b/clang/test/Modules/Inputs/PR21687/module.modulemap new file mode 100644 index 000000000000..77e0a89e39a0 --- /dev/null +++ b/clang/test/Modules/Inputs/PR21687/module.modulemap @@ -0,0 +1,3 @@ +module a { header "a.h" export * } +module b { header "b.h" export * } +module c { header "c.h" export * } diff --git a/clang/test/Modules/pr21687.cpp b/clang/test/Modules/pr21687.cpp new file mode 100644 index 000000000000..ad67489541d8 --- /dev/null +++ b/clang/test/Modules/pr21687.cpp @@ -0,0 +1,3 @@ +// RUN: rm -rf %t +// RUN: %clang_cc1 -fmodules -fmodules-cache-path=%t -I%S/Inputs/PR21687 -emit-llvm-only %s +#include "c.h" -- 2.34.1