danielkiss created this revision.
danielkiss added reviewers: chill, pcc, olista01, asl.
Herald added subscribers: cfe-commits, aheejin, kristof.beyls, sbc100.
Herald added a reviewer: jdoerfert.
Herald added a project: clang.

A runtime function needs the same arguments as normal function. 
Attributes of PAuth and BTI are added to the default arguments.
Function level attribute handling is adopted.
After this change the all runtime created functions like _clang_call_terminate
will get the default arguments including PAC/BTI if applicable.


Repository:
  rG LLVM Github Monorepo

https://reviews.llvm.org/D75181

Files:
  clang/lib/CodeGen/CGCall.cpp
  clang/lib/CodeGen/CodeGenModule.cpp
  clang/lib/CodeGen/TargetInfo.cpp
  clang/test/CodeGen/ignore-exceptions.cpp
  clang/test/CodeGenCXX/aarch64-branch-target_clang_call_terminate.cpp
  clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp
  clang/test/CodeGenCXX/dynamic-cast.cpp
  clang/test/CodeGenCXX/exceptions.cpp
  clang/test/CodeGenCXX/runtimecc.cpp
  clang/test/CodeGenCXX/wasm-eh.cpp
  clang/test/CodeGenObjC/arc.m
  clang/test/CodeGenObjC/attr-objc-runtime-visible.m
  clang/test/CodeGenObjC/class-stubs.m
  clang/test/CodeGenObjC/nonlazy-msgSend.m
  clang/test/CodeGenObjC/objc-literal-debugger-test.m
  clang/test/OpenMP/barrier_codegen.cpp
  clang/test/OpenMP/nvptx_parallel_codegen.cpp
  clang/test/OpenMP/openmp_win_codegen.cpp
  clang/test/PCH/objc_container.m

Index: clang/test/PCH/objc_container.m
===================================================================
--- clang/test/PCH/objc_container.m
+++ clang/test/PCH/objc_container.m
@@ -22,4 +22,4 @@
 // CHECK-IR: ret void
 
 // CHECK-IR: attributes #0 = { noinline nounwind {{.*}} }
-// CHECK-IR: attributes #1 = { nonlazybind }
+// CHECK-IR: attributes #1 = { nonlazybind {{.*}} }
Index: clang/test/OpenMP/openmp_win_codegen.cpp
===================================================================
--- clang/test/OpenMP/openmp_win_codegen.cpp
+++ clang/test/OpenMP/openmp_win_codegen.cpp
@@ -61,9 +61,9 @@
 // CHECK-NEXT: call void @__kmpc_end_critical(%struct.ident_t* {{.*}}@0, i32 [[GID]],
 // CHECK-NEXT: cleanupret from {{.*}} unwind label %[[CATCHTERM:[^ ]+]]
 // CHECK:      cleanuppad within none []
-// CHECK-NEXT: call void @"?terminate@@YAXXZ"() #5 [ "funclet"(token %{{.*}}) ]
+// CHECK-NEXT: call void @"?terminate@@YAXXZ"() #6 [ "funclet"(token %{{.*}}) ]
 // CHECK-NEXT: unreachable
 // CHECK:      [[CATCHTERM]]
 // CHECK-NEXT: cleanuppad within [[CATCHPAD]] []
-// CHECK-NEXT: call void @"?terminate@@YAXXZ"() #5 [ "funclet"(token %{{.*}}) ]
+// CHECK-NEXT: call void @"?terminate@@YAXXZ"() #6 [ "funclet"(token %{{.*}}) ]
 // CHECK-NEXT: unreachable
Index: clang/test/OpenMP/nvptx_parallel_codegen.cpp
===================================================================
--- clang/test/OpenMP/nvptx_parallel_codegen.cpp
+++ clang/test/OpenMP/nvptx_parallel_codegen.cpp
@@ -321,7 +321,7 @@
 // CHECK: call void @__kmpc_barrier(%struct.ident_t* @{{.+}}, i32 %{{.+}}) #[[#CONVERGENT:]]
 // CHECK: ret void
 
-// CHECK: declare void @__kmpc_barrier(%struct.ident_t*, i32) #[[#CONVERGENT]]
+// CHECK: declare void @__kmpc_barrier(%struct.ident_t*, i32) #[[#CONVERGENT_DEC:]]
 
 // CHECK-LABEL: define {{.*}}void {{@__omp_offloading_.+template.+l55}}_worker()
 // CHECK-LABEL: define {{.*}}void {{@__omp_offloading_.+template.+l55}}(
