Currently bitmasking is used for loadCoercion of vector values, this is troublesome because these operations propagate poison.
This patch uses a combination of vector operations instead.
Fixes PR63059.
Details
Diff Detail
- Repository
- rG LLVM Github Monorepo
Event Timeline
llvm/lib/Transforms/Utils/VNCoercion.cpp | ||
---|---|---|
316 | Do you also need to do this for the vector-of-pointers case that is handled above? |
llvm/lib/Transforms/Utils/VNCoercion.cpp | ||
---|---|---|
316 | Yes, the vector-of-pointers should be converted to a vector-of-ints and then the rest of the logic would work fine for that case. |
This causes an assertion failure:
define i11 @test(ptr %loc, <4 x i6> %v) { store <4 x i6> %v, ptr %loc %ref = load i11, ptr %loc ret i11 %ref }
llvm/lib/Transforms/Utils/VNCoercion.cpp | ||
---|---|---|
321 | Invert condition and early return? | |
377 | This looks incorrect to me for the case where the division isn't exact, e.g. this is a miscompile: define i16 @test(ptr %loc, <4 x i16> %v) { ; CHECK-LABEL: define i16 @test ; CHECK-SAME: (ptr [[LOC:%.*]], <4 x i16> [[V:%.*]]) { ; CHECK-NEXT: store <4 x i16> [[V]], ptr [[LOC]], align 8 ; CHECK-NEXT: [[GEP:%.*]] = getelementptr i8, ptr [[LOC]], i64 1 ; CHECK-NEXT: [[TMP1:%.*]] = extractelement <4 x i16> [[V]], i64 0 ; CHECK-NEXT: ret i16 [[TMP1]] ; store <4 x i16> %v, ptr %loc %gep = getelementptr i8, ptr %loc, i64 1 %ref = load i16, ptr %gep ret i16 %ref } The loaded value is the high part of elements zero and the low part of element 1, not just element 0. |
llvm/lib/Transforms/Utils/VNCoercion.cpp | ||
---|---|---|
377 | Nice catch! Thank you! NumEltsRequiredFromVec needs to take into consideration the offset. I'll try to support this case without making this even more complex. |
Do you also need to do this for the vector-of-pointers case that is handled above?