382 changes: 310 additions & 72 deletions llvm/lib/Transforms/Instrumentation/MemorySanitizer.cpp

Large diffs are not rendered by default.

20 changes: 20 additions & 0 deletions llvm/test/Instrumentation/MemorySanitizer/alloca.ll
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-poison-stack-with-call=1 -S | FileCheck %s --check-prefixes=CHECK,CALL
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=1 -S | FileCheck %s --check-prefixes=CHECK,ORIGIN
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=2 -S | FileCheck %s --check-prefixes=CHECK,ORIGIN
; RUN: opt < %s -msan -msan-kernel=1 -S | FileCheck %s --check-prefixes=CHECK,KMSAN

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"
target triple = "x86_64-unknown-linux-gnu"
Expand All @@ -16,6 +17,7 @@ entry:
; INLINE: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 -1, i64 4, i1 false)
; CALL: call void @__msan_poison_stack(i8* {{.*}}, i64 4)
; ORIGIN: call void @__msan_set_alloca_origin4(i8* {{.*}}, i64 4,
; KMSAN: call void @__msan_poison_alloca(i8* {{.*}}, i64 4,
; CHECK: ret void


Expand All @@ -31,6 +33,7 @@ l:
; INLINE: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 -1, i64 4, i1 false)
; CALL: call void @__msan_poison_stack(i8* {{.*}}, i64 4)
; ORIGIN: call void @__msan_set_alloca_origin4(i8* {{.*}}, i64 4,
; KMSAN: call void @__msan_poison_alloca(i8* {{.*}}, i64 4,
; CHECK: ret void

define void @array() sanitize_memory {
Expand All @@ -43,6 +46,7 @@ entry:
; INLINE: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 -1, i64 20, i1 false)
; CALL: call void @__msan_poison_stack(i8* {{.*}}, i64 20)
; ORIGIN: call void @__msan_set_alloca_origin4(i8* {{.*}}, i64 20,
; KMSAN: call void @__msan_poison_alloca(i8* {{.*}}, i64 20,
; CHECK: ret void

define void @array_non_const(i64 %cnt) sanitize_memory {
Expand All @@ -56,4 +60,20 @@ entry:
; INLINE: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 -1, i64 %[[A]], i1 false)
; CALL: call void @__msan_poison_stack(i8* {{.*}}, i64 %[[A]])
; ORIGIN: call void @__msan_set_alloca_origin4(i8* {{.*}}, i64 %[[A]],
; KMSAN: call void @__msan_poison_alloca(i8* {{.*}}, i64 %[[A]],
; CHECK: ret void

; Check that the local is unpoisoned in the absence of sanitize_memory
define void @unpoison_local() {
entry:
%x = alloca i32, i64 5, align 4
ret void
}

; CHECK-LABEL: define void @unpoison_local(
; INLINE: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 0, i64 20, i1 false)
; CALL: call void @llvm.memset.p0i8.i64(i8* align 4 {{.*}}, i8 0, i64 20, i1 false)
; ORIGIN-NOT: call void @__msan_set_alloca_origin4(i8* {{.*}}, i64 20,
; KMSAN: call void @__msan_unpoison_alloca(i8* {{.*}}, i64 20)
; CHECK: ret void

404 changes: 404 additions & 0 deletions llvm/test/Instrumentation/MemorySanitizer/msan_kernel_basic.ll
Original file line number Diff line number Diff line change
@@ -0,0 +1,404 @@
; KMSAN instrumentation tests
; RUN: opt < %s -msan -msan-kernel=1 -S | FileCheck %s -check-prefixes=CHECK

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"
target triple = "x86_64-unknown-linux-gnu"

; Check the instrumentation prologue.
define void @Empty() nounwind uwtable sanitize_memory {
entry:
ret void
}

; CHECK-LABEL: @Empty
; CHECK: entry:
; CHECK: @__msan_get_context_state()
; %param_shadow:
; CHECK: getelementptr {{.*}} i32 0, i32 0
; %retval_shadow:
; CHECK: getelementptr {{.*}} i32 0, i32 1
; %va_arg_shadow:
; CHECK: getelementptr {{.*}} i32 0, i32 2
; %va_arg_origin:
; CHECK: getelementptr {{.*}} i32 0, i32 3
; %va_arg_overflow_size:
; CHECK: getelementptr {{.*}} i32 0, i32 4
; %param_origin:
; CHECK: getelementptr {{.*}} i32 0, i32 5
; %retval_origin:
; CHECK: getelementptr {{.*}} i32 0, i32 6
; CHECK: entry.split:

; Check instrumentation of stores

define void @Store1(i8* nocapture %p, i8 %x) nounwind uwtable sanitize_memory {
entry:
store i8 %x, i8* %p
ret void
}

; CHECK-LABEL: @Store1
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: [[BASE2:%[0-9]+]] = ptrtoint {{.*}} [[PARAM_SHADOW]]
; CHECK: [[BASE:%[0-9]+]] = ptrtoint {{.*}} [[PARAM_SHADOW]]
; CHECK: [[SHADOW:%[a-z0-9_]+]] = inttoptr {{.*}} [[BASE]]
; Load the shadow of %p and check it
; CHECK: load i64, i64* [[SHADOW]]
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; CHECK: @__msan_metadata_ptr_for_store_1(i8* %p)
; CHECK: store i8
; If the new shadow is non-zero, jump to __msan_chain_origin()
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
; CHECK: @__msan_chain_origin
; Storing origin here:
; CHECK: store i32
; CHECK: br label
; CHECK: <label>
; CHECK: store i8
; CHECK: ret void

define void @Store2(i16* nocapture %p, i16 %x) nounwind uwtable sanitize_memory {
entry:
store i16 %x, i16* %p
ret void
}

; CHECK-LABEL: @Store2
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; CHECK: [[REG:%[0-9]+]] = bitcast i16* %p to i8*
; CHECK: @__msan_metadata_ptr_for_store_2(i8* [[REG]])
; CHECK: store i16
; If the new shadow is non-zero, jump to __msan_chain_origin()
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
; CHECK: @__msan_chain_origin
; Storing origin here:
; CHECK: store i32
; CHECK: br label
; CHECK: <label>
; CHECK: store i16
; CHECK: ret void


define void @Store4(i32* nocapture %p, i32 %x) nounwind uwtable sanitize_memory {
entry:
store i32 %x, i32* %p
ret void
}

; CHECK-LABEL: @Store4
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i32
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; CHECK: [[REG:%[0-9]+]] = bitcast i32* %p to i8*
; CHECK: @__msan_metadata_ptr_for_store_4(i8* [[REG]])
; CHECK: store i32
; If the new shadow is non-zero, jump to __msan_chain_origin()
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
; CHECK: @__msan_chain_origin
; Storing origin here:
; CHECK: store i32
; CHECK: br label
; CHECK: <label>
; CHECK: store i32
; CHECK: ret void

define void @Store8(i64* nocapture %p, i64 %x) nounwind uwtable sanitize_memory {
entry:
store i64 %x, i64* %p
ret void
}

; CHECK-LABEL: @Store8
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; CHECK: [[REG:%[0-9]+]] = bitcast i64* %p to i8*
; CHECK: @__msan_metadata_ptr_for_store_8(i8* [[REG]])
; CHECK: store i64
; If the new shadow is non-zero, jump to __msan_chain_origin()
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
; CHECK: @__msan_chain_origin
; Storing origin here:
; CHECK: store i32
; CHECK: br label
; CHECK: <label>
; CHECK: store i64
; CHECK: ret void

define void @Store16(i128* nocapture %p, i128 %x) nounwind uwtable sanitize_memory {
entry:
store i128 %x, i128* %p
ret void
}

; CHECK-LABEL: @Store16
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; CHECK: [[REG:%[0-9]+]] = bitcast i128* %p to i8*
; CHECK: @__msan_metadata_ptr_for_store_n(i8* [[REG]], i64 16)
; CHECK: store i128
; If the new shadow is non-zero, jump to __msan_chain_origin()
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
; CHECK: @__msan_chain_origin
; Storing origin here:
; CHECK: store i32
; CHECK: br label
; CHECK: <label>
; CHECK: store i128
; CHECK: ret void


; Check instrumentation of loads

define i8 @Load1(i8* nocapture %p) nounwind uwtable sanitize_memory {
entry:
%0 = load i8, i8* %p
ret i8 %0
}

; CHECK-LABEL: @Load1
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; Load the value from %p. This is done before accessing the shadow
; to ease atomic handling.
; CHECK: load i8
; CHECK: @__msan_metadata_ptr_for_load_1(i8* %p)
; Load the shadow and origin.
; CHECK: load i8
; CHECK: load i32


define i16 @Load2(i16* nocapture %p) nounwind uwtable sanitize_memory {
entry:
%0 = load i16, i16* %p
ret i16 %0
}

; CHECK-LABEL: @Load2
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; Load the value from %p. This is done before accessing the shadow
; to ease atomic handling.
; CHECK: load i16
; CHECK: [[REG:%[0-9]+]] = bitcast i16* %p to i8*
; CHECK: @__msan_metadata_ptr_for_load_2(i8* [[REG]])
; Load the shadow and origin.
; CHECK: load i16
; CHECK: load i32


define i32 @Load4(i32* nocapture %p) nounwind uwtable sanitize_memory {
entry:
%0 = load i32, i32* %p
ret i32 %0
}

; CHECK-LABEL: @Load4
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; Load the value from %p. This is done before accessing the shadow
; to ease atomic handling.
; CHECK: load i32
; CHECK: [[REG:%[0-9]+]] = bitcast i32* %p to i8*
; CHECK: @__msan_metadata_ptr_for_load_4(i8* [[REG]])
; Load the shadow and origin.
; CHECK: load i32
; CHECK: load i32

define i64 @Load8(i64* nocapture %p) nounwind uwtable sanitize_memory {
entry:
%0 = load i64, i64* %p
ret i64 %0
}

; CHECK-LABEL: @Load8
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; Load the value from %p. This is done before accessing the shadow
; to ease atomic handling.
; CHECK: load i64
; CHECK: [[REG:%[0-9]+]] = bitcast i64* %p to i8*
; CHECK: @__msan_metadata_ptr_for_load_8(i8* [[REG]])
; Load the shadow and origin.
; CHECK: load i64
; CHECK: load i32

define i128 @Load16(i128* nocapture %p) nounwind uwtable sanitize_memory {
entry:
%0 = load i128, i128* %p
ret i128 %0
}

; CHECK-LABEL: @Load16
; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK-LABEL: entry.split:
; CHECK: ptrtoint {{.*}} [[PARAM_SHADOW]]
; Load the shadow of %p and check it
; CHECK: load i64
; CHECK: icmp
; CHECK: br i1
; CHECK-LABEL: <label>
; Load the value from %p. This is done before accessing the shadow
; to ease atomic handling.
; CHECK: load i128
; CHECK: [[REG:%[0-9]+]] = bitcast i128* %p to i8*
; CHECK: @__msan_metadata_ptr_for_load_n(i8* [[REG]], i64 16)
; Load the shadow and origin.
; CHECK: load i128
; CHECK: load i32


; Test kernel-specific va_list instrumentation

%struct.__va_list_tag = type { i32, i32, i8*, i8* }
declare void @llvm.va_start(i8*) nounwind
declare void @llvm.va_end(i8*)
@.str = private unnamed_addr constant [4 x i8] c"%d\0A\00", align 1
declare dso_local i32 @VAListFn(i8*, %struct.__va_list_tag*) local_unnamed_addr

; Function Attrs: nounwind uwtable
define dso_local i32 @VarArgFn(i8* %fmt, ...) local_unnamed_addr sanitize_memory #0 {
entry:
%args = alloca [1 x %struct.__va_list_tag], align 16
%0 = bitcast [1 x %struct.__va_list_tag]* %args to i8*
%arraydecay = getelementptr inbounds [1 x %struct.__va_list_tag], [1 x %struct.__va_list_tag]* %args, i64 0, i64 0
call void @llvm.va_start(i8* nonnull %0)
%call = call i32 @VAListFn(i8* %fmt, %struct.__va_list_tag* nonnull %arraydecay)
call void @llvm.va_end(i8* nonnull %0)
ret i32 %call
}

; Kernel is built without SSE support.
attributes #0 = { "target-features"="+fxsr,+x87,-sse" }

; CHECK-LABEL: @VarArgFn
; CHECK: @__msan_get_context_state()
; CHECK: [[VA_ARG_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 2
; CHECK: [[VA_ARG_ORIGIN:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 3
; CHECK: [[VA_ARG_OVERFLOW_SIZE:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 4

; CHECK-LABEL: entry.split:
; CHECK: [[OSIZE:%[0-9]+]] = load i64, i64* [[VA_ARG_OVERFLOW_SIZE]]
; Register save area is 48 bytes for non-SSE builds.
; CHECK: [[SIZE:%[0-9]+]] = add i64 48, [[OSIZE]]
; CHECK: [[SHADOWS:%[0-9]+]] = alloca i8, i64 [[SIZE]]
; CHECK: [[VA_ARG_SHADOW]]
; CHECK: call void @llvm.memcpy{{.*}}(i8* align 8 [[SHADOWS]], {{.*}}, i64 [[SIZE]]
; CHECK: [[ORIGINS:%[0-9]+]] = alloca i8, i64 [[SIZE]]
; CHECK: [[VA_ARG_ORIGIN]]
; CHECK: call void @llvm.memcpy{{.*}}(i8* align 8 [[ORIGINS]], {{.*}}, i64 [[SIZE]]
; CHECK: call i32 @VAListFn

; Function Attrs: nounwind uwtable
define dso_local void @VarArgCaller() local_unnamed_addr sanitize_memory {
entry:
%call = tail call i32 (i8*, ...) @VarArgFn(i8* getelementptr inbounds ([4 x i8], [4 x i8]* @.str, i64 0, i64 0), i32 123)
ret void
}

; CHECK-LABEL: @VarArgCaller

; CHECK-LABEL: entry:
; CHECK: @__msan_get_context_state()
; CHECK: [[PARAM_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 0
; CHECK: [[VA_ARG_SHADOW:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 2
; CHECK: [[VA_ARG_OVERFLOW_SIZE:%[a-z0-9_]+]] = getelementptr {{.*}} i32 0, i32 4

; CHECK-LABEL: entry.split:
; CHECK: [[PARAM_SI:%[_a-z0-9]+]] = ptrtoint {{.*}} [[PARAM_SHADOW]]
; CHECK: [[ARG1_S:%[_a-z0-9]+]] = inttoptr i64 [[PARAM_SI]] to i64*
; First argument is initialized
; CHECK: store i64 0, i64* [[ARG1_S]]

; Dangling cast of va_arg_shadow[0], unused because the first argument is fixed.
; CHECK: [[VA_CAST0:%[_a-z0-9]+]] = ptrtoint {{.*}} [[VA_ARG_SHADOW]] to i64

; CHECK: [[VA_CAST1:%[_a-z0-9]+]] = ptrtoint {{.*}} [[VA_ARG_SHADOW]] to i64
; CHECK: [[ARG1_SI:%[_a-z0-9]+]] = add i64 [[VA_CAST1]], 8
; CHECK: [[PARG1_S:%[_a-z0-9]+]] = inttoptr i64 [[ARG1_SI]] to i32*

; Shadow for 123 is 0.
; CHECK: store i32 0, i32* [[ARG1_S]]

; CHECK: store i64 0, i64* [[VA_ARG_OVERFLOW_SIZE]]
; CHECK: call i32 (i8*, ...) @VarArgFn({{.*}} @.str{{.*}} i32 123)
21 changes: 15 additions & 6 deletions llvm/test/Instrumentation/MemorySanitizer/store-origin.ll
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=1 -S | FileCheck -check-prefix=CHECK -check-prefix=CHECK-ORIGINS1 %s
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=2 -S | FileCheck -check-prefix=CHECK -check-prefix=CHECK-ORIGINS2 %s
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=1 -S | FileCheck -check-prefixes=CHECK,CHECK-MSAN,CHECK-ORIGINS1 %s
; RUN: opt < %s -msan -msan-check-access-address=0 -msan-track-origins=2 -S | FileCheck -check-prefixes=CHECK,CHECK-MSAN,CHECK-ORIGINS2 %s
; RUN: opt < %s -msan -msan-kernel=1 -msan-check-access-address=0 -S | FileCheck -check-prefixes=CHECK,CHECK-KMSAN,CHECK-ORIGINS2 %s

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"
target triple = "x86_64-unknown-linux-gnu"
Expand Down Expand Up @@ -52,9 +53,17 @@ attributes #1 = { nounwind readnone }


; CHECK-LABEL: @Store
; CHECK: load {{.*}} @__msan_param_tls
; CHECK: [[ORIGIN:%[01-9a-z]+]] = load {{.*}} @__msan_param_origin_tls
; CHECK: store {{.*}}!dbg ![[DBG:[01-9]+]]

; CHECK-MSAN: load {{.*}} @__msan_param_tls
; CHECK-MSAN: [[ORIGIN:%[0-9a-z]+]] = load {{.*}} @__msan_param_origin_tls

; CHECK-KMSAN-LABEL: entry.split:
; CHECK-KMSAN: %param_shadow
; CHECK-KMSAN: load i32, i32*
; CHECK-KMSAN: %param_origin
; CHECK-KMSAN: [[ORIGIN:%[0-9a-z]+]] = load i32, i32*

; CHECK: store {{.*}}!dbg ![[DBG:[0-9]+]]
; CHECK: icmp
; CHECK: br i1
; CHECK: <label>
Expand All @@ -63,7 +72,7 @@ attributes #1 = { nounwind readnone }
; CHECK-ORIGINS1: store i32 {{.*}}[[ORIGIN]],{{.*}}!dbg !{{.*}}[[DBG]]

; Origin tracking level 2: pass origin value through __msan_chain_origin and store the result.
; CHECK-ORIGINS2: [[ORIGIN2:%[01-9a-z]+]] = call i32 @__msan_chain_origin(i32 {{.*}}[[ORIGIN]])
; CHECK-ORIGINS2: [[ORIGIN2:%[0-9a-z]+]] = call i32 @__msan_chain_origin(i32 {{.*}}[[ORIGIN]])
; CHECK-ORIGINS2: store i32 {{.*}}[[ORIGIN2]],{{.*}}!dbg !{{.*}}[[DBG]]

; CHECK: br label{{.*}}!dbg !{{.*}}[[DBG]]
Expand Down