@@ -369,9 +369,11 @@
 // CHECK:  br label
 
 
-// CHECK: declare i32 @__kmpc_warp_active_thread_mask() #[[#CONVERGENT:]]
-// CHECK: declare void @__kmpc_syncwarp(i32) #[[#CONVERGENT:]]
+// CHECK: declare i32 @__kmpc_warp_active_thread_mask() #
+// CHECK: declare void @__kmpc_syncwarp(i32) #
+
+// CHECK: attributes #[[#CONVERGENT_DEC]] = { convergent {{.*}} }
+// CHECK: attributes #[[#CONVERGENT]] = { convergent }
 
-// CHECK: attributes #[[#CONVERGENT]] = {{.*}} convergent {{.*}}
 
 #endif
Index: clang/test/OpenMP/barrier_codegen.cpp
===================================================================
--- clang/test/OpenMP/barrier_codegen.cpp
+++ clang/test/OpenMP/barrier_codegen.cpp
@@ -42,8 +42,7 @@
   return tmain(argc) + tmain(argv[0][0]) + a;
 }
 
-// CLANGCG:            declare i32 @__kmpc_global_thread_num(%struct.ident_t*)
-// CLANGCG-NOT:        #
+// CLANGCG:            declare i32 @__kmpc_global_thread_num(%struct.ident_t*) #
 // IRBUILDER:          ; Function Attrs: nounwind
 // IRBUILDER-NEXT:     declare i32 @__kmpc_global_thread_num(%struct.ident_t*) #
 // IRBUILDER_OPT:      ; Function Attrs: nofree nosync nounwind readonly
Index: clang/test/CodeGenObjC/objc-literal-debugger-test.m
===================================================================
--- clang/test/CodeGenObjC/objc-literal-debugger-test.m
+++ clang/test/CodeGenObjC/objc-literal-debugger-test.m
@@ -52,4 +52,4 @@
 
 // CHECK: declare i8* @objc_msgSend(i8*, i8*, ...) [[NLB:#[0-9]+]]
 
-// CHECK: attributes [[NLB]] = { nonlazybind }
+// CHECK: attributes [[NLB]] = { nonlazybind {{.*}} }
Index: clang/test/CodeGenObjC/nonlazy-msgSend.m
===================================================================
--- clang/test/CodeGenObjC/nonlazy-msgSend.m
+++ clang/test/CodeGenObjC/nonlazy-msgSend.m
@@ -5,4 +5,4 @@
   [x foo];
 }
 
-// CHECK: attributes [[NLB]] = { nonlazybind }
+// CHECK: attributes [[NLB]] = { nonlazybind {{.*}}}
Index: clang/test/CodeGenObjC/class-stubs.m
===================================================================
--- clang/test/CodeGenObjC/class-stubs.m
+++ clang/test/CodeGenObjC/class-stubs.m
@@ -81,4 +81,4 @@
 @end
 
 // -- calls to objc_loadClassRef() are readnone
-// CHECK: attributes [[ATTRLIST]] = { nounwind nonlazybind readnone }
+// CHECK: attributes [[ATTRLIST]] = { nounwind nonlazybind readnone {{.*}} }
Index: clang/test/CodeGenObjC/attr-objc-runtime-visible.m
===================================================================
--- clang/test/CodeGenObjC/attr-objc-runtime-visible.m
+++ clang/test/CodeGenObjC/attr-objc-runtime-visible.m
@@ -14,6 +14,6 @@
 // CHECK: [[CLASSNAME:@.*]] = private unnamed_addr constant [22 x i8] c"MyRuntimeVisibleClass
 // CHECK: define i8* @getClass() #0 {
 Class getClass(void) {
-  // CHECK: call i8* @objc_lookUpClass(i8* getelementptr inbounds ([22 x i8], [22 x i8]* [[CLASSNAME]], i32 0, i32 0)) #2
+  // CHECK: call i8* @objc_lookUpClass(i8* getelementptr inbounds ([22 x i8], [22 x i8]* [[CLASSNAME]], i32 0, i32 0)) #3
   return [A class];
 }
Index: clang/test/CodeGenObjC/arc.m
===================================================================
--- clang/test/CodeGenObjC/arc.m
+++ clang/test/CodeGenObjC/arc.m
@@ -1557,6 +1557,6 @@
   getAggDtor();
 }
 
