Commit 675f720
authored
RMSD: reformulate two loops so their omp simd pragmas can be honoured (plumed#1438)
* RMSD: reformulate two loops so their omp simd pragmas can be honoured
A plain `./configure && make` fails on any machine whose default C++ compiler is
clang: configure enables OpenMP automatically, and src/tools/Makefile appends
-Werror, so the vectorizer's refusal is fatal.
RMSD.cpp:1443:35: error: loop not vectorized: the optimizer was unable to
perform the requested transformation; the transformation might be disabled or
specified as part of an unsupported transformation ordering
[-Werror,-Wpass-failed=transform-warning]
RMSD.cpp:1487:35: error: (the same, in getDDistanceDReference)
Both are attributed to the opening line of the enclosing function, which hides
the loop at fault. Each of the two functions contains exactly one
`#pragma omp simd`, so the attribution is unambiguous: the loops at lines 1479
and 1530.
The pragma is kept. The loop body is rewritten so the compiler can act on it:
the loop-invariant `(ddist_dc*-csum)` is hoisted into a named Vector, and the
Vector expression is expanded into its three components. Both loops now
vectorize at width 4, confirmed with -Rpass=loop-vectorize, instead of being
refused.
Alternatives measured with clang 20.1.1, all on the same tree:
braces around the if body still fails
hoisting the invariant only still fails
binding `Vector& dv=derivatives[iat]` still fails
flatten to `double*` + manual 3-way unroll vectorizes, but the pointer
is UB when n==0
per-component `derivatives[iat][k]` vectorizes <- chosen
The Vector arithmetic creates temporaries the vectorizer cannot see through, and
naming the element through a reference reintroduces them; only the direct
per-component form works.
No other pragma in the file is touched. The other eight active ones already
vectorize. Two more, on identically shaped std::vector<Vector> loops at lines
1339 and 1426, were commented out long ago because they gave wrong results with
the Intel compiler; these two had the same shape.
Behaviour is unchanged, and the 17 regtests that exercise these paths pass,
including rt-rmsd-displace, which is the align != displace case that actually
enters the modified branch.
This is the same class of problem as plumed#1437. It escapes CI because no job builds
clang with OpenMP enabled: the Linux workflow uses gcc and icpx, and macsimple
uses AppleClang without libomp, where `#pragma omp simd` is inert.
* RMSD: also unswitch getDistance's reduction loop
The first commit fixed the two loops that fail at -O3. Building PLUMED with
mpicxx at -O2 shows a third one, which -O3 happens to vectorize:
RMSD.cpp:1361:22: error: loop not vectorized: the optimizer was unable to
perform the requested transformation [-Werror,-Wpass-failed=transform-warning]
The remark is attributed to getDistance()'s opening line; the pragma is the
`omp simd reduction(+:localDist)` at line 1374. Its body branches on alEqDis
and safe, both of which are loop-invariant members, so the loop carries a
per-iteration test the vectorizer will not always unswitch by itself.
Hoisting the two branches out of the loop makes it vectorize at -O2 as well.
This is a pure unswitching: both conditions are invariant, the summation order
is unchanged, and the arithmetic is untouched, so results are bit-identical.
Measured on this file with clang 20.1.1, counting -Wpass-failed diagnostics
(-march makes no difference at any level):
-O level before after
-O0 0 0
-O1 5 4
-Os 8 7
-O2 3 0
-O3 2 0
-O1 and -Os remain non-clean, but not for a reason any source change can fix:
clang's loop vectorizer is effectively disabled there, so every `omp simd` in
the file is refused, including the ones that are perfectly good at -O2. Making
PLUMED buildable at those levels would mean not combining -Werror with
-Wpass-failed in the module makefiles; that is a build-system decision and is
deliberately left out of this PR.1 parent e44cef6 commit 675f720
1 file changed
Lines changed: 22 additions & 9 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
1371 | 1371 | | |
1372 | 1372 | | |
1373 | 1373 | | |
1374 | | - | |
1375 | | - | |
1376 | | - | |
1377 | | - | |
| 1374 | + | |
| 1375 | + | |
| 1376 | + | |
| 1377 | + | |
1378 | 1378 | | |
1379 | 1379 | | |
1380 | | - | |
| 1380 | + | |
| 1381 | + | |
| 1382 | + | |
| 1383 | + | |
1381 | 1384 | | |
1382 | 1385 | | |
1383 | 1386 | | |
| |||
1475 | 1478 | | |
1476 | 1479 | | |
1477 | 1480 | | |
1478 | | - | |
| 1481 | + | |
| 1482 | + | |
1479 | 1483 | | |
1480 | 1484 | | |
1481 | | - | |
| 1485 | + | |
| 1486 | + | |
| 1487 | + | |
| 1488 | + | |
1482 | 1489 | | |
| 1490 | + | |
1483 | 1491 | | |
1484 | 1492 | | |
1485 | 1493 | | |
| |||
1526 | 1534 | | |
1527 | 1535 | | |
1528 | 1536 | | |
1529 | | - | |
| 1537 | + | |
| 1538 | + | |
1530 | 1539 | | |
1531 | 1540 | | |
1532 | | - | |
| 1541 | + | |
| 1542 | + | |
| 1543 | + | |
| 1544 | + | |
1533 | 1545 | | |
| 1546 | + | |
1534 | 1547 | | |
1535 | 1548 | | |
1536 | 1549 | | |
| |||
0 commit comments