Home | History | Annotate | Download | only in AddressSanitizer
      1 ; Test hanlding of llvm.lifetime intrinsics.
      2 ; RUN: opt < %s -asan -asan-module -asan-use-after-scope -asan-use-after-return=0 -S | FileCheck %s
      3 ; RUN: opt < %s -asan -asan-module -asan-use-after-scope -asan-use-after-return=0 -asan-instrument-allocas=0 -S | FileCheck %s --check-prefix=CHECK-NO-DYNAMIC
      4 
      5 target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128-n8:16:32:64-S128"
      6 target triple = "x86_64-unknown-linux-gnu"
      7 
      8 declare void @llvm.lifetime.start(i64, i8* nocapture) nounwind
      9 declare void @llvm.lifetime.end(i64, i8* nocapture) nounwind
     10 
     11 define void @lifetime_no_size() sanitize_address {
     12 entry:
     13   %i = alloca i32, align 4
     14   %i.ptr = bitcast i32* %i to i8*
     15   call void @llvm.lifetime.start(i64 -1, i8* %i.ptr)
     16   store volatile i8 0, i8* %i.ptr
     17   call void @llvm.lifetime.end(i64 -1, i8* %i.ptr)
     18 
     19 ; Check that lifetime with no size are ignored.
     20 ; CHECK-LABEL: define void @lifetime_no_size()
     21 ; CHECK-NOT: @__asan_poison_stack_memory
     22 ; CHECK-NOT: @__asan_unpoison_stack_memory
     23 ; CHECK: ret void
     24   ret void
     25 }
     26 
     27 ; Generic case of lifetime analysis.
     28 define void @lifetime() sanitize_address {
     29   ; CHECK-LABEL: define void @lifetime()
     30 
     31   ; Regular variable lifetime intrinsics.
     32   %i = alloca i32, align 4
     33   %i.ptr = bitcast i32* %i to i8*
     34   call void @llvm.lifetime.start(i64 3, i8* %i.ptr)
     35   store volatile i8 0, i8* %i.ptr
     36   ; Memory is unpoisoned at llvm.lifetime.start
     37   ; CHECK: %[[VAR:[^ ]*]] = ptrtoint i32* %{{[^ ]+}} to i64
     38   ; CHECK-NEXT: call void @__asan_unpoison_stack_memory(i64 %[[VAR]], i64 3)
     39   call void @llvm.lifetime.end(i64 4, i8* %i.ptr)
     40   call void @llvm.lifetime.end(i64 2, i8* %i.ptr)
     41   ; Memory is poisoned at every call to llvm.lifetime.end
     42   ; CHECK: call void @__asan_poison_stack_memory(i64 %{{[^ ]+}}, i64 4)
     43   ; CHECK: call void @__asan_poison_stack_memory(i64 %{{[^ ]+}}, i64 2)
     44 
     45   ; Lifetime intrinsics for array.
     46   %arr = alloca [10 x i32], align 16
     47   %arr.ptr = bitcast [10 x i32]* %arr to i8*
     48   call void @llvm.lifetime.start(i64 40, i8* %arr.ptr)
     49   store volatile i8 0, i8* %arr.ptr
     50   ; CHECK: call void @__asan_unpoison_stack_memory(i64 %{{[^ ]+}}, i64 40)
     51   ; CHECK-NO-DYNAMIC-NOT: call void @__asan_unpoison_stack_memory(i64 %{{[^ ]+}}, i64 40)
     52   call void @llvm.lifetime.end(i64 40, i8* %arr.ptr)
     53   ; CHECK: call void @__asan_poison_stack_memory(i64 %{{[^ ]+}}, i64 40)
     54   ; CHECK-NO-DYNAMIC-NOT: call void @__asan_poison_stack_memory(i64 %{{[^ ]+}}, i64 40)
     55 
     56   ; One more lifetime start/end for the same variable %i.
     57   call void @llvm.lifetime.start(i64 4, i8* %i.ptr)
     58   store volatile i8 0, i8* %i.ptr
     59   ; CHECK: call void @__asan_unpoison_stack_memory(i64 %{{[^ ]+}}, i64 4)
     60   call void @llvm.lifetime.end(i64 4, i8* %i.ptr)
     61   ; CHECK: call void @__asan_poison_stack_memory(i64 %{{[^ ]+}}, i64 4)
     62 
     63   ; Memory is unpoisoned at function exit (only once).
     64   ; CHECK: call void @__asan_unpoison_stack_memory(i64 %{{[^ ]+}}, i64 {{.*}})
     65   ; CHECK-NOT: @__asan_unpoison_stack_memory
     66   ; CHECK: ret void
     67   ret void
     68 }
     69 
     70 ; Check that arguments of lifetime may come from phi nodes.
     71 define void @phi_args(i1 %x) sanitize_address {
     72   ; CHECK-LABEL: define void @phi_args(i1 %x)
     73 
     74 entry:
     75   %i = alloca i64, align 4
     76   %i.ptr = bitcast i64* %i to i8*
     77   call void @llvm.lifetime.start(i64 8, i8* %i.ptr)
     78   store volatile i8 0, i8* %i.ptr
     79   ; CHECK: __asan_unpoison_stack_memory
     80   br i1 %x, label %bb0, label %bb1
     81 
     82 bb0:
     83   %i.ptr2 = bitcast i64* %i to i8*
     84   br label %bb1
     85 
     86 bb1:
     87   %i.phi = phi i8* [ %i.ptr, %entry ], [ %i.ptr2, %bb0 ]
     88   call void @llvm.lifetime.end(i64 8, i8* %i.phi)
     89   ; CHECK: __asan_poison_stack_memory
     90   ; CHECK: ret void
     91   ret void
     92 }
     93 
     94 define void @zero_sized(i64 %a) #0 {
     95 ; CHECK-LABEL: define void @zero_sized(i64 %a)
     96 
     97 entry:
     98   %a.addr = alloca i64, align 8
     99   %b = alloca [0 x i8], align 1
    100   store i64 %a, i64* %a.addr, align 8
    101   %0 = bitcast [0 x i8]* %b to i8*
    102   call void @llvm.lifetime.start(i64 0, i8* %0) #2
    103   ; CHECK-NOT: call void @__asan_unpoison_stack_memory
    104   %1 = bitcast [0 x i8]* %b to i8*
    105   call void @llvm.lifetime.end(i64 0, i8* %1) #2
    106   ; CHECK-NOT: call void @__asan_poison_stack_memory
    107 
    108   ret void
    109 }
    110