-// ARC-ALIEN: attributes [[NLB]] = { nonlazybind }
-// ARC-NATIVE: attributes [[NLB]] = { nonlazybind }
+// ARC-ALIEN: attributes [[NLB]] = { nonlazybind {{.*}}}
+// ARC-NATIVE: attributes [[NLB]] = { nonlazybind {{.*}}}
 // CHECK: attributes [[NUW]] = { nounwind }
Index: clang/test/CodeGenCXX/wasm-eh.cpp
===================================================================
--- clang/test/CodeGenCXX/wasm-eh.cpp
+++ clang/test/CodeGenCXX/wasm-eh.cpp
@@ -35,7 +35,7 @@
 // CHECK-NEXT:   %[[EXN:.*]] = call i8* @llvm.wasm.get.exception(token %[[CATCHPAD]])
 // CHECK-NEXT:   store i8* %[[EXN]], i8** %exn.slot
 // CHECK-NEXT:   %[[SELECTOR:.*]] = call i32 @llvm.wasm.get.ehselector(token %[[CATCHPAD]])
-// CHECK-NEXT:   %[[TYPEID:.*]] = call i32 @llvm.eh.typeid.for(i8* bitcast (i8** @_ZTIi to i8*)) #2
+// CHECK-NEXT:   %[[TYPEID:.*]] = call i32 @llvm.eh.typeid.for(i8* bitcast (i8** @_ZTIi to i8*)) #3
 // CHECK-NEXT:   %[[MATCHES:.*]] = icmp eq i32 %[[SELECTOR]], %[[TYPEID]]
 // CHECK-NEXT:   br i1 %[[MATCHES]], label %[[CATCH_INT_BB:.*]], label %[[CATCH_FALLTHROUGH_BB:.*]]
 
@@ -53,7 +53,7 @@
 // CHECK-NEXT:   br label %[[TRY_CONT_BB:.*]]
 
 // CHECK: [[CATCH_FALLTHROUGH_BB]]
-// CHECK-NEXT:   %[[TYPEID:.*]] = call i32 @llvm.eh.typeid.for(i8* bitcast (i8** @_ZTId to i8*)) #2
+// CHECK-NEXT:   %[[TYPEID:.*]] = call i32 @llvm.eh.typeid.for(i8* bitcast (i8** @_ZTId to i8*)) #3
 // CHECK-NEXT:   %[[MATCHES:.*]] = icmp eq i32 %[[SELECTOR]], %[[TYPEID]]
 // CHECK-NEXT:   br i1 %[[MATCHES]], label %[[CATCH_FLOAT_BB:.*]], label %[[RETHROW_BB:.*]]
 
Index: clang/test/CodeGenCXX/runtimecc.cpp
===================================================================
--- clang/test/CodeGenCXX/runtimecc.cpp
+++ clang/test/CodeGenCXX/runtimecc.cpp
@@ -22,11 +22,11 @@
   A global;
 // CHECK-LABEL:    define internal void @__cxx_global_var_init()
 // CHECK:      call [[A]]* @_ZN5test01AC1Ev([[A]]* @_ZN5test06globalE)
-// CHECK-NEXT: call i32 @__cxa_atexit(void (i8*)* bitcast ([[A]]* ([[A]]*)* @_ZN5test01AD1Ev to void (i8*)*), i8* bitcast ([[A]]* @_ZN5test06globalE to i8*), i8* @__dso_handle) [[NOUNWIND:#[0-9]+]]
+// CHECK-NEXT: call i32 @__cxa_atexit(void (i8*)* bitcast ([[A]]* ([[A]]*)* @_ZN5test01AD1Ev to void (i8*)*), i8* bitcast ([[A]]* @_ZN5test06globalE to i8*), i8* @__dso_handle) [[NOUNWIND_CALL:#[0-9]+]]
 // CHECK-NEXT: ret void
 }
 
