Different behaviou of setMeshQuads() between v3.1.2 and v3.2.0 in setting 2D mesh connectivity

  <mesh name="A-Mesh" dimensions="2">
    <use-data name="etaHOS" />
    <use-data name="UHOS" />
  </mesh>

  <mesh name="B-Mesh" dimensions="2">
    <use-data name="etaHOS" />
    <use-data name="UHOS" />
  </mesh>

  <participant name="A">
    <provide-mesh name="A-Mesh" />
    <receive-mesh name="B-Mesh" from="B" />
    <read-data name="etaHOS" mesh="A-Mesh" />
    <read-data name="UHOS" mesh="A-Mesh" />
    <mapping:linear-cell-interpolation direction="read" from="B-Mesh" to="A-Mesh" constraint="consistent" />
  </participant>

  <participant name="B">
    <provide-mesh name="B-Mesh" />
    <write-data name="etaHOS" mesh="B-Mesh" />
    <write-data name="UHOS" mesh="B-Mesh" />
  </participant>

As shown above, pure 2D coupling ({x0, y0,x1, y1,x2, y2,… …, xn, yn} passed to precicef_set_vertices()), to satisfy mapping:linear-cell-interpolation, precicef_set_mesh_quads() is called to build connectivities for Mesh-B. But got the following error in v3.2.0. It works fine in v3.1.2. Wondering if there’s any un-documented change in behavious of the precicef_set_mesh_quads() function. How can I get around this? Many thanks.

ASSERTION FAILED
Location:   precice::math::geometry::ConvexityResult precice::math::geometry::isConvexQuad(std::array<Eigen::Matrix<double, -1, 1>, 4>)
File:       /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/src/math/geometry.cpp:149
Expression: std::all_of(coords.cbegin(), coords.cend(), [](const auto &v) { return v.size() == 3; })
Rank:       0
Arguments:
  0: "This only works in 3D." == This only works in 3D.

Stacktrace:
 0# 0x00007FC652F4458C in /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/platforms/lib64/libprecice.so.3
 1# 0x00007FC65272779B in /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/platforms/lib64/libprecice.so.3
 2# 0x00007FC652E8DADA in /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/platforms/lib64/libprecice.so.3
 3# precice::Participant::setMeshQuads(precice::span<char const, 18446744073709551615ul>, precice::span<int const, 18446744073709551615ul>) in /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/platforms/lib64/libprecice.so.3
 4# precicef_set_mesh_quads_ in /scratcha-fdgs/lux/OpenFOAM/lux-v2106/platforms/precice-3.2.0/platforms/lib64/libprecice.so.3

For 3D cases, where precicef_set_mesh_tetrahedra() is called, the code works fine both in v3.1.2 and v3.2.0.

@Makis After digging into the source code, found that in setMeshQuads(), there’s a line:

    auto convexity = math::geometry::isConvexQuad(coords);

at beginning of which is:

  PRECICE_ASSERT(std::all_of(coords.cbegin(), coords.cend(),
                             [](const auto &v) { return v.size() == 3; }),
                 "This only works in 3D.");

Guess this assert will call std::abort() if dim != 3 in Degub mode, which is unfortunate my case. And previously in v3.1.2 I am only running in Release mode, that is why I didn’t get error.

My question is, my earlier runs in v3.1.2 showed me that precice works fine when I call setMeshQuads() for pure 2D cases, why in the above PRECICE_ASSERT it is said “This only works in 3D”? My use case is 2D volume coupling, and I quote your document “For volume coupling in 2D, mesh connectivity boils down to defining triangles and / or quads between vertices”.

Rebuild with Release mode, got another error from same function call (math::geometry::isConvexQuad(coords)):

---[precice] ERROR:  Non-planar quads are not supported. The vertex coordinates are: [312.5,2.55, 375,2.55, 375,3.825, 312.5,3.825].

This is not happening in v3.1.2. The difference in configuring v3.1.2 and v3.2.0 is just replaced boost 1.82.0 to 1.86.0. same eigen lib.

made following change to the precice code, now it works. Hope this will not break the precice internal logic.

ConvexityResult isConvexQuad(std::array<Eigen::VectorXd, 4> coords)
{
  // Ensure all points have at least 2 or 3 dimensions
  PRECICE_ASSERT(std::all_of(coords.cbegin(), coords.cend(),
                             [](const auto& v) {
                               return v.size() == 2 || v.size() == 3;
                             }),
                 "All coordinates must be 2D or 3D.");

  // If coords are 2D, extend them to 3D by adding a zero z-component
  if (coords[0].size() == 2) {
    for (auto& v : coords) {
      Eigen::VectorXd extended(3);
      extended << v[0], v[1], 0.0;
      v = extended;
    }
  }

  // Now ensure all vectors are 3D
  PRECICE_ASSERT(std::all_of(coords.cbegin(), coords.cend(),
                             [](const auto& v) { return v.size() == 3; }),
                 "This only works in 3D.");

  // ...The rest remains the same...
}

so far the tests are normal.

Hi,
This definitely a bug in preCICE.
Quads were never designed to be used in 2D, which changed with the introduction of the linear cell interpolation mapping.

Thanks for doing the research! I opened an issue:

Best
Frédéric