Index: lib/CodeGen/CGObjC.cpp =================================================================== --- lib/CodeGen/CGObjC.cpp +++ lib/CodeGen/CGObjC.cpp @@ -2906,7 +2906,9 @@ llvm::Function::Create(LTy, llvm::GlobalValue::InternalLinkage, "__assign_helper_atomic_property_", &CGM.getModule()); - + + CGM.SetInternalFunctionAttributes(nullptr, Fn, FI); + StartFunction(FD, C.VoidTy, Fn, FI, args); DeclRefExpr DstExpr(&dstDecl, false, DestTy, @@ -2985,6 +2987,8 @@ llvm::Function::Create(LTy, llvm::GlobalValue::InternalLinkage, "__copy_helper_atomic_property_", &CGM.getModule()); + CGM.SetInternalFunctionAttributes(nullptr, Fn, FI); + StartFunction(FD, C.VoidTy, Fn, FI, args); DeclRefExpr SrcExpr(&srcDecl, false, SrcTy, Index: lib/CodeGen/CGOpenMPRuntime.cpp =================================================================== --- lib/CodeGen/CGOpenMPRuntime.cpp +++ lib/CodeGen/CGOpenMPRuntime.cpp @@ -1490,7 +1490,7 @@ auto *Fn = llvm::Function::Create( CGM.getTypes().GetFunctionType(CGFI), llvm::GlobalValue::InternalLinkage, ".omp.copyprivate.copy_func", &CGM.getModule()); - CGM.SetLLVMFunctionAttributes(/*D=*/nullptr, CGFI, Fn); + CGM.SetInternalFunctionAttributes(/*D=*/nullptr, Fn, CGFI); CodeGenFunction CGF(CGM); CGF.StartFunction(GlobalDecl(), C.VoidTy, Fn, CGFI, Args); // Dest = (void*[n])(LHSArg); @@ -2048,7 +2048,7 @@ auto *TaskEntry = llvm::Function::Create(TaskEntryTy, llvm::GlobalValue::InternalLinkage, ".omp_task_entry.", &CGM.getModule()); - CGM.SetLLVMFunctionAttributes(/*D=*/nullptr, TaskEntryFnInfo, TaskEntry); + CGM.SetInternalFunctionAttributes(/*D=*/nullptr, TaskEntry, TaskEntryFnInfo); CodeGenFunction CGF(CGM); CGF.disableDebugInfo(); CGF.StartFunction(GlobalDecl(), KmpInt32Ty, TaskEntry, TaskEntryFnInfo, Args); @@ -2115,7 +2115,8 @@ auto *DestructorFn = llvm::Function::Create(DestructorFnTy, llvm::GlobalValue::InternalLinkage, ".omp_task_destructor.", &CGM.getModule()); - CGM.SetLLVMFunctionAttributes(/*D=*/nullptr, DestructorFnInfo, DestructorFn); + CGM.SetInternalFunctionAttributes(/*D=*/nullptr, DestructorFn, + DestructorFnInfo); CodeGenFunction CGF(CGM); CGF.disableDebugInfo(); CGF.StartFunction(GlobalDecl(), KmpInt32Ty, DestructorFn, DestructorFnInfo, @@ -2191,8 +2192,8 @@ auto *TaskPrivatesMap = llvm::Function::Create( TaskPrivatesMapTy, llvm::GlobalValue::InternalLinkage, ".omp_task_privates_map.", &CGM.getModule()); - CGM.SetLLVMFunctionAttributes(/*D=*/nullptr, TaskPrivatesMapFnInfo, - TaskPrivatesMap); + CGM.SetInternalFunctionAttributes(/*D=*/nullptr, TaskPrivatesMap, + TaskPrivatesMapFnInfo); TaskPrivatesMap->addFnAttr(llvm::Attribute::AlwaysInline); CodeGenFunction CGF(CGM); CGF.disableDebugInfo(); @@ -2693,7 +2694,7 @@ auto *Fn = llvm::Function::Create( CGM.getTypes().GetFunctionType(CGFI), llvm::GlobalValue::InternalLinkage, ".omp.reduction.reduction_func", &CGM.getModule()); - CGM.SetLLVMFunctionAttributes(/*D=*/nullptr, CGFI, Fn); + CGM.SetInternalFunctionAttributes(/*D=*/nullptr, Fn, CGFI); CodeGenFunction CGF(CGM); CGF.StartFunction(GlobalDecl(), C.VoidTy, Fn, CGFI, Args); Index: test/CodeGenObjCXX/property-object-reference-2.mm =================================================================== --- test/CodeGenObjCXX/property-object-reference-2.mm +++ test/CodeGenObjCXX/property-object-reference-2.mm @@ -29,7 +29,7 @@ @synthesize MyProperty1 = _cppObject1; @end -// CHECK-LABEL: define internal void @__copy_helper_atomic_property_( +// CHECK-LABEL: define internal void @__copy_helper_atomic_property_(%struct.TCPPObject*, %struct.TCPPObject*) # // CHECK: [[TWO:%.*]] = load %struct.TCPPObject*, %struct.TCPPObject** [[ADDR:%.*]], align 8 // CHECK: [[THREE:%.*]] = load %struct.TCPPObject*, %struct.TCPPObject** [[ADDR1:%.*]], align 8 // CHECK: [[CALL:%.*]] = call i32 @_Z7DEFAULTv() @@ -43,7 +43,7 @@ // CHECK: call void @objc_copyCppObjectAtomic(i8* [[THREE]], i8* [[TWO]], i8* bitcast (void (%struct.TCPPObject*, %struct.TCPPObject*)* @__copy_helper_atomic_property_ to i8*)) // CHECK: ret void -// CHECK-LABEL: define internal void @__assign_helper_atomic_property_( +// CHECK-LABEL: define internal void @__assign_helper_atomic_property_(%struct.TCPPObject*, %struct.TCPPObject*) # // CHECK: [[TWO:%.*]] = load %struct.TCPPObject*, %struct.TCPPObject** [[ADDR:%.*]], align 8 // CHECK: [[THREE:%.*]] = load %struct.TCPPObject*, %struct.TCPPObject** [[ADDR1:%.*]], align 8 // CHECK: [[CALL:%.*]] = call dereferenceable({{[0-9]+}}) %struct.TCPPObject* @_ZN10TCPPObjectaSERKS_(%struct.TCPPObject* [[TWO]], %struct.TCPPObject* dereferenceable({{[0-9]+}}) [[THREE]]) Index: test/OpenMP/function-attr.cpp =================================================================== --- /dev/null +++ test/OpenMP/function-attr.cpp @@ -0,0 +1,54 @@ +// RUN: %clang_cc1 -fopenmp -x c++ -triple x86_64-apple-darwin10 -stack-protector 2 -emit-llvm -o - %s | FileCheck %s + +// Check that function attributes are added to the OpenMP runtime functions. + +template +struct S { + T f; + S(T a) : f(a) {} + S() : f() {} + operator T() { return T(); } + ~S() {} +}; + +// CHECK: define internal void @.omp.copyprivate.copy_func(i8*, i8*) [[ATTR0:#[0-9]+]] { + +void foo0(); + +int foo1() { + char a; + +#pragma omp parallel + a = 2; +#pragma omp single copyprivate(a) + foo0(); + + return 0; +} + +// CHECK: define internal void @.omp_task_privates_map.({{.*}}) [[ATTR3:#[0-9]+]] { +// CHECK: define internal i32 @.omp_task_entry.({{.*}}) [[ATTR0]] { +// CHECK: define internal i32 @.omp_task_destructor.({{.*}}) [[ATTR0]] { + +int foo2() { + S s_arr[] = {1, 2}; + S var(3); +#pragma omp task private(s_arr, var) + s_arr[0] = var; + return 0; +} + +// CHECK: define internal void @.omp.reduction.reduction_func(i8*, i8*) [[ATTR0]] { + +float foo3(int n, float *a, float *b) { + int i; + float result; + +#pragma omp parallel for private(i) reduction(+:result) + for (i=0; i < n; i++) + result = result + (a[i] * b[i]); + return result; +} + +// CHECK: attributes [[ATTR0]] = {{{.*}} sspstrong {{.*}}} +// CHECK: attributes [[ATTR3]] = {{{.*}} sspstrong {{.*}}}