https://gcc.gnu.org/bugzilla/show_bug.cgi?id=123539
Bug ID: 123539
Summary: Signed overflow introduced by vectorizer
Product: gcc
Version: 16.0
Status: UNCONFIRMED
Severity: normal
Priority: P3
Component: tree-optimization
Assignee: unassigned at gcc dot gnu.org
Reporter: kristerw at gcc dot gnu.org
Blocks: 118443
Target Milestone: ---
The vectorizer introduces new signed overflow when the function below is
compiled for x86_64 with -O3. This was supposed to be fixed by PR121631, but
the issue is still present.
struct mystr
{
int f1;
int f2;
};
struct mystr a[16];
struct mystr b[16];
int res1, res2;
void
foo (void)
{
int i;
int sum1 = 0;
int sum2 = 0;
for (i = 0; i < 16; i++)
{
sum1 += a[i].f1 + b[i].f1;
sum2 += a[i].f2 + b[i].f2;
}
res1 = sum1;
res2 = sum2;
}
The final reduction in the vectorized loop is done as:
int _7;
int _8;
int _9;
vector(4) unsigned int _16;
int _37;
int _38;
int _39;
[...]
_16 = VIEW_CONVERT_EXPR<vector(4) unsigned int>(vect_sum2_14.12_17);
_9 = BIT_FIELD_REF <_16, 32, 0>;
_8 = BIT_FIELD_REF <_16, 32, 32>;
_7 = BIT_FIELD_REF <_16, 32, 64>;
_37 = BIT_FIELD_REF <_16, 32, 96>;
_38 = _9 + _7;
_39 = _8 + _37;
res1 = _38;
res2 = _39;
return;
The vector is converted to unsigned, but the extracted values are still signed,
so the additions _38 and _39 may overflow and invoke undefined behavior for
input where the original code had defined behavior.
Referenced Bugs:
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=118443
[Bug 118443] [Meta bug] Bugs triggered by and blocking more smtgcc testing