Dear GCC Developers,
I'm writing to report an observation regarding loop unswitching behavior when
compiling the attached code with GCC 15 using -O2 -funswitch-loops optimization
flags. Here's a detailed analysis of the issue:
Code Overview:
int
foo(double *a, double *b, double *c, double *d, double *r, int size, int order)
{
for (int i = 0; i < size; i++)
{
double tmp;
if (order < 3)
tmp = -8 * a[i];
else
tmp = -4 * b[i];
double x = 3 * tmp + d[i] + tmp;
if (5 > order)
x = 2;
if (order == 12345)
x = 5;
for (int j = 0; j < size; j++)
{
double y = 3.4f * tmp + d[i];
r[j] += x + y;
}
}
return 0;
}
Outer loop with multiple conditional checks on 'order' parameter.
Complex control flow with three independent conditionals.
Inner loop containing runtime-invariant computations.
Observed Behavior:
The compiler fails to unswitch the outer loop despite the presence of multiple
loop-invariant conditions. This prevents:
Constant propagation of 'x' variable. Elimination of dead code paths (order ==
12345 and 5 > order check).
Current unswitching (tree_unswitch_outer_loop) appears limited to inner loop
guards. What prevents handling nested loops with complex control flow?
Potential Constraints:
Register pressure considerations in multi-versioned loops. Code size explosion
vs. runtime tradeoffs. Interaction with subsequent optimization passes.
Could you help clarify:
Architectural constraints in current unswitching implementation?
Planned improvements for nested loop optimization?
Recommended workarounds for such patterns?
Thank you for your time and expertise. I'd be happy to provide additional
details if needed.
Best regards,