'pure' and 'const' functions should also be marked nounwind. Migrate
test over from llvm/test/FrontendC++ and update others to account for
the change.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@137669 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGCall.cpp b/lib/CodeGen/CGCall.cpp
index 023dd22..dc3e702 100644
--- a/lib/CodeGen/CGCall.cpp
+++ b/lib/CodeGen/CGCall.cpp
@@ -739,10 +739,15 @@
 
     if (TargetDecl->hasAttr<NoReturnAttr>())
       FuncAttrs |= llvm::Attribute::NoReturn;
-    if (TargetDecl->hasAttr<ConstAttr>())
+
+    // 'const' and 'pure' attribute functions are also nounwind.
+    if (TargetDecl->hasAttr<ConstAttr>()) {
       FuncAttrs |= llvm::Attribute::ReadNone;
-    else if (TargetDecl->hasAttr<PureAttr>())
+      FuncAttrs |= llvm::Attribute::NoUnwind;
+    } else if (TargetDecl->hasAttr<PureAttr>()) {
       FuncAttrs |= llvm::Attribute::ReadOnly;
+      FuncAttrs |= llvm::Attribute::NoUnwind;
+    }
     if (TargetDecl->hasAttr<MallocAttr>())
       RetAttrs |= llvm::Attribute::NoAlias;
   }
diff --git a/test/CodeGen/libcalls.c b/test/CodeGen/libcalls.c
index 5ff684f..458c591 100644
--- a/test/CodeGen/libcalls.c
+++ b/test/CodeGen/libcalls.c
@@ -24,9 +24,9 @@
 // CHECK-YES: declare float @sqrtf(float)
 // CHECK-YES: declare double @sqrt(double)
 // CHECK-YES: declare x86_fp80 @sqrtl(x86_fp80)
-// CHECK-NO: declare float @sqrtf(float) readnone
-// CHECK-NO: declare double @sqrt(double) readnone
-// CHECK-NO: declare x86_fp80 @sqrtl(x86_fp80) readnone
+// CHECK-NO: declare float @sqrtf(float) nounwind readnone
+// CHECK-NO: declare double @sqrt(double) nounwind readnone
+// CHECK-NO: declare x86_fp80 @sqrtl(x86_fp80) nounwind readnone
 
 // CHECK-YES: define void @test_pow
 // CHECK-NO: define void @test_pow
diff --git a/test/CodeGen/struct-passing.c b/test/CodeGen/struct-passing.c
index 8e5c0ad..efb00ef 100644
--- a/test/CodeGen/struct-passing.c
+++ b/test/CodeGen/struct-passing.c
@@ -16,8 +16,8 @@
 
 void *ps[] = { f0, f1, f2, f3, f4, f5 };
 
-// CHECK: declare i32 @f0() readnone
-// CHECK: declare i32 @f1() readonly
+// CHECK: declare i32 @f0() nounwind readnone
+// CHECK: declare i32 @f1() nounwind readonly
 // CHECK: declare void @f2({{.*}} sret)
 // CHECK: declare void @f3({{.*}} sret)
 // CHECK: declare void @f4({{.*}} byval align 4)
diff --git a/test/CodeGenCXX/2009-05-04-PureConstNounwind.cpp b/test/CodeGenCXX/2009-05-04-PureConstNounwind.cpp
new file mode 100644
index 0000000..7089207
--- /dev/null
+++ b/test/CodeGenCXX/2009-05-04-PureConstNounwind.cpp
@@ -0,0 +1,8 @@
+// RUN: %clang_cc1 -fexceptions -emit-llvm %s -o - | grep nounwind | count 4
+int c(void) __attribute__((const));
+int p(void) __attribute__((pure));
+int t(void);
+
+int f(void) {
+  return c() + p() + t();
+}