Skip to content

Commit dbfc3ed

Browse files
authored
[TypeSanitizer] Use alloca size for lifetime markers (#152154)
Split out from #150248: Use the size of the alloca instead of the size passed to the lifetime intrinsic. As a bonus, this handles dynamic allocas correctly (see the added test) instead of doing a memset with size -1...
1 parent f73a302 commit dbfc3ed

File tree

2 files changed

+66
-5
lines changed

2 files changed

+66
-5
lines changed

llvm/lib/Transforms/Instrumentation/TypeSanitizer.cpp

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -789,6 +789,13 @@ bool TypeSanitizer::instrumentMemInst(Value *V, Instruction *ShadowBase,
789789
bool NeedsMemMove = false;
790790
IRBuilder<> IRB(BB, IP);
791791

792+
auto GetAllocaSize = [&](AllocaInst *AI) {
793+
return IRB.CreateMul(
794+
IRB.CreateZExtOrTrunc(AI->getArraySize(), IntptrTy),
795+
ConstantInt::get(IntptrTy,
796+
DL.getTypeAllocSize(AI->getAllocatedType())));
797+
};
798+
792799
if (auto *A = dyn_cast<Argument>(V)) {
793800
assert(A->hasByValAttr() && "Type reset for non-byval argument?");
794801

@@ -811,7 +818,11 @@ bool TypeSanitizer::instrumentMemInst(Value *V, Instruction *ShadowBase,
811818
}
812819
}
813820
} else if (auto *II = dyn_cast<LifetimeIntrinsic>(I)) {
814-
Size = II->getArgOperand(0);
821+
auto *AI = dyn_cast<AllocaInst>(II->getArgOperand(1));
822+
if (!AI)
823+
return false;
824+
825+
Size = GetAllocaSize(AI);
815826
Dest = II->getArgOperand(1);
816827
} else if (auto *AI = dyn_cast<AllocaInst>(I)) {
817828
// We need to clear the types for new stack allocations (or else we might
@@ -820,10 +831,7 @@ bool TypeSanitizer::instrumentMemInst(Value *V, Instruction *ShadowBase,
820831
IRB.SetInsertPoint(&*std::next(BasicBlock::iterator(I)));
821832
IRB.SetInstDebugLocation(I);
822833

823-
Size = IRB.CreateMul(
824-
IRB.CreateZExtOrTrunc(AI->getArraySize(), IntptrTy),
825-
ConstantInt::get(IntptrTy,
826-
DL.getTypeAllocSize(AI->getAllocatedType())));
834+
Size = GetAllocaSize(AI);
827835
Dest = I;
828836
} else {
829837
return false;

llvm/test/Instrumentation/TypeSanitizer/alloca.ll

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,3 +74,56 @@ loop:
7474
exit:
7575
ret void
7676
}
77+
78+
define void @dynamic_alloca_lifetime_test(i1 %c, i64 %n) sanitize_type {
79+
; CHECK-LABEL: @dynamic_alloca_lifetime_test(
80+
; CHECK-NEXT: entry:
81+
; CHECK-NEXT: [[APP_MEM_MASK:%.*]] = load i64, ptr @__tysan_app_memory_mask, align 8
82+
; CHECK-NEXT: [[SHADOW_BASE:%.*]] = load i64, ptr @__tysan_shadow_memory_address, align 8
83+
; CHECK-NEXT: [[X:%.*]] = alloca i32, i64 [[N:%.*]], align 1
84+
; CHECK-NEXT: [[TMP0:%.*]] = mul i64 [[N]], 4
85+
; CHECK-NEXT: [[TMP1:%.*]] = ptrtoint ptr [[X]] to i64
86+
; CHECK-NEXT: [[TMP2:%.*]] = and i64 [[TMP1]], [[APP_MEM_MASK]]
87+
; CHECK-NEXT: [[TMP3:%.*]] = shl i64 [[TMP2]], 3
88+
; CHECK-NEXT: [[TMP4:%.*]] = add i64 [[TMP3]], [[SHADOW_BASE]]
89+
; CHECK-NEXT: [[TMP5:%.*]] = inttoptr i64 [[TMP4]] to ptr
90+
; CHECK-NEXT: [[TMP6:%.*]] = shl i64 [[TMP0]], 3
91+
; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[TMP5]], i8 0, i64 [[TMP6]], i1 false)
92+
; CHECK-NEXT: br label [[LOOP:%.*]]
93+
; CHECK: loop:
94+
; CHECK-NEXT: [[TMP7:%.*]] = mul i64 [[N]], 4
95+
; CHECK-NEXT: [[TMP8:%.*]] = ptrtoint ptr [[X]] to i64
96+
; CHECK-NEXT: [[TMP9:%.*]] = and i64 [[TMP8]], [[APP_MEM_MASK]]
97+
; CHECK-NEXT: [[TMP10:%.*]] = shl i64 [[TMP9]], 3
98+
; CHECK-NEXT: [[TMP11:%.*]] = add i64 [[TMP10]], [[SHADOW_BASE]]
99+
; CHECK-NEXT: [[TMP12:%.*]] = inttoptr i64 [[TMP11]] to ptr
100+
; CHECK-NEXT: [[TMP13:%.*]] = shl i64 [[TMP7]], 3
101+
; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[TMP12]], i8 0, i64 [[TMP13]], i1 false)
102+
; CHECK-NEXT: call void @llvm.lifetime.start.p0(i64 -1, ptr [[X]])
103+
; CHECK-NEXT: call void @alloca_test_use(ptr [[X]])
104+
; CHECK-NEXT: [[TMP14:%.*]] = mul i64 [[N]], 4
105+
; CHECK-NEXT: [[TMP15:%.*]] = ptrtoint ptr [[X]] to i64
106+
; CHECK-NEXT: [[TMP16:%.*]] = and i64 [[TMP15]], [[APP_MEM_MASK]]
107+
; CHECK-NEXT: [[TMP17:%.*]] = shl i64 [[TMP16]], 3
108+
; CHECK-NEXT: [[TMP18:%.*]] = add i64 [[TMP17]], [[SHADOW_BASE]]
109+
; CHECK-NEXT: [[TMP19:%.*]] = inttoptr i64 [[TMP18]] to ptr
110+
; CHECK-NEXT: [[TMP20:%.*]] = shl i64 [[TMP14]], 3
111+
; CHECK-NEXT: call void @llvm.memset.p0.i64(ptr align 8 [[TMP19]], i8 0, i64 [[TMP20]], i1 false)
112+
; CHECK-NEXT: call void @llvm.lifetime.end.p0(i64 -1, ptr [[X]])
113+
; CHECK-NEXT: br i1 [[C:%.*]], label [[LOOP]], label [[EXIT:%.*]]
114+
; CHECK: exit:
115+
; CHECK-NEXT: ret void
116+
;
117+
entry:
118+
%x = alloca i32, i64 %n, align 1
119+
br label %loop
120+
121+
loop:
122+
call void @llvm.lifetime.start.p0(i64 -1, ptr %x)
123+
call void @alloca_test_use(ptr %x)
124+
call void @llvm.lifetime.end.p0(i64 -1, ptr %x)
125+
br i1 %c, label %loop, label %exit
126+
127+
exit:
128+
ret void
129+
}

0 commit comments

Comments
 (0)