Miscompile when indexing an array with small unsigned types.

This commit is contained in:
Christoffer Lerno
2024-12-28 17:39:25 +01:00
parent b7082f34a1
commit f5cea221a6
3 changed files with 13 additions and 9 deletions

View File

@@ -29,6 +29,7 @@
- Use `weak_odr` rather than `weak` on Windows which seems to prevent issues such as #1704.
- Use `weak` on dyn-symbols on Linux.
- Fix crash on project.json not having an empty set of targets.
- Miscompile when indexing an array with small unsigned types for enums.
### Stdlib changes
- Increase BitWriter.write_bits limit up to 32 bits.

View File

@@ -5292,10 +5292,9 @@ LLVMValueRef llvm_emit_array_gep_raw_index(GenContext *c, LLVMValueRef ptr, LLVM
LLVMTypeRef element_type = LLVMGetElementType(array_type);
Type *index_type = index->type;
ASSERT0(type_is_integer(index_type));
LLVMTypeRef idx_type = llvm_get_type(c, index_type);
if (type_is_unsigned(index_type) && type_size(index_type) < type_size(type_usz))
{
index_val = llvm_zext_trunc(c, index_val, idx_type);
index_val = llvm_zext_trunc(c, index_val, llvm_get_type(c, type_usz));
}
*alignment = type_min_alignment(llvm_abi_size(c, element_type), array_alignment);
return llvm_emit_pointer_inbounds_gep_raw(c, element_type, ptr, index_val);

View File

@@ -41,17 +41,21 @@ entry:
store i32 1, ptr %f, align 4
store i32 0, ptr %g, align 4
%0 = load i32, ptr %f, align 4
%ptroffset = getelementptr inbounds [4 x i8], ptr @"test.Foo$val", i32 %0
%zext = zext i32 %0 to i64
%ptroffset = getelementptr inbounds [4 x i8], ptr @"test.Foo$val", i64 %zext
%1 = load i32, ptr %f, align 4
%ptroffset1 = getelementptr inbounds [8 x i8], ptr @"test.Foo$testme", i32 %1
%zext1 = zext i32 %1 to i64
%ptroffset2 = getelementptr inbounds [8 x i8], ptr @"test.Foo$testme", i64 %zext1
%2 = load i32, ptr %g, align 4
%ptroffset2 = getelementptr inbounds [4 x i8], ptr @"test.Foo$val", i32 %2
%zext3 = zext i32 %2 to i64
%ptroffset4 = getelementptr inbounds [4 x i8], ptr @"test.Foo$val", i64 %zext3
%3 = load i32, ptr %g, align 4
%ptroffset3 = getelementptr inbounds [8 x i8], ptr @"test.Foo$testme", i32 %3
%zext5 = zext i32 %3 to i64
%ptroffset6 = getelementptr inbounds [8 x i8], ptr @"test.Foo$testme", i64 %zext5
%4 = load i32, ptr %ptroffset, align 4
%5 = load ptr, ptr %ptroffset1, align 8
%6 = load i32, ptr %ptroffset2, align 4
%7 = load ptr, ptr %ptroffset3, align 8
%5 = load ptr, ptr %ptroffset2, align 8
%6 = load i32, ptr %ptroffset4, align 4
%7 = load ptr, ptr %ptroffset6, align 8
%8 = call i32 (ptr, ...) @printf(ptr @.str.2, i32 %4, ptr %5, i32 %6, ptr %7)
ret void
}