[PATCH] D86841: [clang] Add mayprogress and llvm.loop.mustprogress attribute deduction
atmnpatel updated this revision to Diff 291471. atmnpatel added a comment. Flipped direction. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D86841/new/ https://reviews.llvm.org/D86841 Files: clang/lib/CodeGen/CGLoopInfo.cpp clang/lib/CodeGen/CGLoopInfo.h clang/lib/CodeGen/CGStmt.cpp clang/lib/CodeGen/CodeGenFunction.cpp clang/test/CodeGen/address-safety-attr-flavors.cpp clang/test/CodeGen/address-safety-attr.cpp clang/test/CodeGen/attr-noprogress.c clang/test/CodeGen/attr-noprogress.cpp clang/test/CodeGen/memtag-attr.cpp clang/test/CodeGen/no-builtin.cpp clang/test/CodeGenCXX/cxx11-trivial-initializer-struct.cpp clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp clang/test/CodeGenCXX/thunks-ehspec.cpp clang/test/CodeGenCXX/thunks.cpp clang/test/OpenMP/simd_metadata.c clang/test/Profile/c-unprofiled-blocks.c clang/test/utils/update_cc_test_checks/Inputs/basic-cplusplus.cpp.expected clang/test/utils/update_cc_test_checks/Inputs/check-attributes.cpp.funcattrs.expected Index: clang/test/utils/update_cc_test_checks/Inputs/check-attributes.cpp.funcattrs.expected === --- clang/test/utils/update_cc_test_checks/Inputs/check-attributes.cpp.funcattrs.expected +++ clang/test/utils/update_cc_test_checks/Inputs/check-attributes.cpp.funcattrs.expected @@ -11,7 +11,7 @@ struct RT Z; }; -// CHECK: Function Attrs: noinline nounwind optnone +// CHECK: Function Attrs: noinline nounwind optnone mustprogress // CHECK-LABEL: @_Z3fooP2ST( // CHECK-NEXT: entry: // CHECK-NEXT:[[S_ADDR:%.*]] = alloca %struct.ST*, align 8 Index: clang/test/utils/update_cc_test_checks/Inputs/basic-cplusplus.cpp.expected === --- clang/test/utils/update_cc_test_checks/Inputs/basic-cplusplus.cpp.expected +++ clang/test/utils/update_cc_test_checks/Inputs/basic-cplusplus.cpp.expected @@ -44,7 +44,7 @@ // CHECK-NEXT:[[THIS_ADDR:%.*]] = alloca %class.Foo*, align 8 // CHECK-NEXT:store %class.Foo* [[THIS:%.*]], %class.Foo** [[THIS_ADDR]], align 8 // CHECK-NEXT:[[THIS1:%.*]] = load %class.Foo*, %class.Foo** [[THIS_ADDR]], align 8 -// CHECK-NEXT:call void @_ZN3FooD2Ev(%class.Foo* [[THIS1]]) [[ATTR2:#.*]] +// CHECK-NEXT:call void @_ZN3FooD2Ev(%class.Foo* [[THIS1]]) [[ATTR3:#.*]] // CHECK-NEXT:ret void // Foo::~Foo() {} @@ -70,7 +70,7 @@ // CHECK-NEXT:call void @_ZN3FooC1Ei(%class.Foo* [[F]], i32 1) // CHECK-NEXT:[[CALL:%.*]] = call i32 @_ZNK3Foo23function_defined_inlineEi(%class.Foo* [[F]], i32 2) // CHECK-NEXT:[[CALL1:%.*]] = call i32 @_ZNK3Foo28function_defined_out_of_lineEi(%class.Foo* [[F]], i32 3) -// CHECK-NEXT:call void @_ZN3FooD1Ev(%class.Foo* [[F]]) [[ATTR2]] +// CHECK-NEXT:call void @_ZN3FooD1Ev(%class.Foo* [[F]]) [[ATTR3]] // CHECK-NEXT:ret i32 0 // int main() { Index: clang/test/Profile/c-unprofiled-blocks.c === --- clang/test/Profile/c-unprofiled-blocks.c +++ clang/test/Profile/c-unprofiled-blocks.c @@ -16,7 +16,7 @@ // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} while (--i) {} - // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} + // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}, !llvm.loop [[LOOP1:!.*]] do {} while (i++ < 75); // PGOUSE: switch {{.*}} [ @@ -46,7 +46,7 @@ // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} while (--i) {} -// PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} +// PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}, !llvm.loop [[LOOP2:!.*]] do {} while (i++ < 75); // PGOUSE: switch {{.*}} [ Index: clang/test/OpenMP/simd_metadata.c === --- clang/test/OpenMP/simd_metadata.c +++ clang/test/OpenMP/simd_metadata.c @@ -137,7 +137,8 @@ } // CHECK: store float {{.+}}, float* {{.+}}, align {{.+}}, !llvm.access.group ![[ACCESS_GROUP_13:[0-9]+]] } -// CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER:![0-9]+]] + // CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER_INNER:![0-9]+]] + // CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER:![0-9]+]] } // Metadata for h1: Index: clang/test/CodeGenCXX/thunks.cpp === --- clang/test/CodeGenCXX/thunks.cpp +++ clang/test/CodeGenCXX/thunks.cpp @@ -529,7 +529,7 @@ // CHECK-NONOPT-LABEL: define linkonce_odr void @_ZThn8_N6Test101C3fooEv // Checking with opt -// CHECK-OPT-LABEL: define internal void @_ZThn8_N6Test4B12_GLOBAL__N_11C1fEv(%"struct.Test4B::(anonymous namespace)::C"* %this) unnamed_addr #0 align 2 +// CHECK-OPT-LABEL: define internal void @_ZThn8_N6Test4B12_GLOBAL__N_11C1fEv(%"struct.Test4B::(anonymous namespace)::C"* %this)
[PATCH] D86841: [clang] Add mayprogress and llvm.loop.mustprogress attribute deduction
atmnpatel updated this revision to Diff 291249. atmnpatel added a comment. More tightly follows both the C and C++ standards. `maynotprogress` is only added to C functions when compiled with C11 or later. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D86841/new/ https://reviews.llvm.org/D86841 Files: clang/lib/CodeGen/CGLoopInfo.cpp clang/lib/CodeGen/CGLoopInfo.h clang/lib/CodeGen/CGStmt.cpp clang/lib/CodeGen/CodeGenFunction.cpp clang/test/CodeGen/attr-noprogress.c clang/test/CodeGen/attr-noprogress.cpp clang/test/CodeGen/unwind-attr.c clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp clang/test/CodeGenObjC/class-stubs.m clang/test/CodeGenObjC/gnu-exceptions.m clang/test/OpenMP/simd_metadata.c clang/test/Profile/c-unprofiled-blocks.c Index: clang/test/Profile/c-unprofiled-blocks.c === --- clang/test/Profile/c-unprofiled-blocks.c +++ clang/test/Profile/c-unprofiled-blocks.c @@ -16,7 +16,7 @@ // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} while (--i) {} - // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} + // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}, !llvm.loop [[LOOP1:!.*]] do {} while (i++ < 75); // PGOUSE: switch {{.*}} [ @@ -46,7 +46,7 @@ // PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} while (--i) {} -// PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}{{$}} +// PGOUSE: br i1 %{{[^,]*}}, label %{{[^,]*}}, label %{{[^,]*}}, !llvm.loop [[LOOP2:!.*]] do {} while (i++ < 75); // PGOUSE: switch {{.*}} [ Index: clang/test/OpenMP/simd_metadata.c === --- clang/test/OpenMP/simd_metadata.c +++ clang/test/OpenMP/simd_metadata.c @@ -137,7 +137,8 @@ } // CHECK: store float {{.+}}, float* {{.+}}, align {{.+}}, !llvm.access.group ![[ACCESS_GROUP_13:[0-9]+]] } -// CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER:![0-9]+]] + // CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER_INNER:![0-9]+]] + // CHECK: br label %{{.+}}, !llvm.loop [[LOOP_H3_HEADER:![0-9]+]] } // Metadata for h1: Index: clang/test/CodeGenObjC/gnu-exceptions.m === --- clang/test/CodeGenObjC/gnu-exceptions.m +++ clang/test/CodeGenObjC/gnu-exceptions.m @@ -32,4 +32,4 @@ log(1); } -// CHECK: attributes [[TF]] = { noinline optnone "{{.*}} } +// CHECK: attributes [[TF]] = { noinline optnone maynotprogress "{{.*}} } Index: clang/test/CodeGenObjC/class-stubs.m === --- clang/test/CodeGenObjC/class-stubs.m +++ clang/test/CodeGenObjC/class-stubs.m @@ -55,7 +55,7 @@ + (void) anotherClassMethod { [super classMethod]; } -// CHECK-LABEL: define internal void @"\01+[Derived(MyCategory) anotherClassMethod]"(i8* %self, i8* %_cmd) #0 { +// CHECK-LABEL: define internal void @"\01+[Derived(MyCategory) anotherClassMethod]"(i8* %self, i8* %_cmd) #3 { // CHECK-NEXT: entry: // CHECK:[[SUPER:%.*]] = alloca %struct._objc_super, align 8 // CHECK:[[METACLASS_REF:%.*]] = load %struct._class_t*, %struct._class_t** @"OBJC_CLASSLIST_SUP_REFS_$_", align 8 @@ -68,7 +68,7 @@ - (void) anotherInstanceMethod { [super instanceMethod]; } -// CHECK-LABEL: define internal void @"\01-[Derived(MyCategory) anotherInstanceMethod]"(%0* %self, i8* %_cmd) #0 { +// CHECK-LABEL: define internal void @"\01-[Derived(MyCategory) anotherInstanceMethod]"(%0* %self, i8* %_cmd) #3 { // CHECK-NEXT: entry: // CHECK:[[SUPER:%.*]] = alloca %struct._objc_super, align 8 // CHECK:[[CLASS_REF:%.*]] = call %struct._class_t* @objc_loadClassref(i8** @"OBJC_CLASSLIST_SUP_REFS_$_.1") Index: clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp === --- clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp +++ clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp @@ -4,7 +4,7 @@ // RUN: %clang_cc1 -triple x86_64-apple-darwin -std=c++11 -emit-llvm -o - %s -O3 -disable-llvm-optzns -fno-unroll-loops | FileCheck --check-prefix=UNROLL_DISABLED_MD %s // RUN: %clang_cc1 -triple x86_64-apple-darwin -std=c++11 -emit-llvm -o - %s -O3 -disable-llvm-optzns | FileCheck --check-prefix=NO_UNROLL_MD %s -// NO_UNROLL_MD-NOT: llvm.loop +// NO_UNROLL_MD-NOT: llvm.loop.unroll.disable // Verify unroll.disable metadata is added to while loop with -fno-unroll-loops // and optlevel > 0. Index: clang/test/CodeGen/unwind-attr.c === --- clang/test/CodeGen/unwind-attr.c +++ clang/test/CodeGen/unwind-attr.c @@ -23,7 +23,7 @@ return 0; } -// CHECK: attributes [[TF]] = { noinline optnone "{{.*}} } +// CHECK: attributes [[TF]] = { noinline optnone maynotprogress "{{.*}} } //
[PATCH] D86841: [clang] Add mayprogress and llvm.loop.mustprogress attribute deduction
atmnpatel updated this revision to Diff 289997. atmnpatel added a comment. Renamed `mayprogress` to `maynotprogress`. Repository: rG LLVM Github Monorepo CHANGES SINCE LAST ACTION https://reviews.llvm.org/D86841/new/ https://reviews.llvm.org/D86841 Files: clang/lib/CodeGen/CGLoopInfo.cpp clang/lib/CodeGen/CGLoopInfo.h clang/lib/CodeGen/CGStmt.cpp clang/lib/CodeGen/CodeGenFunction.cpp clang/lib/CodeGen/CodeGenFunction.h clang/test/CodeGen/attr-noprogress.c clang/test/CodeGen/attr-noprogress.cpp clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp Index: clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp === --- clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp +++ clang/test/CodeGenCXX/fno-unroll-loops-metadata.cpp @@ -4,7 +4,7 @@ // RUN: %clang_cc1 -triple x86_64-apple-darwin -std=c++11 -emit-llvm -o - %s -O3 -disable-llvm-optzns -fno-unroll-loops | FileCheck --check-prefix=UNROLL_DISABLED_MD %s // RUN: %clang_cc1 -triple x86_64-apple-darwin -std=c++11 -emit-llvm -o - %s -O3 -disable-llvm-optzns | FileCheck --check-prefix=NO_UNROLL_MD %s -// NO_UNROLL_MD-NOT: llvm.loop +// NO_UNROLL_MD-NOT: llvm.loop.unroll.disable // Verify unroll.disable metadata is added to while loop with -fno-unroll-loops // and optlevel > 0. Index: clang/test/CodeGen/attr-noprogress.cpp === --- /dev/null +++ clang/test/CodeGen/attr-noprogress.cpp @@ -0,0 +1,188 @@ +// NOTE: Assertions have been autogenerated by utils/update_cc_test_checks.py UTC_ARGS: --check-attributes +// RUN: %clang_cc1 -S -emit-llvm %s -o - | FileCheck %s + +int a = 0; +int b = 0; + +// CHECK: Function Attrs: noinline nounwind optnone maynotprogress +// CHECK-LABEL: @_Z2f1v( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[FOR_COND:%.*]] +// CHECK: for.cond: +// CHECK: br i1 true, label [[FOR_BODY:%.*]], label [[FOR_END:%.*]] +// CHECK: for.body: +// CHECK: br label [[FOR_COND]] +// CHECK: for.end: +// CHECK: ret void +// +void f1() { + for (; 1;) { + } +} + +// CHECK: Function Attrs: noinline nounwind optnone +// CHECK-LABEL: @_Z2f2v( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[FOR_COND:%.*]] +// CHECK: for.cond: +// CHECK: [[TMP0:%.*]] = load i32, i32* @a, align 4 +// CHECK: [[TMP1:%.*]] = load i32, i32* @b, align 4 +// CHECK: [[CMP:%.*]] = icmp eq i32 [[TMP0]], [[TMP1]] +// CHECK: br i1 [[CMP]], label [[FOR_BODY:%.*]], label [[FOR_END:%.*]] +// CHECK: for.body: +// CHECK: br label [[FOR_COND]] +// CHECK: for.end: +// CHECK: ret void +// +void f2() { + for (; a == b;) { + } +} + +// CHECK: Function Attrs: noinline nounwind optnone maynotprogress +// CHECK-LABEL: @_Z1Fv( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[FOR_COND:%.*]] +// CHECK: for.cond: +// CHECK: br i1 true, label [[FOR_BODY:%.*]], label [[FOR_END:%.*]] +// CHECK: for.body: +// CHECK: br label [[FOR_COND]] +// CHECK: for.end: +// CHECK: br label [[FOR_COND1:%.*]] +// CHECK: for.cond1: +// CHECK: [[TMP0:%.*]] = load i32, i32* @a, align 4 +// CHECK: [[TMP1:%.*]] = load i32, i32* @b, align 4 +// CHECK: [[CMP:%.*]] = icmp eq i32 [[TMP0]], [[TMP1]] +// CHECK: br i1 [[CMP]], label [[FOR_BODY2:%.*]], label [[FOR_END3:%.*]] +// CHECK: for.body2: +// CHECK: br label [[FOR_COND1]], !llvm.loop [[LOOP2:!.*]] +// CHECK: for.end3: +// CHECK: ret void +// +void F() { + for (; 1;) { + } + for (; a == b;) { + } +} + +// CHECK: Function Attrs: noinline nounwind optnone maynotprogress +// CHECK-LABEL: @_Z2w1v( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[WHILE_BODY:%.*]] +// CHECK: while.body: +// CHECK: br label [[WHILE_BODY]] +// +void w1() { + while (1) { + } +} + +// CHECK: Function Attrs: noinline nounwind optnone +// CHECK-LABEL: @_Z2w2v( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[WHILE_COND:%.*]] +// CHECK: while.cond: +// CHECK: [[TMP0:%.*]] = load i32, i32* @a, align 4 +// CHECK: [[TMP1:%.*]] = load i32, i32* @b, align 4 +// CHECK: [[CMP:%.*]] = icmp eq i32 [[TMP0]], [[TMP1]] +// CHECK: br i1 [[CMP]], label [[WHILE_BODY:%.*]], label [[WHILE_END:%.*]] +// CHECK: while.body: +// CHECK: br label [[WHILE_COND]] +// CHECK: while.end: +// CHECK: ret void +// +void w2() { + while (a == b) { + } +} + +// CHECK: Function Attrs: noinline nounwind optnone maynotprogress +// CHECK-LABEL: @_Z1Wv( +// CHECK-NEXT: entry: +// CHECK-NEXT:br label [[WHILE_COND:%.*]] +// CHECK: while.cond: +// CHECK: [[TMP0:%.*]] = load i32, i32* @a, align 4 +// CHECK: [[TMP1:%.*]] = load i32, i32* @b, align 4 +// CHECK: [[CMP:%.*]] = icmp eq i32 [[TMP0]], [[TMP1]] +// CHECK: br i1 [[CMP]],