-// CHECK: declare i32 @__cxa_atexit(void (i8*)*, i8*, i8*) [[NOUNWIND]]
+// CHECK: declare i32 @__cxa_atexit(void (i8*)*, i8*, i8*) [[NOUNWIND_DEC:#[0-9]+]]
 
 namespace test1 {
   void test() {
@@ -34,7 +34,7 @@
   }
 
 // CHECK-LABEL:    define void @_ZN5test14testEv()
-// CHECK:      [[T0:%.*]] = call i8* @__cxa_allocate_exception(i32 4) [[NOUNWIND]]
+// CHECK:      [[T0:%.*]] = call i8* @__cxa_allocate_exception(i32 4) [[NOUNWIND_CALL]]
 // CHECK-NEXT: [[T1:%.*]] = bitcast i8* [[T0]] to i32*
 // CHECK-NEXT: store i32 0, i32* [[T1]]
 // CHECK-NEXT: call void @__cxa_throw(i8* [[T0]], i8* bitcast (i8** @_ZTIi to i8*), i8* null) [[NORETURN:#[0-9]+]]
@@ -49,5 +49,6 @@
 // CHECK:   call void @__cxx_global_var_init()
 
 
-// CHECK: attributes [[NOUNWIND]] = { nounwind }
+// CHECK: attributes [[NOUNWIND_DEC]] = { nounwind {{.*}} }
+// CHECK: attributes [[NOUNWIND_CALL]] = { nounwind }
 // CHECK: attributes [[NORETURN]] = { noreturn }
Index: clang/test/CodeGenCXX/exceptions.cpp
===================================================================
--- clang/test/CodeGenCXX/exceptions.cpp
+++ clang/test/CodeGenCXX/exceptions.cpp
@@ -594,4 +594,4 @@
   // CHECK11:       call void @_ZN6test121AdlEPvS1_(i8* [[PTR]], i8* [[PTR]])
 }
 
-// CHECK98: attributes [[NI_NR_NUW]] = { noinline noreturn nounwind }
+// CHECK98: attributes [[NI_NR_NUW]] = { noinline noreturn nounwind {{.*}}}
Index: clang/test/CodeGenCXX/dynamic-cast.cpp
===================================================================
--- clang/test/CodeGenCXX/dynamic-cast.cpp
+++ clang/test/CodeGenCXX/dynamic-cast.cpp
@@ -20,5 +20,5 @@
 
 // CHECK: declare i8* @__dynamic_cast(i8*, i8*, i8*, i64) [[NUW_RO:#[0-9]+]]
 
-// CHECK: attributes [[NUW_RO]] = { nounwind readonly }
+// CHECK: attributes [[NUW_RO]] = { nounwind readonly {{.*}}}
 // CHECK: attributes [[NR]] = { noreturn }
Index: clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp
===================================================================
--- clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp
+++ clang/test/CodeGenCXX/cxx1z-aligned-allocation.cpp
@@ -54,11 +54,11 @@
 void *a1(long n) { return new A[n]; }
 
 // CHECK-LABEL: define {{.*}} @_Z2a2P1A(
-// CHECK: call void @_ZdlPvmSt11align_val_t(i8* %{{.*}}, i64 512, i64 32) #9
+// CHECK: call void @_ZdlPvmSt11align_val_t(i8* %{{.*}}, i64 512, i64 32) #10
 void a2(A *p) { delete p; }
 
 // CHECK-LABEL: define {{.*}} @_Z2a3P1A(
-// CHECK: call void @_ZdaPvSt11align_val_t(i8* %{{.*}}, i64 32) #9
+// CHECK: call void @_ZdaPvSt11align_val_t(i8* %{{.*}}, i64 32) #10
 void a3(A *p) { delete[] p; }
 
 
Index: clang/test/CodeGenCXX/aarch64-branch-target_clang_call_terminate.cpp
===================================================================
--- /dev/null
+++ clang/test/CodeGenCXX/aarch64-branch-target_clang_call_terminate.cpp
@@ -0,0 +1,34 @@
+// RUN: %clang  -target aarch64-arm-none-eabi -S -emit-llvm -mbranch-protection=none -c %s -o - | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-NONE
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=standard %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-BTI
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=pac-ret %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-PARTIAL
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=pac-ret+leaf %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-NONE
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=pac-ret+b-key %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-NONE
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=pac-ret+b-key+leaf %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-NONE
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=bti %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-BTI
+// RUN: %clang -target aarch64-arm-none-eabi -S -emit-llvm -o - -mbranch-protection=pac-ret+b-key+leaf+bti %s | \
+// RUN: FileCheck %s --check-prefix=CHECK --check-prefix=CHECK-BTI
+
+void a();
+void d();
+
+void c() {
+  try {
+    d();
+  } catch (...) {
+    a();
+  }
+}
+
+// CHECK: ; Function Attrs: noinline noreturn nounwind
+// CHECK: define linkonce_odr hidden void @__clang_call_terminate(i8* %0) #[[ATTR:[0-9]*]] comdat {
+
+// CHECK-NONE-NOT: attributes #[[ATTR]] = {{{.*}} "branch-target-enforcement" {{.*}} }
+// CHECK-NONE: attributes #[[ATTR]] = { noinline noreturn nounwind {{.*}} }
+// CHECK-BTI:  attributes #[[ATTR]] = { noinline noreturn nounwind "branch-target-enforcement" {{.*}} }
Index: clang/test/CodeGen/ignore-exceptions.cpp
===================================================================
--- clang/test/CodeGen/ignore-exceptions.cpp
+++ clang/test/CodeGen/ignore-exceptions.cpp
@@ -12,10 +12,10 @@
   } catch(...) {
   }
 // CHECK:  %a = alloca %struct.A, align 1
