Skip to content

Commit

Permalink
Fix Mesh::operator=
Browse files Browse the repository at this point in the history
bcnames are now stored in FaceDescriptor (as string members, no
pointers), so the name mapping must be applied to materials/bcnames
(depending on the mesh dimension).
  • Loading branch information
mhochsteger committed Mar 25, 2024
1 parent dfba4ed commit 29c6b8e
Showing 1 changed file with 10 additions and 9 deletions.
19 changes: 10 additions & 9 deletions libsrc/meshing/meshclass.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -319,26 +319,27 @@ namespace netgen
hmin = mesh2.hmin;
maxhdomain = mesh2.maxhdomain;

// Remap string* values to new mesh
std::map<const string*, string*> names_map;
for (auto fi : Range(facedecoding))
names_map[&mesh2.facedecoding[fi].bcname] = &facedecoding[fi].bcname;

This comment has been minimized.

Copy link
@StefanBruens

StefanBruens Dec 20, 2024

Contributor

What is the intention of this map?

facedecoding has just been assigned as mesh2.facedecoding, so this is an identity mapping.


materials.SetSize( mesh2.materials.Size() );
for ( int i = 0; i < mesh2.materials.Size(); i++ )
if ( mesh2.materials[i] ) materials[i] = new string ( *mesh2.materials[i] );
{
const string * old_name = mesh2.materials[i];
if ( old_name ) materials[i] = dimension == 2 ? names_map[old_name] : new string ( *old_name );

This comment has been minimized.

Copy link
@StefanBruens

StefanBruens Dec 20, 2024

Contributor

This is quite problematic:

  1. It leaks the old string (if bcnames[i] != nullptr)
  2. It assigns the address from the FaceDescriptor bcname member to bcnames[i]. The address becomes invalid as soon the facedecoding array is grown, and causes double frees.

See #203

else materials[i] = 0;
}

std::map<const string*, string*> bcmap;
bcnames.SetSize( mesh2.bcnames.Size() );
for ( int i = 0; i < mesh2.bcnames.Size(); i++ )
{
if ( mesh2.bcnames[i] ) bcnames[i] = new string ( *mesh2.bcnames[i] );
const string * old_name = mesh2.bcnames[i];
if ( old_name ) bcnames[i] = dimension == 3 ? names_map[old_name] : new string ( *old_name );
else bcnames[i] = 0;
bcmap[mesh2.bcnames[i]] = bcnames[i];
}

// Remap string* members in FaceDescriptor to new mesh
for (auto & f : facedecoding)
f.SetBCName( bcmap[&f.GetBCName()] );


cd2names.SetSize(mesh2.cd2names.Size());
for (int i=0; i < mesh2.cd2names.Size(); i++)
if (mesh2.cd2names[i]) cd2names[i] = new string(*mesh2.cd2names[i]);
Expand Down

0 comments on commit 29c6b8e

Please sign in to comment.