// Test 0 as initializer.
-// CHECK: @private_p = local_unnamed_addr addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
+// CHECK: @private_p = local_unnamed_addr addrspace(1) global i8* null, align 4
private char *private_p = 0;
// CHECK: @local_p = local_unnamed_addr addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
// Test NULL as initializer.
-// CHECK: @private_p_NULL = local_unnamed_addr addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
+// CHECK: @private_p_NULL = local_unnamed_addr addrspace(1) global i8* null, align 4
private char *private_p_NULL = NULL;
// CHECK: @local_p_NULL = local_unnamed_addr addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
// CHECK: @fold_generic = local_unnamed_addr addrspace(1) global i32 addrspace(4)* null, align 4
generic int *fold_generic = (global int*)(generic float*)(private char*)0;
-// CHECK: @fold_priv = local_unnamed_addr addrspace(1) global i16* addrspacecast (i16 addrspace(4)* null to i16*), align 4
+// CHECK: @fold_priv = local_unnamed_addr addrspace(1) global i16* null, align 4
private short *fold_priv = (private short*)(generic int*)(global void*)0;
-// CHECK: @fold_priv_arith = local_unnamed_addr addrspace(1) global i8* inttoptr (i32 9 to i8*), align 4
+// CHECK: @fold_priv_arith = local_unnamed_addr addrspace(1) global i8* inttoptr (i32 10 to i8*), align 4
private char *fold_priv_arith = (private char*)0 + 10;
-// CHECK: @fold_int = local_unnamed_addr addrspace(1) global i32 13, align 4
+// CHECK: @fold_int = local_unnamed_addr addrspace(1) global i32 14, align 4
int fold_int = (int)(private void*)(generic char*)(global int*)0 + 14;
-// CHECK: @fold_int2 = local_unnamed_addr addrspace(1) global i32 12, align 4
+// CHECK: @fold_int2 = local_unnamed_addr addrspace(1) global i32 13, align 4
int fold_int2 = (int) ((private void*)0 + 13);
-// CHECK: @fold_int3 = local_unnamed_addr addrspace(1) global i32 -1, align 4
+// CHECK: @fold_int3 = local_unnamed_addr addrspace(1) global i32 0, align 4
int fold_int3 = (int) ((private int*)0);
-// CHECK: @fold_int4 = local_unnamed_addr addrspace(1) global i32 7, align 4
+// CHECK: @fold_int4 = local_unnamed_addr addrspace(1) global i32 8, align 4
int fold_int4 = (int) &((private int*)0)[2];
-// CHECK: @fold_int5 = local_unnamed_addr addrspace(1) global i32 3, align 4
+// CHECK: @fold_int5 = local_unnamed_addr addrspace(1) global i32 4, align 4
int fold_int5 = (int) &((private StructTy1*)0)->p2;
+
+// CHECK: @fold_int_local = local_unnamed_addr addrspace(1) global i32 13, align 4
+int fold_int_local = (int)(local void*)(generic char*)(global int*)0 + 14;
+
+// CHECK: @fold_int2_local = local_unnamed_addr addrspace(1) global i32 12, align 4
+int fold_int2_local = (int) ((local void*)0 + 13);
+
+// CHECK: @fold_int3_local = local_unnamed_addr addrspace(1) global i32 -1, align 4
+int fold_int3_local = (int) ((local int*)0);
+
+// CHECK: @fold_int4_local = local_unnamed_addr addrspace(1) global i32 7, align 4
+int fold_int4_local = (int) &((local int*)0)[2];
+
+// CHECK: @fold_int5_local = local_unnamed_addr addrspace(1) global i32 3, align 4
+int fold_int5_local = (int) &((local StructTy1*)0)->p2;
+
+
// Test static variable initialization.
-// NOOPT: @test_static_var.sp1 = internal addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
-// NOOPT: @test_static_var.sp2 = internal addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
-// NOOPT: @test_static_var.sp3 = internal addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
-// NOOPT: @test_static_var.sp4 = internal addrspace(1) global i8* null, align 4
-// NOOPT: @test_static_var.sp5 = internal addrspace(1) global i8* null, align 4
-// NOOPT: @test_static_var.SS1 = internal addrspace(1) global %struct.StructTy1 { i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, align 4
-// NOOPT: @test_static_var.SS2 = internal addrspace(1) global %struct.StructTy2 zeroinitializer, align 4
+// NOOPT: @test_static_var_private.sp1 = internal addrspace(1) global i8* null, align 4
+// NOOPT: @test_static_var_private.sp2 = internal addrspace(1) global i8* null, align 4
+// NOOPT: @test_static_var_private.sp3 = internal addrspace(1) global i8* null, align 4
+// NOOPT: @test_static_var_private.sp4 = internal addrspace(1) global i8* null, align 4
+// NOOPT: @test_static_var_private.sp5 = internal addrspace(1) global i8* null, align 4
+// NOOPT: @test_static_var_private.SS1 = internal addrspace(1) global %struct.StructTy1 { i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, align 4
+// NOOPT: @test_static_var_private.SS2 = internal addrspace(1) global %struct.StructTy2 zeroinitializer, align 4
-void test_static_var(void) {
+void test_static_var_private(void) {
static private char *sp1 = 0;
static private char *sp2 = NULL;
static private char *sp3;
static StructTy2 SS2;
}
+// NOOPT: @test_static_var_local.sp1 = internal addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
+// NOOPT: @test_static_var_local.sp2 = internal addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
+// NOOPT: @test_static_var_local.sp3 = internal addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
+// NOOPT: @test_static_var_local.sp4 = internal addrspace(1) global i8 addrspace(3)* null, align 4
+// NOOPT: @test_static_var_local.sp5 = internal addrspace(1) global i8 addrspace(3)* null, align 4
+// NOOPT: @test_static_var_local.SS1 = internal addrspace(1) global %struct.StructTy1 { i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, align 4
+// NOOPT: @test_static_var_local.SS2 = internal addrspace(1) global %struct.StructTy2 zeroinitializer, align 4
+void test_static_var_local(void) {
+ static local char *sp1 = 0;
+ static local char *sp2 = NULL;
+ static local char *sp3;
+ static local char *sp4 = (local char*)((void)0, 0);
+ const int x = 0;
+ static local char *sp5 = (local char*)x;
+ static StructTy1 SS1;
+ static StructTy2 SS2;
+}
+
// Test function-scope variable initialization.
-// NOOPT-LABEL: test_func_scope_var
-// NOOPT: store i8* addrspacecast (i8 addrspace(4)* null to i8*), i8** %sp1, align 4
-// NOOPT: store i8* addrspacecast (i8 addrspace(4)* null to i8*), i8** %sp2, align 4
+// NOOPT-LABEL: @test_func_scope_var_private(
+// NOOPT: store i8* null, i8** %sp1, align 4
+// NOOPT: store i8* null, i8** %sp2, align 4
// NOOPT: store i8* null, i8** %sp3, align 4
// NOOPT: store i8* null, i8** %sp4, align 4
// NOOPT: %[[SS1:.*]] = bitcast %struct.StructTy1* %SS1 to i8*
-// NOOPT: call void @llvm.memcpy.p0i8.p2i8.i64(i8* %[[SS1]], i8 addrspace(2)* bitcast (%struct.StructTy1 addrspace(2)* @test_func_scope_var.SS1 to i8 addrspace(2)*), i64 32, i32 4, i1 false)
+// NOOPT: call void @llvm.memcpy.p0i8.p2i8.i64(i8* %[[SS1]], i8 addrspace(2)* bitcast (%struct.StructTy1 addrspace(2)* @test_func_scope_var_private.SS1 to i8 addrspace(2)*), i64 32, i32 4, i1 false)
// NOOPT: %[[SS2:.*]] = bitcast %struct.StructTy2* %SS2 to i8*
// NOOPT: call void @llvm.memset.p0i8.i64(i8* %[[SS2]], i8 0, i64 24, i32 4, i1 false)
-
-void test_func_scope_var(void) {
+void test_func_scope_var_private(void) {
private char *sp1 = 0;
private char *sp2 = NULL;
private char *sp3 = (private char*)((void)0, 0);
StructTy2 SS2 = {0, 0, 0};
}
+// Test function-scope variable initialization.
+// NOOPT-LABEL: @test_func_scope_var_local(
+// NOOPT: store i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(3)** %sp1, align 4
+// NOOPT: store i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(3)** %sp2, align 4
+// NOOPT: store i8 addrspace(3)* null, i8 addrspace(3)** %sp3, align 4
+// NOOPT: store i8 addrspace(3)* null, i8 addrspace(3)** %sp4, align 4
+// NOOPT: %[[SS1:.*]] = bitcast %struct.StructTy1* %SS1 to i8*
+// NOOPT: call void @llvm.memcpy.p0i8.p2i8.i64(i8* %[[SS1]], i8 addrspace(2)* bitcast (%struct.StructTy1 addrspace(2)* @test_func_scope_var_local.SS1 to i8 addrspace(2)*), i64 32, i32 4, i1 false)
+// NOOPT: %[[SS2:.*]] = bitcast %struct.StructTy2* %SS2 to i8*
+// NOOPT: call void @llvm.memset.p0i8.i64(i8* %[[SS2]], i8 0, i64 24, i32 4, i1 false)
+void test_func_scope_var_local(void) {
+ local char *sp1 = 0;
+ local char *sp2 = NULL;
+ local char *sp3 = (local char*)((void)0, 0);
+ const int x = 0;
+ local char *sp4 = (local char*)x;
+ StructTy1 SS1 = {0, 0, 0, 0, 0};
+ StructTy2 SS2 = {0, 0, 0};
+}
+
+
// Test default initialization of pointers.
// Tentative definition of global variables with non-zero initializer
// cannot have common linkage since common linkage requires zero initialization
// and does not have explicit section.
-// CHECK: @p1 = weak local_unnamed_addr addrspace(1) global i8* addrspacecast (i8 addrspace(4)* null to i8*), align 4
+// CHECK: @p1 = common local_unnamed_addr addrspace(1) global i8* null, align 4
private char *p1;
// CHECK: @p2 = weak local_unnamed_addr addrspace(1) global i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), align 4
// Test default initialization of sturcture.
-// CHECK: @S1 = weak local_unnamed_addr addrspace(1) global %struct.StructTy1 { i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, align 4
+// CHECK: @S1 = weak local_unnamed_addr addrspace(1) global %struct.StructTy1 { i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, align 4
StructTy1 S1;
// CHECK: @S2 = common local_unnamed_addr addrspace(1) global %struct.StructTy2 zeroinitializer, align 4
StructTy2 S2;
// Test default initialization of array.
-// CHECK: @A1 = weak local_unnamed_addr addrspace(1) global [2 x %struct.StructTy1] [%struct.StructTy1 { i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, %struct.StructTy1 { i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }], align 4
+// CHECK: @A1 = weak local_unnamed_addr addrspace(1) global [2 x %struct.StructTy1] [%struct.StructTy1 { i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }, %struct.StructTy1 { i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(2)* null, i8 addrspace(1)* null, i8 addrspace(4)* null }], align 4
StructTy1 A1[2];
// CHECK: @A2 = common local_unnamed_addr addrspace(1) global [2 x %struct.StructTy2] zeroinitializer, align 4
// Test comparison with 0.
// CHECK-LABEL: cmp_private
-// CHECK: icmp eq i8* %p, addrspacecast (i8 addrspace(4)* null to i8*)
+// CHECK: icmp eq i8* %p, null
void cmp_private(private char* p) {
if (p != 0)
*p = 0;
// Test comparison with NULL.
// CHECK-LABEL: cmp_NULL_private
-// CHECK: icmp eq i8* %p, addrspacecast (i8 addrspace(4)* null to i8*)
+// CHECK: icmp eq i8* %p, null
void cmp_NULL_private(private char* p) {
if (p != NULL)
*p = 0;
// Test storage 0 as null pointer.
// CHECK-LABEL: test_storage_null_pointer
-// CHECK: store i8* addrspacecast (i8 addrspace(4)* null to i8*), i8* addrspace(4)* %arg_private
+// CHECK: store i8* null, i8* addrspace(4)* %arg_private
// CHECK: store i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(3)* addrspace(4)* %arg_local
// CHECK: store i8 addrspace(1)* null, i8 addrspace(1)* addrspace(4)* %arg_global
// CHECK: store i8 addrspace(2)* null, i8 addrspace(2)* addrspace(4)* %arg_constant
// Test storage NULL as null pointer.
// CHECK-LABEL: test_storage_null_pointer_NULL
-// CHECK: store i8* addrspacecast (i8 addrspace(4)* null to i8*), i8* addrspace(4)* %arg_private
+// CHECK: store i8* null, i8* addrspace(4)* %arg_private
// CHECK: store i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(3)* addrspace(4)* %arg_local
// CHECK: store i8 addrspace(1)* null, i8 addrspace(1)* addrspace(4)* %arg_global
// CHECK: store i8 addrspace(2)* null, i8 addrspace(2)* addrspace(4)* %arg_constant
generic char* arg_generic);
// CHECK-LABEL: test_pass_null_pointer_arg
-// CHECK: call void @test_pass_null_pointer_arg_calee(i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(1)* null, i8 addrspace(2)* null, i8 addrspace(4)* null)
-// CHECK: call void @test_pass_null_pointer_arg_calee(i8* addrspacecast (i8 addrspace(4)* null to i8*), i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(1)* null, i8 addrspace(2)* null, i8 addrspace(4)* null)
+// CHECK: call void @test_pass_null_pointer_arg_calee(i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(1)* null, i8 addrspace(2)* null, i8 addrspace(4)* null)
+// CHECK: call void @test_pass_null_pointer_arg_calee(i8* null, i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*), i8 addrspace(1)* null, i8 addrspace(2)* null, i8 addrspace(4)* null)
void test_pass_null_pointer_arg(void) {
test_pass_null_pointer_arg_calee(0, 0, 0, 0, 0);
test_pass_null_pointer_arg_calee(NULL, NULL, NULL, NULL, NULL);
size_t arg_generic);
// CHECK-LABEL: test_cast_null_pointer_to_sizet
-// CHECK: call void @test_cast_null_pointer_to_sizet_calee(i64 ptrtoint (i8* addrspacecast (i8 addrspace(4)* null to i8*) to i64), i64 ptrtoint (i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*) to i64), i64 0, i64 0, i64 0)
-// CHECK: call void @test_cast_null_pointer_to_sizet_calee(i64 ptrtoint (i8* addrspacecast (i8 addrspace(4)* null to i8*) to i64), i64 ptrtoint (i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*) to i64), i64 0, i64 0, i64 0)
+// CHECK: call void @test_cast_null_pointer_to_sizet_calee(i64 0, i64 ptrtoint (i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*) to i64), i64 0, i64 0, i64 0)
+// CHECK: call void @test_cast_null_pointer_to_sizet_calee(i64 0, i64 ptrtoint (i8 addrspace(3)* addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*) to i64), i64 0, i64 0, i64 0)
void test_cast_null_pointer_to_sizet(void) {
test_cast_null_pointer_to_sizet_calee((size_t)((private char*)0),
(size_t)((local char*)0),
// Test cast to bool.
// CHECK-LABEL: cast_bool_private
-// CHECK: icmp eq i8* %p, addrspacecast (i8 addrspace(4)* null to i8*)
+// CHECK: icmp eq i8* %p, null
void cast_bool_private(private char* p) {
if (p)
*p = 0;
private char *p;
} StructTy3;
-// CHECK-LABEL: test_memset
-// CHECK: call void @llvm.memset.p0i8.i64(i8* {{.*}}, i8 0, i64 32, i32 8, i1 false)
-// CHECK: store i8* addrspacecast (i8 addrspace(4)* null to i8*), i8** {{.*}}
-StructTy3 test_memset(void) {
+// CHECK-LABEL: test_memset_private
+// CHECK: call void @llvm.memset.p0i8.i64(i8* nonnull {{.*}}, i8 0, i64 40, i32 8, i1 false)
+StructTy3 test_memset_private(void) {
StructTy3 S3 = {0, 0, 0, 0, 0};
return S3;
}
// Test casting literal 0 to pointer.
// A 0 literal casted to pointer should become a null pointer.
-// CHECK-LABEL: test_cast_0_to_ptr
-// CHECK: ret i32* addrspacecast (i32 addrspace(4)* null to i32*)
-private int* test_cast_0_to_ptr(void) {
+// CHECK-LABEL: test_cast_0_to_local_ptr
+// CHECK: ret i32 addrspace(3)* addrspacecast (i32 addrspace(4)* null to i32 addrspace(3)*)
+local int* test_cast_0_to_local_ptr(void) {
+ return (local int*)0;
+}
+
+// CHECK-LABEL: test_cast_0_to_private_ptr
+// CHECK: ret i32* null
+private int* test_cast_0_to_private_ptr(void) {
return (private int*)0;
}
// Test casting non-literal integer with 0 value to pointer.
// A non-literal integer expression with 0 value is casted to a pointer with
-// zero value.
+// zero value.
-// CHECK-LABEL: test_cast_int_to_ptr1
+// CHECK-LABEL: test_cast_int_to_ptr1_private
// CHECK: ret i32* null
-private int* test_cast_int_to_ptr1(void) {
+private int* test_cast_int_to_ptr1_private(void) {
return (private int*)((void)0, 0);
}
+// CHECK-LABEL: test_cast_int_to_ptr1_local
+ // CHECK: ret i32 addrspace(3)* null
+local int* test_cast_int_to_ptr1_local(void) {
+ return (local int*)((void)0, 0);
+}
+
// CHECK-LABEL: test_cast_int_to_ptr2
// CHECK: ret i32* null
private int* test_cast_int_to_ptr2(void) {
return a && ((private char*)NULL);
}
-// CHECK-LABEL: test_not_ptr
-// CHECK: %[[lnot:.*]] = icmp eq i8* %p, addrspacecast (i8 addrspace(4)* null to i8*)
+// CHECK-LABEL: test_not_private_ptr
+// CHECK: %[[lnot:.*]] = icmp eq i8* %p, null
+// CHECK: %[[lnot_ext:.*]] = zext i1 %[[lnot]] to i32
+// CHECK: ret i32 %[[lnot_ext]]
+int test_not_private_ptr(private char* p) {
+ return !p;
+}
+
+// CHECK-LABEL: test_not_local_ptr
+// CHECK: %[[lnot:.*]] = icmp eq i8 addrspace(3)* %p, addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*)
// CHECK: %[[lnot_ext:.*]] = zext i1 %[[lnot]] to i32
// CHECK: ret i32 %[[lnot_ext]]
-int test_not_ptr(private char* p) {
+int test_not_local_ptr(local char* p) {
return !p;
}
+
+
// CHECK-LABEL: test_and_ptr
-// CHECK: %[[tobool:.*]] = icmp ne i8* %p1, addrspacecast (i8 addrspace(4)* null to i8*)
+// CHECK: %[[tobool:.*]] = icmp ne i8* %p1, null
// CHECK: %[[tobool1:.*]] = icmp ne i8 addrspace(3)* %p2, addrspacecast (i8 addrspace(4)* null to i8 addrspace(3)*)
// CHECK: %[[res:.*]] = and i1 %[[tobool]], %[[tobool1]]
// CHECK: %[[land_ext:.*]] = zext i1 %[[res]] to i32
}
// Test folding of null pointer in function scope.
-// NOOPT-LABEL: test_fold
+// NOOPT-LABEL: test_fold_private
// NOOPT: call void @test_fold_callee
// NOOPT: store i32 addrspace(1)* null, i32 addrspace(1)** %glob, align 4
// NOOPT: %{{.*}} = sub i64 %{{.*}}, 0
// NOOPT: call void @test_fold_callee
-// NOOPT: %{{.*}} = add nsw i64 %{{.*}}, sext (i32 ptrtoint (i32* addrspacecast (i32 addrspace(4)* null to i32*) to i32) to i64)
+// NOOPT: %{{.*}} = add nsw i64 %{{.*}}, 0
// NOOPT: %{{.*}} = sub nsw i64 %{{.*}}, 1
void test_fold_callee(void);
-void test_fold(void) {
+void test_fold_private(void) {
global int* glob = (test_fold_callee(), (global int*)(generic char*)0);
long x = glob - (global int*)(generic char*)0;
x = x + (int)(test_fold_callee(), (private int*)(generic char*)(global short*)0);
x = x - (int)((private int*)0 == (private int*)(generic char*)0);
}
+
+// NOOPT-LABEL: test_fold_local
+// NOOPT: call void @test_fold_callee
+// NOOPT: store i32 addrspace(1)* null, i32 addrspace(1)** %glob, align 4
+// NOOPT: %{{.*}} = sub i64 %{{.*}}, 0
+// NOOPT: call void @test_fold_callee
+// NOOPT: %{{.*}} = add nsw i64 %{{.*}}, sext (i32 ptrtoint (i32 addrspace(3)* addrspacecast (i32 addrspace(4)* null to i32 addrspace(3)*) to i32) to i64)
+// NOOPT: %{{.*}} = sub nsw i64 %{{.*}}, 1
+void test_fold_local(void) {
+ global int* glob = (test_fold_callee(), (global int*)(generic char*)0);
+ long x = glob - (global int*)(generic char*)0;
+ x = x + (int)(test_fold_callee(), (local int*)(generic char*)(global short*)0);
+ x = x - (int)((local int*)0 == (local int*)(generic char*)0);
+}