Skip to content

Commit

Permalink
Fixed occasional crash when constructing LineInterfaceGeometry inst…
Browse files Browse the repository at this point in the history
…ances (#12679)

When a `LineInterfaceGeometry` instance was constructed with a list of node pointers where at least one of them is null, the application would crash. The underlying reason was that calculating the points of the mid-line geometry failed, due to dereferencing the null pointer. This fix checks whether there are any null pointers in the provided vector of node pointers, and if there are it will return a vector of null pointers for the mid-line points.

Note that being able to deal with such input is required, since at element registration time we always provide the "blueprint" element with a list of null pointers for the element's nodes.
  • Loading branch information
avdg81 authored Sep 18, 2024
1 parent 868f44d commit 5824a0d
Show file tree
Hide file tree
Showing 2 changed files with 26 additions and 0 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@
#include "geometries/geometry.h"
#include "includes/node.h"

#include <algorithm>

namespace Kratos
{

Expand Down Expand Up @@ -240,6 +242,13 @@ class LineInterfaceGeometry : public Geometry<Node>
const auto points = this->Points();
const auto number_of_midline_nodes = std::size_t{points.size() / 2};

auto is_null = [](const auto& rNodePtr) { return rNodePtr == nullptr; };
if (std::any_of(points.ptr_begin(), points.ptr_end(), is_null)) {
// At least one point is not defined, so the points of the mid-line can't be computed.
// As a result, all the mid-line points will be undefined.
return PointerVector<Node>{number_of_midline_nodes};
}

auto result = PointerVector<Node>{};
for (std::size_t i = 0; i < number_of_midline_nodes; ++i) {
const auto mid_point = (points[i] + points[i + number_of_midline_nodes]) / 2;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,19 @@ KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometryIsAGeometry, KratosGeoMechanicsFastSu
KRATOS_EXPECT_NE(base_geometry, nullptr);
}

KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometryCanBeConstructedGivenASetOfNullPointersToNodes,
KratosGeoMechanicsFastSuiteWithoutKernel)
{
// The following constructor input data resembles what is done at element registration time
const auto six_null_pointers_to_nodes = Geometry<Node>::PointsArrayType{6};

const auto geometry = LineInterfaceGeometry<Line2D3<Node>>{six_null_pointers_to_nodes};

KRATOS_EXPECT_EQ(geometry.PointsNumber(), 6);
KRATOS_EXPECT_EQ(geometry.LocalSpaceDimension(), 1);
KRATOS_EXPECT_EQ(geometry.WorkingSpaceDimension(), 2);
}

KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometry_Create_CreatesNewInstanceOfCorrectType, KratosGeoMechanicsFastSuiteWithoutKernel)
{
const auto geometry = LineInterfaceGeometry<Line2D2<Node>>();
Expand All @@ -76,6 +89,8 @@ KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometry_Create_CreatesNewInstanceOfCorrectTy
KRATOS_EXPECT_NE(dynamic_cast<const LineInterfaceGeometry<Line2D2<Node>>*>(new_geometry.get()), nullptr);
KRATOS_EXPECT_EQ(new_geometry->PointsNumber(), 4);
KRATOS_EXPECT_EQ(new_geometry->Id(), 0);
KRATOS_EXPECT_EQ(new_geometry->LocalSpaceDimension(), 1);
KRATOS_EXPECT_EQ(new_geometry->WorkingSpaceDimension(), 2);
}

KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometry_CreateWithId_CreatesNewInstanceOfCorrectTypeAndId,
Expand All @@ -95,6 +110,8 @@ KRATOS_TEST_CASE_IN_SUITE(InterfaceGeometry_CreateWithId_CreatesNewInstanceOfCor
KRATOS_EXPECT_NE(dynamic_cast<const LineInterfaceGeometry<Line2D2<Node>>*>(new_geometry.get()), nullptr);
KRATOS_EXPECT_EQ(new_geometry->PointsNumber(), 4);
KRATOS_EXPECT_EQ(new_geometry->Id(), new_geometry_id);
KRATOS_EXPECT_EQ(new_geometry->LocalSpaceDimension(), 1);
KRATOS_EXPECT_EQ(new_geometry->WorkingSpaceDimension(), 2);
}

KRATOS_TEST_CASE_IN_SUITE(CreatingInterfaceWithThreeNodesThrows, KratosGeoMechanicsFastSuiteWithoutKernel)
Expand Down

0 comments on commit 5824a0d

Please sign in to comment.