https://gcc.gnu.org/g:b44b4f74344e094ff58125ed2f00dbb70aafc942
commit r16-6235-gb44b4f74344e094ff58125ed2f00dbb70aafc942 Author: Richard Biener <[email protected]> Date: Wed Dec 17 14:38:23 2025 +0100 c/123156 - overflow in shuffle mask for __builtin_shufflevector At some point the permute vector element type had to match the value elemnt in size which easily leads to overflow for char element types as shown in the testcase. This was relaxed for constant permute masks, so use ssizetype. PR c/123156 gcc/c-family/ * c-common.cc (c_build_shufflevector): Use ssizetype for the permute vector element type. gcc/testsuite/ * gcc.dg/torture/builtin-shufflevector-pr123156.c: New testcase. Diff: --- gcc/c-family/c-common.cc | 4 +-- .../torture/builtin-shufflevector-pr123156.c | 40 ++++++++++++++++++++++ 2 files changed, 41 insertions(+), 3 deletions(-) diff --git a/gcc/c-family/c-common.cc b/gcc/c-family/c-common.cc index 3cec729c901c..1200a025cc97 100644 --- a/gcc/c-family/c-common.cc +++ b/gcc/c-family/c-common.cc @@ -1260,9 +1260,7 @@ c_build_shufflevector (location_t loc, tree v0, tree v1, vec_perm_indices indices (sel, 2, maskl); tree ret_type = build_vector_type (TREE_TYPE (TREE_TYPE (v0)), maskl); - tree mask_type = build_vector_type (build_nonstandard_integer_type - (TREE_INT_CST_LOW (TYPE_SIZE (TREE_TYPE (ret_type))), 1), - maskl); + tree mask_type = build_vector_type (ssizetype, maskl); /* Pad out arguments to the common vector size. */ if (v0n < maskl) { diff --git a/gcc/testsuite/gcc.dg/torture/builtin-shufflevector-pr123156.c b/gcc/testsuite/gcc.dg/torture/builtin-shufflevector-pr123156.c new file mode 100644 index 000000000000..ec220bcf39ca --- /dev/null +++ b/gcc/testsuite/gcc.dg/torture/builtin-shufflevector-pr123156.c @@ -0,0 +1,40 @@ +/* { dg-do run } */ + +#include <stdint.h> + +#define BS_VEC(type, num) type __attribute__((vector_size(num * sizeof(type)))) +#define BITCAST(T, F, arg) \ + ((union { \ + F src; \ + T dst; \ + })arg) \ + .dst + +uint64_t func_1() +{ + BS_VEC(uint64_t, 32) BS_VAR_0; + BS_VAR_0 = BITCAST( + BS_VEC(uint64_t, 32), BS_VEC(uint8_t, 256), + __builtin_shufflevector( + (BS_VEC(uint8_t, 2)){ 2 }, (BS_VEC(uint8_t, 2)){}, 1, 0, 2, 2, 2, 3, + 1, 2, 3, 1, 3, 3, 2, 1, 3, 0, 2, 2, 1, 2, 1, 3, 1, 1, 0, 0, 2, 0, 3, + 2, 2, 0, 1, 3, 1, 2, 0, 2, 0, 3, 0, 0, 2, 0, 2, 1, 3, 2, 3, 2, 1, 1, + 2, 3, 3, 3, 3, 0, 1, 2, 3, 2, 0, 2, 2, 2, 0, 3, 3, 3, 1, 3, 0, 0, 2, + 3, 1, 1, 2, 2, 1, 2, 0, 0, 3, 2, 2, 3, 2, 2, 3, 2, 0, 2, 2, 0, 2, 1, + 3, 1, 0, 2, 1, 3, 2, 1, 0, 2, 3, 0, 1, 3, 2, 1, 3, 1, 1, 3, 2, 2, 0, + 3, 2, 2, 0, 3, 0, 3, 2, 3, 1, 3, 2, 3, 3, 2, 2, 0, 0, 0, 2, 1, 3, 1, + 2, 2, 3, 0, 1, 3, 1, 1, 2, 0, 1, 2, 1, 2, 0, 2, 0, 2, 3, 3, 3, 1, 2, + 0, 3, 1, 2, 0, 1, 0, 3, 0, 0, 3, 2, 2, 0, 3, 1, 2, 0, 1, 1, 3, 0, 1, + 3, 1, 3, 2, 1, 3, 1, 2, 1, 1, 0, 1, 3, 3, 2, 3, 2, 2, 0, 2, 2, 2, 1, + 1, 0, 3, 1, 3, 0, 3, 0, 0, 1, 3, 3, 1, 2, 1, 1, 3, 1, 0, 2, 1, 3, 2, + 1, 3, 2, 2, 2, 3, 2, 0, 1, 3, 3, 3, 0, 0, 0, 1, 3, 2, 2, 1)); + return BS_VAR_0[0]; +} + +int main() +{ + uint64_t BS_CHECKSUM = func_1(); + if (BS_CHECKSUM != 0x0000000000000200ull) + __builtin_abort (); + return 0; +}
