-// Copyright (C) 2007-2020 CEA/DEN, EDF R&D
+// Copyright (C) 2007-2021 CEA/DEN, EDF R&D
//
// This library is free software; you can redistribute it and/or
// modify it under the terms of the GNU Lesser General Public
#include <SMESH_TypeDefs.hxx>
#include <SMESH_subMesh.hxx>
#include <SMESH_MesherHelper.hxx>
+#include <SMESH_File.hxx>
#include "utilities.h"
try {
OSD_File( fileName ).Remove();
}
- catch ( Standard_ProgramError ) {
+ catch ( Standard_ProgramError& ) {
MESSAGE("Can't remove file: " << fileName.ToCString() << " ; file does not exist or permission denied");
}
}
//=============================================================================
// Here we are going to use the GHS3DPRL mesher for tetra-hpc (formerly tepal in v3 (2014))
bool GHS3DPRLPlugin_GHS3DPRL::Compute(SMESH_Mesh& theMesh,
- const TopoDS_Shape& theShape)
+ const TopoDS_Shape& /*theShape*/)
{
SMESH_MesherHelper helper( theMesh );
bool ok = Compute( theMesh, &helper );
//=============================================================================
// Here we are going to use the GHS3DPRL mesher for tetra-hpc (formerly tepal in v3 (2014))
bool GHS3DPRLPlugin_GHS3DPRL::Compute(SMESH_Mesh& theMesh,
- SMESH_MesherHelper* theHelper)
+ SMESH_MesherHelper* /*theHelper*/)
{
bool Ok=false;
- TCollection_AsciiString pluginerror("ghs3dprl: ");
+ TCollection_AsciiString pluginerror("MG-TETRA_HPC: ");
SMESHDS_Mesh* meshDS = theMesh.GetMeshDS();
if ( theMesh.NbTriangles() == 0 )
return error( COMPERR_BAD_INPUT_MESH, "No triangles in the mesh" );
if (_hypothesis==NULL){
- pluginerror += "No existing parameters/hypothesis for GHS3DPRL";
+ pluginerror += "No existing parameters/hypothesis for MG-TETRA_HPC";
cout <<"\n"<<pluginerror<<"\n\n";
error(COMPERR_ALGO_FAILED, pluginerror.ToCString() );
return false;
map <int,int> aSmdsToGHS3DPRLIdMap;
map <int,const SMDS_MeshNode*> aGHS3DPRLIdToNodeMap;
- GHS3DPRL_In = path + "GHS3DPRL";
+ _genericName = GHS3DPRLPlugin_Hypothesis::GetFileName(_hypothesis);
+ TCollection_AsciiString aGenericName((char*) _genericName.c_str() );
+ GHS3DPRL_In = aGenericName + ".mesh";
GHS3DPRL_Out = path + casenamemed;
- GHS3DPRL_Out_Mesh = path + casenamemed + "_out.mesh";
+ GHS3DPRL_Out_Mesh = aGenericName + "_out.mesh";
GHS3DPRL_Outxml = path + casenamemed + ".xml"; //master file
- logFileName = path + casenamemed + ".log"; // MG library output
+ logFileName = aGenericName + ".log"; // MG library output
NbPart=_NbPart;
Gradation=_Gradation;
MinSize=_MinSize;
// --verbose=0 --menu=no --launchtetra=yes;
run_GHS3DPRL = run_GHS3DPRL +
- " --casename=" + GHS3DPRL_In +
+ " --casename=" + aGenericName +
" --number=" + NbPart +
" --medname=" + GHS3DPRL_Out +
" --launchtetra=yes" +
system( run_nokeep_files.ToCString() ); //clean files
run_nokeep_files = rm + GHS3DPRL_In + "* ";
- fileskinmesh=path + "GHS3DPRL.mesh";
- GHS3DPRL_Out = path + casenamemed;
removeFile( GHS3DPRL_Outxml ); //only the master xml file
MG_TetraHPC_API mgTetraHPC( _computeCanceled, _progress );
if ( !useLib )
mgTetraHPC.SetUseExecutable();
- exportGMF( &mgTetraHPC, fileskinmesh.ToCString(), meshDS );
+ exportGMF( &mgTetraHPC, GHS3DPRL_In.ToCString(), meshDS );
- if ( useLib )
+ if ( true /*useLib*/ )
{
- TCollection_AsciiString cmd = TCollection_AsciiString("mg-tetra_hpc.exe") +
- " --number_of_subdomains=" + NbPart +
- " --gradation=" + Gradation +
- " --min_size=" + MinSize +
- " --max_size=" + MaxSize +
- " --verbose=3" +
- " --out=" + GHS3DPRL_Out_Mesh +
- " " + _AdvOptions.c_str();
+ TCollection_AsciiString cmd = TCollection_AsciiString();
+ if (_Multithread)
+ cmd += "mg-tetra_hpc.exe";
+ else
+ cmd = cmd + "mpirun --n " + NbPart + " mg-tetra_hpc_mpi.exe";
+ cmd = cmd + " --in=" + GHS3DPRL_In;
+ if (_Multithread)
+ cmd = cmd +" --max_number_of_threads=" + NbPart;
+ cmd = cmd + " --gradation=" + Gradation;
+ cmd = cmd + " --min_size=" + MinSize;
+ cmd = cmd + " --max_size=" + MaxSize;
+ cmd = cmd + " --verbose=3";
+ cmd = cmd + " --out=" + GHS3DPRL_Out_Mesh;
+ cmd = cmd + " " + _AdvOptions.c_str();
+ cmd = cmd + " 1>" + logFileName;
cout << endl
<< " Run mg-tetra_hpc as library. Creating a mesh file " << GHS3DPRL_Out_Mesh << endl
<< " Creating a log file : " << logFileName << endl << endl;
mgTetraHPC.SetLogFile( logFileName.ToCString() );
- mgTetraHPC.Compute( cmd.ToCString() );
+ std::string log;
+ Ok = mgTetraHPC.Compute( cmd.ToCString(), log );
- std::string log = mgTetraHPC.GetLog();
- if ( log.find(" Dlim " ) != std::string::npos ||
- log.find(" license ") != std::string::npos )
- return error("License problem");
+ if (!Ok)
+ {
+ std::cout << "Error: " << std::endl;
+ std::cout << log << std::endl;
+ // try to guess an error from the output log
+ std::string log2 = mgTetraHPC.GetLog();
+ if ( log2.find("Dlim" ) != std::string::npos ||
+ log2.find("icense") != std::string::npos )
+ return error("License problem");
+ std::cout << log2 << std::endl;
+ if ( log2.find("You are using an empty MPI stubs library") != std::string::npos )
+ {
+ std:string msg = "You are using an empty MPI stubs library. Please build it first to be able to use mg-tetra_hpc_mpi.exe.\n";
+ msg += "./salome context\n";
+ msg += "cd $MESHGEMSHOME/stubs\n";
+ msg += "mpicc meshgems_mpi.c -DMESHGEMS_LINUX_BUILD -I../include -shared -fPIC -o $MESHGEMSHOME/lib/Linux_64/libmeshgems_mpi.so";
+ return error(msg);
+ }
+ return error(log);
+ }
// set --launchtetra=no
int yesPos = run_GHS3DPRL.Search("launchtetra") + sizeof("launchtetra");
cout<<" Write input file for mg-tetra_hpc "<<fileskinmesh<<"...";
cout<<" ...done\n";
}
- fileskinmed=path + "GHS3DPRL_skin.med";
- cout<<" Write file "<<fileskinmed<<"...";
- theMesh.ExportMED(fileskinmed.ToCString(),"SKIN_INITIAL",true);
- cout<<" ...done\n\n";
- cout<<"GHS3DPRL command :\n "<<run_GHS3DPRL.ToCString()<<endl;
+ if (!_Multithread)
+ {
+ fileskinmed=path + casenamemed + "_skin.med";
+ cout<<" Write file "<<fileskinmed<<"...";
+ theMesh.ExportMED(fileskinmed.ToCString(),"SKIN_INITIAL",true);
+ cout<<" ...done\n\n";
+ }
+
+ // convert .mesh (one or several) to med file(s) with xml master file if mpi
+ cout<<"Mesh conversion command :\n "<<run_GHS3DPRL.ToCString()<<endl;
//sometimes it is better to wait flushing files on slow filesystem...
- system( "sleep 3" );
+ // system( "sleep 3" );
//launch tetrahpc2med which launch mg-tetra_hpc.py which launch mg-tetra_hpc(_mpi?).exe
res = system( run_GHS3DPRL.ToCString() );
- if (res > 0)
+ if (res > 0)
{
pluginerror = pluginerror + "PROBLEM tetrahpc2med command";
cout<<pluginerror<<endl;
error(COMPERR_ALGO_FAILED, pluginerror.ToCString());
return false; //but it is not a problem but if true my message is overwritten
}
- system( "sleep 3" );
+ //system( "sleep 3" );
if (_Background) {
- pluginerror = pluginerror + "backgrounding... plugin is not waiting for output files "+ casenamemed + "_*.med";
+ pluginerror = pluginerror + "backgrounding... plugin is not waiting for output files "+ path +casenamemed + "_*.med";
cout<<pluginerror<<endl;
error(COMPERR_NO_MESH_ON_SHAPE, pluginerror.ToCString());
return false; //but it is not a problem but if true my message is overwritten
//return true; //but it is not a problem,
}
- // read a result, GHS3DPRL_Out is the name of master file (previous xml format)
- FILE * aResultFile = fopen( GHS3DPRL_Outxml.ToCString(), "r" );
- if (aResultFile){
- Ok = true;
- fclose(aResultFile);
- cout<<"GHS3DPRL OK output master file "<<casenamemed<<".xml exist !\n\n";
- pluginerror = pluginerror + "MG-tetra_hpc mesh(es) not loaded in memory, are stored in files "+ casenamemed + "_*.med";
- cout<<pluginerror<<endl;
- error(COMPERR_WARNING, pluginerror.ToCString() );
- if (!_KeepFiles) system( run_nokeep_files.ToCString() );
+ if (_Multithread)
+ {
+ // check the med file has been created (only one med file, since multithread)
+ TCollection_AsciiString resuMedFile = TCollection_AsciiString(path) + casenamemed + "_1.med";
+ SMESH_File file( resuMedFile.ToCString() );
+ if (file.exists() && file.size() > 0)
+ {
+ Ok = true;
+ pluginerror = pluginerror + "MG-tetra_hpc mesh not loaded in memory, is stored in file "+ resuMedFile;
+ cout<<pluginerror<<endl;
+ error(COMPERR_WARNING, pluginerror.ToCString() );
+ if (!_KeepFiles) system( run_nokeep_files.ToCString() );
+ }
}
- else{
- Ok = false; //it is a problem AND my message is NOT overwritten
- pluginerror = pluginerror + "output master file " + casenamemed + ".xml do not exist";
- cout<<pluginerror<<endl;
- error(COMPERR_ALGO_FAILED, pluginerror.ToCString() );
- cout<<"GHS3DPRL KO output files "<<GHS3DPRL_Out<<" do not exist ! see intermediates files keeped:\n";
- TCollection_AsciiString run_list_files("ls -alt ");
- run_list_files += GHS3DPRL_Out + "* " + GHS3DPRL_In + "* " + path + "tetrahpc.log";
- system( run_list_files.ToCString() );
- cout<<endl;
+ else
+ {
+ // read a result, GHS3DPRL_Outxml is the name of master file (previous xml format)
+ FILE * aResultFile = fopen( GHS3DPRL_Outxml.ToCString(), "r" );
+ if (aResultFile){
+ Ok = true;
+ fclose(aResultFile);
+ cout<<"MG-TETRA_HPC OK output master file "<<casenamemed<<".xml exist !\n\n";
+ pluginerror = pluginerror + "MG-tetra_hpc meshes not loaded in memory, are stored in files "+ path + casenamemed + "_*.med";
+ cout<<pluginerror<<endl;
+ error(COMPERR_WARNING, pluginerror.ToCString() );
+ if (!_KeepFiles) system( run_nokeep_files.ToCString() );
+ }
+ else{
+ Ok = false; //it is a problem AND my message is NOT overwritten
+ pluginerror = pluginerror + "output master file " + casenamemed + ".xml do not exist";
+ cout<<pluginerror<<endl;
+ error(COMPERR_ALGO_FAILED, pluginerror.ToCString() );
+ cout<<"MG-TETRA_HPC KO output files "<<GHS3DPRL_Out<<" do not exist ! see intermediate files kept:\n";
+ TCollection_AsciiString run_list_files("ls -alt ");
+ run_list_files += GHS3DPRL_Out + "* " + GHS3DPRL_In + "* " + logFileName;
+ system( run_list_files.ToCString() );
+ cout<<endl;
+ }
}
+
return Ok;
}
const TopoDS_Shape& aShape,
MapShapeNbElems& aResMap)
{
- int nbtri = 0, nbqua = 0;
+ smIdType nbtri = 0, nbqua = 0;
double fullArea = 0.0;
for (TopExp_Explorer exp(aShape, TopAbs_FACE); exp.More(); exp.Next()) {
TopoDS_Face F = TopoDS::Face( exp.Current() );
"Submesh can not be evaluated",this));
return false;
}
- std::vector<int> aVec = (*anIt).second;
- nbtri += Max(aVec[SMDSEntity_Triangle],aVec[SMDSEntity_Quad_Triangle]);
- nbqua += Max(aVec[SMDSEntity_Quadrangle],aVec[SMDSEntity_Quad_Quadrangle]);
+ std::vector<smIdType> aVec = (*anIt).second;
+ nbtri += std::max(aVec[SMDSEntity_Triangle],aVec[SMDSEntity_Quad_Triangle]);
+ nbqua += std::max(aVec[SMDSEntity_Quadrangle],aVec[SMDSEntity_Quad_Quadrangle]);
GProp_GProps G;
BRepGProp::SurfaceProperties(F,G);
double anArea = G.Mass();
}
// collect info from edges
- int nb0d_e = 0, nb1d_e = 0;
+ smIdType nb0d_e = 0, nb1d_e = 0;
bool IsQuadratic = false;
bool IsFirst = true;
TopTools_MapOfShape tmpMap;
tmpMap.Add(E);
SMESH_subMesh *aSubMesh = aMesh.GetSubMesh(exp.Current());
MapShapeNbElemsItr anIt = aResMap.find(aSubMesh);
- std::vector<int> aVec = (*anIt).second;
+ std::vector<smIdType> aVec = (*anIt).second;
nb0d_e += aVec[SMDSEntity_Node];
- nb1d_e += Max(aVec[SMDSEntity_Edge],aVec[SMDSEntity_Quad_Edge]);
+ nb1d_e += std::max(aVec[SMDSEntity_Edge],aVec[SMDSEntity_Quad_Edge]);
if(IsFirst) {
IsQuadratic = (aVec[SMDSEntity_Quad_Edge] > aVec[SMDSEntity_Edge]);
IsFirst = false;
double aVolume = G.Mass();
double tetrVol = 0.1179*ELen*ELen*ELen;
double CoeffQuality = 0.9;
- int nbVols = (int)aVolume/tetrVol/CoeffQuality;
- int nb1d_f = (nbtri*3 + nbqua*4 - nb1d_e) / 2;
- int nb1d_in = (int) ( nbVols*6 - nb1d_e - nb1d_f ) / 5;
- std::vector<int> aVec(SMDSEntity_Last);
- for(int i=0; i<SMDSEntity_Last; i++) aVec[i]=0;
+ smIdType nbVols = (smIdType)aVolume/tetrVol/CoeffQuality;
+ smIdType nb1d_f = (nbtri*3 + nbqua*4 - nb1d_e) / 2;
+ smIdType nb1d_in = (smIdType) ( nbVols*6 - nb1d_e - nb1d_f ) / 5;
+ std::vector<smIdType> aVec(SMDSEntity_Last);
+ for(smIdType i=0; i<SMDSEntity_Last; i++) aVec[i]=0;
if( IsQuadratic ) {
aVec[SMDSEntity_Node] = nb1d_in/6 + 1 + nb1d_in;
aVec[SMDSEntity_Quad_Tetra] = nbVols - nbqua*2;