-// CHECK:  %exception = call i8* @__cxa_allocate_exception(i64 4) #1
+// CHECK:  %exception = call i8* @__cxa_allocate_exception(i64 4) #2
 // CHECK:  %0 = bitcast i8* %exception to i32*
 // CHECK:  store i32 1, i32* %0, align 16
-// CHECK:  call void @__cxa_throw(i8* %exception, i8* bitcast (i8** @_ZTIi to i8*), i8* null) #2
+// CHECK:  call void @__cxa_throw(i8* %exception, i8* bitcast (i8** @_ZTIi to i8*), i8* null) #3
 // CHECK:  unreachable
 
 // CHECK-NOT: invoke
Index: clang/lib/CodeGen/TargetInfo.cpp
===================================================================
--- clang/lib/CodeGen/TargetInfo.cpp
+++ clang/lib/CodeGen/TargetInfo.cpp
@@ -5134,10 +5134,18 @@
                     Key == CodeGenOptions::SignReturnAddressKeyValue::AKey
                         ? "a_key"
                         : "b_key");
+    } else {
+      Fn->removeAttribute(llvm::AttributeList::FunctionIndex,
+                          "sign-return-address");
+      Fn->removeAttribute(llvm::AttributeList::FunctionIndex,
+                          "sign-return-address-key");
     }
 
     if (BranchTargetEnforcement)
       Fn->addFnAttr("branch-target-enforcement");
+    else
+      Fn->removeAttribute(llvm::AttributeList::FunctionIndex,
+                          "branch-target-enforcement");
   }
   llvm::Value *decodeReturnAddress(CodeGen::CodeGenFunction &CGF,
                                    llvm::Value *Address) const override {
Index: clang/lib/CodeGen/CodeGenModule.cpp
===================================================================
--- clang/lib/CodeGen/CodeGenModule.cpp
+++ clang/lib/CodeGen/CodeGenModule.cpp
@@ -3390,6 +3390,8 @@
     if (F->empty()) {
       F->setCallingConv(getRuntimeCC());
 
+      AddDefaultFnAttrs(*F);
+
       // In Windows Itanium environments, try to mark runtime functions
       // dllimport. For Mingw and MSVC, don't. We don't really know if the user
       // will link their standard library statically or dynamically. Marking
Index: clang/lib/CodeGen/CGCall.cpp
===================================================================
--- clang/lib/CodeGen/CGCall.cpp
+++ clang/lib/CodeGen/CGCall.cpp
@@ -1823,6 +1823,23 @@
     std::tie(Var, Value) = Attr.split('=');
     FuncAttrs.addAttribute(Var, Value);
   }
+
+  if (CodeGenOpts.BranchTargetEnforcement) {
+    FuncAttrs.addAttribute("branch-target-enforcement");
+  }
+
+  auto RASignKind = CodeGenOpts.getSignReturnAddress();
+  if (RASignKind != CodeGenOptions::SignReturnAddressScope::None) {
+    FuncAttrs.addAttribute(
+        "sign-return-address",
+        RASignKind == CodeGenOptions::SignReturnAddressScope::All ? "all"
+                                                                  : "non-leaf");
+    auto RASignKey = CodeGenOpts.getSignReturnAddressKey();
+    FuncAttrs.addAttribute(
+        "sign-return-address-key",
+        RASignKey == CodeGenOptions::SignReturnAddressKeyValue::AKey ? "a_key"
+                                                                     : "b_key");
+  }
 }
 
 void CodeGenModule::AddDefaultFnAttrs(llvm::Function &F) {
_______________________________________________
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to