162 lines · plain
1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py UTC_ARGS: --function-signature --scrub-attributes --check-attributes --check-globals2; Deep Wrapper disabled3 4; RUN: opt -aa-pipeline=basic-aa -passes=attributor -attributor-manifest-internal -attributor-annotate-decl-cs -S < %s | FileCheck %s --check-prefixes=CHECK,CHECK_DISABLED5 6; Deep Wrapper enabled7 8; RUN: opt -aa-pipeline=basic-aa -passes=attributor -attributor-manifest-internal -attributor-annotate-decl-cs -attributor-allow-deep-wrappers -S < %s | FileCheck %s --check-prefixes=CHECK,CHECK_ENABLED9 10; TEST 1: This function is of linkage `linkonce`, we cannot internalize this11; function and use information derived from it12;13; CHECK-NOT: inner1.internalized14define linkonce i32 @inner1(i32 %a, i32 %b) {15; CHECK-LABEL: define {{[^@]+}}@inner116; CHECK-SAME: (i32 [[A:%.*]], i32 [[B:%.*]]) {17; CHECK-NEXT: entry:18; CHECK-NEXT: [[C:%.*]] = add i32 [[A]], [[B]]19; CHECK-NEXT: ret i32 [[C]]20;21entry:22 %c = add i32 %a, %b23 ret i32 %c24}25 26; TEST 2: This function is of linkage `weak`, we cannot internalize this function and27; use information derived from it28;29; CHECK-NOT: inner2.internalized30define weak i32 @inner2(i32 %a, i32 %b) {31; CHECK-LABEL: define {{[^@]+}}@inner232; CHECK-SAME: (i32 [[A:%.*]], i32 [[B:%.*]]) {33; CHECK-NEXT: entry:34; CHECK-NEXT: [[C:%.*]] = add i32 [[A]], [[B]]35; CHECK-NEXT: ret i32 [[C]]36;37entry:38 %c = add i32 %a, %b39 ret i32 %c40}41 42; TEST 3: This function is of linkage `linkonce_odr`, which can be internalized using the43; deep wrapper, and the IP information derived from this function can be used44;45define linkonce_odr i32 @inner3(i32 %a, i32 %b) {46; CHECK_DISABLED-LABEL: define {{[^@]+}}@inner347; CHECK_DISABLED-SAME: (i32 [[A:%.*]], i32 [[B:%.*]]) {48; CHECK_DISABLED-NEXT: entry:49; CHECK_DISABLED-NEXT: [[C:%.*]] = add i32 [[A]], [[B]]50; CHECK_DISABLED-NEXT: ret i32 [[C]]51;52entry:53 %c = add i32 %a, %b54 ret i32 %c55}56 57; TEST 4: This function is of linkage `weak_odr`, which can be internalized using the deep58; wrapper59;60define weak_odr i32 @inner4(i32 %a, i32 %b) {61; CHECK_DISABLED-LABEL: define {{[^@]+}}@inner462; CHECK_DISABLED-SAME: (i32 [[A:%.*]], i32 [[B:%.*]]) {63; CHECK_DISABLED-NEXT: entry:64; CHECK_DISABLED-NEXT: [[C:%.*]] = add i32 [[A]], [[B]]65; CHECK_DISABLED-NEXT: ret i32 [[C]]66;67entry:68 %c = add i32 %a, %b69 ret i32 %c70}71 72; TEST 5: This function has linkage `linkonce_odr` but is never called (num of use = 0), so there73; is no need to internalize this74;75; CHECK-NOT: inner5.internalized76define linkonce_odr i32 @inner5(i32 %a, i32 %b) {77; CHECK-LABEL: define {{[^@]+}}@inner578; CHECK-SAME: (i32 [[A:%.*]], i32 [[B:%.*]]) {79; CHECK-NEXT: entry:80; CHECK-NEXT: [[C:%.*]] = add i32 [[A]], [[B]]81; CHECK-NEXT: ret i32 [[C]]82;83entry:84 %c = add i32 %a, %b85 ret i32 %c86}87 88; Since the inner1 cannot be internalized, there should be no change to its callsite89; Since the inner2 cannot be internalized, there should be no change to its callsite90; Since the inner3 is internalized, the use of the original function should be replaced by the91; copied one92;93define i32 @outer1() {94; CHECK_DISABLED-LABEL: define {{[^@]+}}@outer1() {95; CHECK_DISABLED-NEXT: entry:96; CHECK_DISABLED-NEXT: [[RET1:%.*]] = call i32 @inner1(i32 noundef 1, i32 noundef 2)97; CHECK_DISABLED-NEXT: [[RET2:%.*]] = call i32 @inner2(i32 noundef 1, i32 noundef 2)98; CHECK_DISABLED-NEXT: [[RET3:%.*]] = call i32 @inner3(i32 [[RET1]], i32 [[RET2]])99; CHECK_DISABLED-NEXT: [[RET4:%.*]] = call i32 @inner4(i32 [[RET3]], i32 [[RET3]])100; CHECK_DISABLED-NEXT: ret i32 [[RET4]]101;102; CHECK_ENABLED-LABEL: define {{[^@]+}}@outer1() {103; CHECK_ENABLED-NEXT: entry:104; CHECK_ENABLED-NEXT: [[RET1:%.*]] = call i32 @inner1(i32 noundef 1, i32 noundef 2)105; CHECK_ENABLED-NEXT: [[RET2:%.*]] = call i32 @inner2(i32 noundef 1, i32 noundef 2)106; CHECK_ENABLED-NEXT: [[RET3:%.*]] = call i32 @inner3.internalized(i32 [[RET1]], i32 [[RET2]])107; CHECK_ENABLED-NEXT: [[RET4:%.*]] = call i32 @inner4.internalized(i32 [[RET3]], i32 [[RET3]])108; CHECK_ENABLED-NEXT: ret i32 [[RET4]]109;110entry:111 %ret1 = call i32 @inner1(i32 1, i32 2)112 %ret2 = call i32 @inner2(i32 1, i32 2)113 %ret3 = call i32 @inner3(i32 %ret1, i32 %ret2)114 %ret4 = call i32 @inner4(i32 %ret3, i32 %ret3)115 ret i32 %ret4116}117 118 119define linkonce_odr void @unused_arg(i8) {120; CHECK_DISABLED-LABEL: define {{[^@]+}}@unused_arg121; CHECK_DISABLED-SAME: (i8 [[TMP0:%.*]]) {122; CHECK_DISABLED-NEXT: unreachable123;124 unreachable125}126 127define void @unused_arg_caller() {128; CHECK_DISABLED-LABEL: define {{[^@]+}}@unused_arg_caller() {129; CHECK_DISABLED-NEXT: call void @unused_arg(i8 noundef 0)130; CHECK_DISABLED-NEXT: ret void131;132; CHECK_ENABLED: Function Attrs: mustprogress nofree norecurse nosync nounwind willreturn memory(none)133; CHECK_ENABLED-LABEL: define {{[^@]+}}@unused_arg_caller134; CHECK_ENABLED-SAME: () #[[ATTR0:[0-9]+]] {135; CHECK_ENABLED-NEXT: unreachable136;137; CGSCC_ENABLED: Function Attrs: nofree norecurse noreturn nosync nounwind readnone willreturn138; CGSCC_ENABLED-LABEL: define {{[^@]+}}@unused_arg_caller139; CGSCC_ENABLED-SAME: () #[[ATTR2:[0-9]+]] {140; CGSCC_ENABLED-NEXT: unreachable141 call void @unused_arg(i8 0)142 ret void143}144 145; Don't crash on linkonce_odr hidden functions146define linkonce_odr hidden void @__clang_call_terminate() {147; CHECK_DISABLED-LABEL: define {{[^@]+}}@__clang_call_terminate() {148; CHECK_DISABLED-NEXT: call void @__clang_call_terminate()149; CHECK_DISABLED-NEXT: unreachable150;151 call void @__clang_call_terminate()152 unreachable153}154 155; CGSCC_ENABLED: attributes #[[ATTR0:[0-9]+]] = { nofree nosync nounwind readnone willreturn }156; CGSCC_ENABLED: attributes #[[ATTR1:[0-9]+]] = { nofree noreturn nosync nounwind readnone willreturn }157; CGSCC_ENABLED: attributes #[[ATTR2]] = { nofree norecurse noreturn nosync nounwind readnone willreturn }158;.159; CHECK_ENABLED: attributes #[[ATTR0]] = { mustprogress nofree norecurse nosync nounwind willreturn memory(none) }160; CHECK_ENABLED: attributes #[[ATTR1:[0-9]+]] = { nounwind memory(none) }161;.162