1; NOTE: Assertions have been autogenerated by utils/update_test_checks.py 2; RUN: opt -passes=memcpyopt -S %s -verify-memoryssa | FileCheck %s 3 4target datalayout = "e-m:o-i64:64-f80:128-n8:16:32:64-S128" 5 6define void @test(ptr %dst1, ptr %dst2, i8 %c) { 7; CHECK-LABEL: @test( 8; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 9; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[DST2:%.*]], i8 [[C]], i64 128, i1 false) 10; CHECK-NEXT: ret void 11; 12 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 128, i1 false) 13 call void @llvm.memcpy.p0.p0.i64(ptr align 8 %dst2, ptr align 8 %dst1, i64 128, i1 false) 14 ret void 15} 16 17define void @test_smaller_memcpy(ptr %dst1, ptr %dst2, i8 %c) { 18; CHECK-LABEL: @test_smaller_memcpy( 19; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 20; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST2:%.*]], i8 [[C]], i64 100, i1 false) 21; CHECK-NEXT: ret void 22; 23 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 128, i1 false) 24 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 100, i1 false) 25 ret void 26} 27 28define void @test_smaller_memset(ptr %dst1, ptr %dst2, i8 %c) { 29; CHECK-LABEL: @test_smaller_memset( 30; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 100, i1 false) 31; CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr [[DST2:%.*]], ptr [[DST1]], i64 128, i1 false) 32; CHECK-NEXT: ret void 33; 34 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 100, i1 false) 35 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 128, i1 false) 36 ret void 37} 38 39define void @test_align_memset(ptr %dst1, ptr %dst2, i8 %c) { 40; CHECK-LABEL: @test_align_memset( 41; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 42; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST2:%.*]], i8 [[C]], i64 128, i1 false) 43; CHECK-NEXT: ret void 44; 45 call void @llvm.memset.p0.i64(ptr align 8 %dst1, i8 %c, i64 128, i1 false) 46 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 128, i1 false) 47 ret void 48} 49 50define void @test_different_types(ptr %dst1, ptr %dst2, i8 %c) { 51; CHECK-LABEL: @test_different_types( 52; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 53; CHECK-NEXT: call void @llvm.memset.p0.i32(ptr [[DST2:%.*]], i8 [[C]], i32 100, i1 false) 54; CHECK-NEXT: ret void 55; 56 call void @llvm.memset.p0.i64(ptr align 8 %dst1, i8 %c, i64 128, i1 false) 57 call void @llvm.memcpy.p0.p0.i32(ptr %dst2, ptr %dst1, i32 100, i1 false) 58 ret void 59} 60 61define void @test_different_types_2(ptr %dst1, ptr %dst2, i8 %c) { 62; CHECK-LABEL: @test_different_types_2( 63; CHECK-NEXT: call void @llvm.memset.p0.i32(ptr align 8 [[DST1:%.*]], i8 [[C:%.*]], i32 128, i1 false) 64; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST2:%.*]], i8 [[C]], i64 100, i1 false) 65; CHECK-NEXT: ret void 66; 67 call void @llvm.memset.p0.i32(ptr align 8 %dst1, i8 %c, i32 128, i1 false) 68 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 100, i1 false) 69 ret void 70} 71 72define void @test_different_source_gep(ptr %dst1, ptr %dst2, i8 %c) { 73; CHECK-LABEL: @test_different_source_gep( 74; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 75; CHECK-NEXT: [[P:%.*]] = getelementptr i8, ptr [[DST1]], i64 64 76; CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr [[DST2:%.*]], ptr [[P]], i64 64, i1 false) 77; CHECK-NEXT: ret void 78; 79 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 128, i1 false) 80 ; FIXME: We could optimize this as well. 81 %p = getelementptr i8, ptr %dst1, i64 64 82 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %p, i64 64, i1 false) 83 ret void 84} 85 86define void @test_variable_size_1(ptr %dst1, i64 %dst1_size, ptr %dst2, i8 %c) { 87; CHECK-LABEL: @test_variable_size_1( 88; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 [[DST1_SIZE:%.*]], i1 false) 89; CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr [[DST2:%.*]], ptr [[DST1]], i64 128, i1 false) 90; CHECK-NEXT: ret void 91; 92 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 %dst1_size, i1 false) 93 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 128, i1 false) 94 ret void 95} 96 97define void @test_variable_size_2(ptr %dst1, ptr %dst2, i64 %dst2_size, i8 %c) { 98; CHECK-LABEL: @test_variable_size_2( 99; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr [[DST1:%.*]], i8 [[C:%.*]], i64 128, i1 false) 100; CHECK-NEXT: call void @llvm.memcpy.p0.p0.i64(ptr [[DST2:%.*]], ptr [[DST1]], i64 [[DST2_SIZE:%.*]], i1 false) 101; CHECK-NEXT: ret void 102; 103 call void @llvm.memset.p0.i64(ptr %dst1, i8 %c, i64 128, i1 false) 104 call void @llvm.memcpy.p0.p0.i64(ptr %dst2, ptr %dst1, i64 %dst2_size, i1 false) 105 ret void 106} 107 108declare void @llvm.memset.p0.i64(ptr nocapture, i8, i64, i1) 109declare void @llvm.memcpy.p0.p0.i64(ptr nocapture, ptr nocapture readonly, i64, i1) 110declare void @llvm.memset.p0.i32(ptr nocapture, i8, i32, i1) 111declare void @llvm.memcpy.p0.p0.i32(ptr nocapture, ptr nocapture readonly, i32, i1) 112