v0.16.0
Loading...
Searching...
No Matches
Public Member Functions | Public Attributes | Static Public Attributes | List of all members
MoFEM::CommInterface Struct Reference

Managing BitRefLevels. More...

#include "src/interfaces/CommInterface.hpp"

Inheritance diagram for MoFEM::CommInterface:
[legend]
Collaboration diagram for MoFEM::CommInterface:
[legend]

Public Member Functions

MoFEMErrorCode query_interface (boost::typeindex::type_index type_index, UnknownInterface **iface) const
 
 CommInterface (const MoFEM::Core &core)
 
 ~CommInterface ()=default
 Destructor.
 
- Public Member Functions inherited from MoFEM::UnknownInterface
template<class IFACE >
MoFEMErrorCode registerInterface (bool error_if_registration_failed=true)
 Register interface.
 
template<class IFACE >
MoFEMErrorCode getInterface (IFACE *&iface) const
 Get interface reference to pointer of interface.
 
template<class IFACE >
MoFEMErrorCode getInterface (IFACE **const iface) const
 Get interface pointer to pointer of interface.
 
template<class IFACE , typename boost::enable_if< boost::is_pointer< IFACE >, int >::type = 0>
IFACE getInterface () const
 Get interface pointer to pointer of interface.
 
template<class IFACE , typename boost::enable_if< boost::is_reference< IFACE >, int >::type = 0>
IFACE getInterface () const
 Get reference to interface.
 
template<class IFACE >
IFACE * getInterface () const
 Function returning pointer to interface.
 
virtual ~UnknownInterface ()=default
 

Public Attributes

MoFEM::CorecOre
 
bool dEbug
 

Static Public Attributes

static bool debug = false
 
static Sev sev = Sev::verbose
 

Load file

using LoadFileFun = std::function< std::array< Range, 4 >(std::array< Range, 4 > &&, std::vector< const CubitMeshSets * > &&)>
 
static std::array< Range, 4 > defaultProcSkinFun (std::array< Range, 4 > &&proc_ents_skin, std::vector< const CubitMeshSets * > &&vec_ptr)
 
static MoFEMErrorCode loadFileRootProcAllRestDistributed (moab::Interface &moab, const char *file_name, int dim, LoadFileFun proc_skin_fun=defaultProcSkinFun, const char *options="PARALLEL=BCAST;PARTITION=")
 Root proc has whole mesh, other procs only part of it.
 
static Range getPartEntities (moab::Interface &moab, int part)
 

Functions when root proc has all entities

@

using EntitiesPetscVector = std::pair< std::pair< Range, Range >, SmartPetscObj< Vec > >
 
using UpdateGhosts = std::function< MoFEMErrorCode(Vec vec)>
 
static EntitiesPetscVector createEntitiesPetscVector (MPI_Comm comm, moab::Interface &moab, std::function< Range(Range)> get_entities_fun, const int nb_coeffs, Sev sev=Sev::verbose, int root_rank=0, bool get_vertices=true)
 Create a ghost vector for exchanging data.
 
static EntitiesPetscVector createEntitiesPetscVector (MPI_Comm comm, moab::Interface &moab, int dim, const int nb_coeffs, Sev sev=Sev::verbose, int root_rank=0)
 Create a ghost vector for exchanging data.
 
static MoFEMErrorCode defaultUpdateGhosts (Vec v)
 
static MoFEMErrorCode setVectorFromTag (moab::Interface &moab, EntitiesPetscVector &vec, Tag tag)
 Set the Vector From Tag object.
 
static MoFEMErrorCode setTagFromVector (moab::Interface &moab, EntitiesPetscVector &vec, Tag tag)
 Set the Tag From Vector object.
 
static MoFEMErrorCode updateEntitiesPetscVector (moab::Interface &moab, EntitiesPetscVector &vec, Tag tag, UpdateGhosts update_gosts=defaultUpdateGhosts)
 Exchange data between vector and data.
 

Make elements multishared

MoFEMErrorCode resolveSharedFiniteElements (const Problem *problem_ptr, const std::string &fe_name, int verb=DEFAULT_VERBOSITY)
 resolve shared entities for finite elements in the problem
 
MoFEMErrorCode resolveSharedFiniteElements (const std::string name, const std::string &fe_name, int verb=DEFAULT_VERBOSITY)
 resolve shared entities for finite elements in the problem
 

Make entities multishared

MoFEMErrorCode makeEntitiesMultishared (const EntityHandle *entities, const int num_entities, const int owner_proc=0, int verb=DEFAULT_VERBOSITY)
 make entities from proc 0 shared on all proc
 
MoFEMErrorCode makeEntitiesMultishared (Range &entities, const int owner_proc=0, int verb=DEFAULT_VERBOSITY)
 make entities from proc 0 shared on all proc
 
MoFEMErrorCode makeFieldEntitiesMultishared (const std::string field_name, const int owner_proc=0, int verb=DEFAULT_VERBOSITY)
 make field entities multi shared
 
MoFEMErrorCode exchangeFieldData (const std::string field_name, int verb=DEFAULT_VERBOSITY)
 Exchange field data.
 

Synchronize entities (Following functions in future will be

deprecated)

MoFEMErrorCode synchroniseEntities (Range &ent, std::map< int, Range > *received_ents, int verb=DEFAULT_VERBOSITY)
 synchronize entity range on processors (collective)
 
MoFEMErrorCode synchroniseEntities (Range &ent, int verb=DEFAULT_VERBOSITY)
 synchronize entity range on processors (collective)
 
MoFEMErrorCode synchroniseFieldEntities (const std::string name, int verb=DEFAULT_VERBOSITY)
 
MoFEMErrorCode resolveParentEntities (const Range &ent, int verb=DEFAULT_VERBOSITY)
 Synchronise parent entities.
 

Read, load and broadcast

@

MoFEMErrorCode partitionMesh (const Range &ents, const int dim, const int adj_dim, const int n_parts, Tag *th_vertex_weights=nullptr, Tag *th_edge_weights=nullptr, Tag *th_part_weights=nullptr, int verb=VERBOSE, const bool debug=false)
 Set partition tag to each finite element in the problem.
 

Additional Inherited Members

- Static Public Member Functions inherited from MoFEM::UnknownInterface
static MoFEMErrorCode getLibVersion (Version &version)
 Get library version.
 
static MoFEMErrorCode getFileVersion (moab::Interface &moab, Version &version)
 Get database major version.
 
static MoFEMErrorCode setFileVersion (moab::Interface &moab, Version version=Version(MoFEM_VERSION_MAJOR, MoFEM_VERSION_MINOR, MoFEM_VERSION_BUILD))
 Get database major version.
 
static MoFEMErrorCode getInterfaceVersion (Version &version)
 Get database major version.
 

Detailed Description

Managing BitRefLevels.

Examples
/home/lk58p/mofem_install/vanilla_dev_release/mofem-cephas/mofem/users_modules/eshelbian_plasticity/src/impl/EshelbianPlasticity.cpp, mofem/atom_tests/build_composite_problem.cpp, mofem/atom_tests/dm_partitioned_no_field.cpp, mofem/atom_tests/partition_mesh.cpp, mofem/atom_tests/simple_l2_only.cpp, mofem/tools/mesh_smoothing.cpp, mofem/tutorials/adv-0_plasticity/plastic.cpp, mofem/tutorials/adv-3_level_set/level_set.cpp, mofem/tutorials/adv-5_poroelasticity/seepage.cpp, mofem/tutorials/cor-10_navier_stokes/navier_stokes.cpp, mofem/tutorials/mix-0_mixed_poisson/mixed_poisson.cpp, mofem/tutorials/vec-5_free_surface/free_surface.cpp, mofem/tutorials/vec-7_shape_optimisation/adjoint.cpp, mofem/users_modules/adolc-plasticity/adolc_plasticity.cpp, mofem/users_modules/basic_finite_elements/elasticity/elasticity.cpp, plastic.cpp, thermo_elastic.cpp, and thermoplastic.cpp.

Definition at line 66 of file CommInterface.hpp.

Member Typedef Documentation

◆ EntitiesPetscVector

using MoFEM::CommInterface::EntitiesPetscVector = std::pair<std::pair<Range, Range>, SmartPetscObj<Vec> >

Definition at line 337 of file CommInterface.hpp.

◆ LoadFileFun

using MoFEM::CommInterface::LoadFileFun = std::function<std::array<Range, 4>( std::array<Range, 4> &&, std::vector<const CubitMeshSets *> &&)>

Definition at line 306 of file CommInterface.hpp.

◆ UpdateGhosts

using MoFEM::CommInterface::UpdateGhosts = std::function<MoFEMErrorCode(Vec vec)>

Definition at line 399 of file CommInterface.hpp.

Constructor & Destructor Documentation

◆ CommInterface()

MoFEM::CommInterface::CommInterface ( const MoFEM::Core core)

Definition at line 16 of file CommInterface.cpp.

17 : cOre(const_cast<MoFEM::Core &>(core)), dEbug(false) {}
Core (interface) class.
Definition Core.hpp:83

◆ ~CommInterface()

MoFEM::CommInterface::~CommInterface ( )
default

Destructor.

Member Function Documentation

◆ createEntitiesPetscVector() [1/2]

CommInterface::EntitiesPetscVector MoFEM::CommInterface::createEntitiesPetscVector ( MPI_Comm  comm,
moab::Interface &  moab,
int  dim,
const int  nb_coeffs,
Sev  sev = Sev::verbose,
int  root_rank = 0 
)
static

Create a ghost vector for exchanging data.

Note
Only works if loadFileRootProcAllRestDistributed function is used.
Parameters
comm
moab
dimdimension of partition entities
adj_dimdimension of adjacent entities
nb_coeffsnumber of coefficients
sev
root_rank

Example:

mField.get_comm(), mField.get_moab(), 2, 3, Sev::inform);
static EntitiesPetscVector createEntitiesPetscVector(MPI_Comm comm, moab::Interface &moab, std::function< Range(Range)> get_entities_fun, const int nb_coeffs, Sev sev=Sev::verbose, int root_rank=0, bool get_vertices=true)
Create a ghost vector for exchanging data.
Returns
std::pair<Range, SmartPetscObj<Vec>>

Definition at line 1753 of file CommInterface.cpp.

1755 {
1757 comm, moab,
1758
1759 [dim](Range r) { return r.subset_by_dimension(dim); }
1760
1761 ,
1762 nb_coeffs, sev, root_rank, (dim != 0) ? false : true);
1763}
int r
Definition sdf.py:205

◆ createEntitiesPetscVector() [2/2]

CommInterface::EntitiesPetscVector MoFEM::CommInterface::createEntitiesPetscVector ( MPI_Comm  comm,
moab::Interface &  moab,
std::function< Range(Range)>  get_entities_fun,
const int  nb_coeffs,
Sev  sev = Sev::verbose,
int  root_rank = 0,
bool  get_vertices = true 
)
static

Create a ghost vector for exchanging data.

Note
Only works if loadFileRootProcAllRestDistributed function is used.
Parameters
comm
moab
get_entities_funfunction to get entities to partition
dimdimension of partition entities
adj_dimdimension of adjacent entities
nb_coeffsnumber of coefficients
sev
root_rank
get_verticeswhether to get vertices along with entities

Example:

mField.get_comm(), mField.get_moab(),
[](Range part_ents) { return part_ents.subset_by_dimension(2); },
3, Sev::inform);
mField.get_moab(), face_exchange, tag_value_to_exchange);
#define CHKERR
Inline error check.
static MoFEMErrorCode updateEntitiesPetscVector(moab::Interface &moab, EntitiesPetscVector &vec, Tag tag, UpdateGhosts update_gosts=defaultUpdateGhosts)
Exchange data between vector and data.
Returns
std::pair<Range, SmartPetscObj<Vec>>

Definition at line 1489 of file CommInterface.cpp.

1492 {
1493
1494 SmartPetscObj<Vec> vec;
1495 Range r, ghost_ents;
1496
1497 auto get_gids = [&](Range &ents) {
1498 std::vector<int> ids(ents.size());
1499 auto gid_tag = moab.globalId_tag();
1500 CHKERR moab.tag_get_data(gid_tag, ents, ids.data());
1501 return ids;
1502 };
1503
1504 auto create_ao = [&](auto &&ids) {
1505 AO ao_raw;
1507 AOCreateMapping(comm, ids.size(), ids.data(), PETSC_NULLPTR, &ao_raw),
1508 "create ao failed");
1509 return SmartPetscObj<AO>(ao_raw, false);
1510 };
1511
1512 auto apply_ao = [&](auto ao, std::vector<int> &&ids) {
1513 CHK_THROW_MESSAGE(AOApplicationToPetsc(ao, ids.size(), ids.data()),
1514 "AOApplicationToPetsc failed");
1515 return ids;
1516 };
1517
1518 auto get_tag_ids = [&](auto ao, Range &ents) {
1519 return apply_ao(ao, get_gids(ents));
1520 };
1521
1522 auto fun = [&]() {
1524 auto pcomm = ParallelComm::get_pcomm(&moab, MYPCOMM_INDEX);
1525 Tag part_tag = pcomm->part_tag();
1526 Range tagged_sets;
1527 CHKERR moab.get_entities_by_type_and_tag(0, MBENTITYSET, &part_tag, NULL, 1,
1528 tagged_sets,
1529 moab::Interface::UNION);
1530 auto get_proc_and_off_proc_ents = [&]() {
1531 Range proc_ents, off_proc_ents;
1532 if (tagged_sets.empty() && pcomm->size() == 1) {
1533 CHK_MOAB_THROW(moab.get_entities_by_handle(0, proc_ents, false),
1534 "get_entities_by_handle failed");
1535 proc_ents = subtract(proc_ents, proc_ents.subset_by_type(MBENTITYSET));
1536 proc_ents = subtract(proc_ents, proc_ents.subset_by_type(MBVERTEX));
1537 return std::make_pair(proc_ents, Range());
1538 }
1539 for (auto &mit : tagged_sets) {
1540 int part;
1541 CHK_MOAB_THROW(moab.tag_get_data(part_tag, &mit, 1, &part),
1542 "tag_get_data failed");
1543 if (part == pcomm->rank()) {
1544 CHK_MOAB_THROW(moab.get_entities_by_handle(mit, proc_ents, false),
1545 "get_entities_by_handle failed");
1546 } else {
1547 CHK_MOAB_THROW(moab.get_entities_by_handle(mit, off_proc_ents, false),
1548 "get_entities_by_handle failed");
1549 }
1550 proc_ents = subtract(proc_ents, off_proc_ents);
1551 }
1552 return std::make_pair(proc_ents, off_proc_ents);
1553 };
1554
1555 auto get_proc_and_off_proc_verts = [&]() {
1556 Range proc_ents, off_proc_ents;
1557 if (tagged_sets.empty()) {
1558 CHK_MOAB_THROW(moab.get_entities_by_type(0, MBVERTEX, proc_ents),
1559 "get_entities_by_type failed");
1560 return std::make_pair(proc_ents, Range());
1561 }
1562 std::map<int, Range> parts_ents;
1563 for (auto &mit : tagged_sets) {
1564 int part;
1565 CHK_MOAB_THROW(moab.tag_get_data(part_tag, &mit, 1, &part),
1566 "tag_get_data failed");
1568 moab.get_entities_by_handle(mit, parts_ents[part], false),
1569 "get_entities_by_handle failed");
1570 parts_ents[part] = subtract(
1571 parts_ents[part], parts_ents[part].subset_by_type(MBENTITYSET));
1572 }
1573 Range v;
1574 CHK_MOAB_THROW(moab.get_connectivity(parts_ents[pcomm->rank()], v),
1575 "get_connectivity failed");
1576 int p = 0;
1577 for (; p != pcomm->rank(); ++p) {
1578 Range vv;
1579 CHK_MOAB_THROW(moab.get_connectivity(parts_ents[p], vv),
1580 "get_connectivity failed");
1581 v = subtract(v, vv);
1582 off_proc_ents.merge(vv);
1583 }
1584 for (; p != pcomm->size(); ++p) {
1585 Range vv;
1586 CHK_MOAB_THROW(moab.get_connectivity(parts_ents[p], vv),
1587 "get_connectivity failed");
1588 vv = subtract(vv, v);
1589 off_proc_ents.merge(vv);
1590 }
1591 proc_ents = v;
1592 return std::make_pair(proc_ents, off_proc_ents);
1593 };
1594
1595 auto [proc_ents, off_proc_ents] = get_proc_and_off_proc_ents();
1596
1597 if (get_vertices) {
1598 auto [proc_verts, off_proc_verts] = get_proc_and_off_proc_verts();
1599 proc_ents.merge(proc_verts);
1600 off_proc_ents.merge(off_proc_verts);
1601 }
1602 r = get_entities_fun(proc_ents);
1603 auto o = get_entities_fun(off_proc_ents);
1604 auto ao = create_ao(get_gids(r));
1605
1606 auto set_ghosts = [&](auto &&ghosts_gids) {
1607 std::vector<int> ghosts_dofs(nb_coeffs * ghosts_gids.size());
1608 for (int i = 0; i < ghosts_gids.size(); ++i)
1609 for (int j = 0; j < nb_coeffs; ++j)
1610 ghosts_dofs[i * nb_coeffs + j] = nb_coeffs * ghosts_gids[i] + j;
1611 return ghosts_dofs;
1612 };
1613
1614 std::vector<int> ghosts;
1615 if (pcomm->rank() == root_rank) {
1616 ghosts = set_ghosts(get_tag_ids(ao, o));
1617 ghost_ents = o;
1618 } else {
1619 Range ents;
1620 CHKERR moab.get_entities_by_handle(0, ents, true);
1621 ents = get_entities_fun(ents);
1622 ents = subtract(ents, r);
1623 ghosts = set_ghosts(get_tag_ids(ao, ents));
1624 ghost_ents = ents;
1625 }
1626
1627 auto create_vec = [&]() {
1629 vec = createGhostVector(comm, nb_coeffs * r.size(), PETSC_DETERMINE,
1630 ghosts.size(), ghosts.data());
1632 };
1633 CHKERR create_vec();
1634
1636 };
1637
1638 CHKERR fun();
1639
1640 auto out = std::make_pair(std::make_pair(r, ghost_ents), vec);
1641
1642#ifndef NDEBUG
1643 {
1644
1645 auto check = [&](auto &ents, auto &id, auto &idx) {
1647 bool error = false;
1648 for (int i = 0; i < ents.size(); ++i) {
1649 for (int j = 0; j < nb_coeffs; ++j) {
1650 if (idx[i * nb_coeffs + j] != nb_coeffs * id[i] + j) {
1651 error = true;
1652 MOFEM_LOG("SYNC", Sev::error)
1653 << "indexes not equal: " << idx[i * nb_coeffs + j]
1654 << " != " << nb_coeffs * idx[i] + j;
1655 }
1656 }
1657 }
1658 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, Sev::error);
1659 if (error)
1660 CHK_THROW_MESSAGE(MOFEM_DATA_INCONSISTENCY, "indexes do not match");
1662 };
1663
1664 std::vector<double> def_val(nb_coeffs, 0.0);
1665 Tag tag;
1666 CHKERR moab.tag_get_handle("TestGather", nb_coeffs, MB_TYPE_DOUBLE, tag,
1667 MB_TAG_SPARSE | MB_TAG_CREAT, def_val.data());
1668 auto ao = create_ao(get_gids(r));
1669 auto id = get_tag_ids(ao, r);
1670 std::vector<double> idx(nb_coeffs * r.size());
1671 for (int i = 0; i < r.size(); ++i) {
1672 for (int j = 0; j < nb_coeffs; ++j) {
1673 idx[i * nb_coeffs + j] = nb_coeffs * id[i] + j;
1674 }
1675 }
1676 CHKERR moab.tag_set_data(tag, r, idx.data());
1677 CHKERR updateEntitiesPetscVector(moab, out, tag);
1678 idx.resize(nb_coeffs * r.size());
1679 CHKERR moab.tag_get_data(tag, r, idx.data());
1680 CHK_THROW_MESSAGE(check(r, id, idx), "indexes do not match")
1681 auto ghost_id = get_tag_ids(ao, ghost_ents);
1682 idx.resize(nb_coeffs * ghost_ents.size());
1683 CHKERR moab.tag_get_data(tag, ghost_ents, idx.data());
1684 CHK_THROW_MESSAGE(check(ghost_ents, ghost_id, idx),
1685 "ghost indexes do not match")
1686 CHKERR moab.tag_delete(tag);
1687 }
1688#endif // NDEBUG
1689
1690 return out;
1691}
#define MOFEM_LOG_SEVERITY_SYNC(comm, severity)
Synchronise "SYNC" on curtain severity level.
#define CHK_THROW_MESSAGE(err, msg)
Check and throw MoFEM exception.
#define MYPCOMM_INDEX
default communicator number PCOMM
#define MoFEMFunctionBegin
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
#define CHK_MOAB_THROW(err, msg)
Check error code of MoAB function and throw MoFEM exception.
@ MOFEM_DATA_INCONSISTENCY
Definition definitions.h:31
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
auto fun
#define MOFEM_LOG(channel, severity)
Log.
FTensor::Index< 'i', SPACE_DIM > i
const double v
phase velocity of light in medium (cm/ns)
FTensor::Index< 'j', 3 > j
auto createGhostVector(MPI_Comm comm, PetscInt n, PetscInt N, PetscInt nghost, const PetscInt ghosts[])
Create smart ghost vector.

◆ defaultProcSkinFun()

static std::array< Range, 4 > MoFEM::CommInterface::defaultProcSkinFun ( std::array< Range, 4 > &&  proc_ents_skin,
std::vector< const CubitMeshSets * > &&  vec_ptr 
)
inlinestatic

Definition at line 310 of file CommInterface.hpp.

311 {
312 return proc_ents_skin;
313 }

◆ defaultUpdateGhosts()

static MoFEMErrorCode MoFEM::CommInterface::defaultUpdateGhosts ( Vec  v)
inlinestatic

Definition at line 401 of file CommInterface.hpp.

401 {
403 CHKERR VecAssemblyBegin(v);
404 CHKERR VecAssemblyEnd(v);
405 CHKERR VecGhostUpdateBegin(v, ADD_VALUES, SCATTER_REVERSE);
406 CHKERR VecGhostUpdateEnd(v, ADD_VALUES, SCATTER_REVERSE);
407 CHKERR VecGhostUpdateBegin(v, INSERT_VALUES, SCATTER_FORWARD);
408 CHKERR VecGhostUpdateEnd(v, INSERT_VALUES, SCATTER_FORWARD);
410 };

◆ exchangeFieldData()

MoFEMErrorCode MoFEM::CommInterface::exchangeFieldData ( const std::string  field_name,
int  verb = DEFAULT_VERBOSITY 
)

Exchange field data.

Exchange field for all shared and ghosted entities. This function should be called collectively over the communicator for this ParallelComm. If the entities vector is empty, all shared entities participate in the exchange. If a proc has no owned entities this function must still be called since it is collective.

Note
collective - need to be run on all processors in communicator
Todo:
It is not working if field has entities different than vertices.
Parameters
verb
field_name
Returns
MoFEMErrorCode

Definition at line 817 of file CommInterface.cpp.

818 {
819 MoFEM::Interface &m_field = cOre;
821 if (m_field.get_comm_size() > 1) {
822
823 Range exchange_ents_data_verts, exchange_ents_data;
824
825 auto *field_ents = m_field.get_field_ents();
826 auto field_bit_number = m_field.get_field_bit_number(field_name);
827 auto lo = field_ents->get<Unique_mi_tag>().lower_bound(
828 FieldEntity::getLoBitNumberUId(field_bit_number));
829 auto hi = field_ents->get<Unique_mi_tag>().lower_bound(
830 FieldEntity::getHiBitNumberUId(field_bit_number));
831
832 for (auto it = lo; it != hi; ++it)
833 if (
834
835 ((*it)->getPStatus()) &&
836
837 (*it)->getNbDofsOnEnt()
838
839 ) {
840 if ((*it)->getEntType() == MBVERTEX)
841 exchange_ents_data_verts.insert((*it)->getEnt());
842 else
843 exchange_ents_data.insert((*it)->getEnt());
844 }
845
846 auto field_ptr = m_field.get_field_structure(field_name);
847 ParallelComm *pcomm = ParallelComm::get_pcomm(
848 &m_field.get_moab(), m_field.get_basic_entity_data_ptr()->pcommID);
849
850 auto exchange = [&](const Range &ents, Tag th) {
852 if (!ents.empty()) {
853 std::vector<Tag> tags;
854 tags.push_back(th);
855 CHKERR pcomm->exchange_tags(tags, tags, ents);
856 }
858 };
859
860 CHKERR exchange(exchange_ents_data_verts, field_ptr->th_FieldDataVerts);
861 CHKERR exchange(exchange_ents_data, field_ptr->th_FieldData);
862 }
864}
virtual const FieldEntity_multiIndex * get_field_ents() const =0
Get the field ents object.
virtual const Field * get_field_structure(const std::string &name, enum MoFEMTypes bh=MF_EXIST) const =0
get field structure
constexpr auto field_name
virtual int get_comm_size() const =0
virtual FieldBitNumber get_field_bit_number(const std::string name) const =0
get field bit number
virtual moab::Interface & get_moab()=0
virtual boost::shared_ptr< BasicEntityData > & get_basic_entity_data_ptr()=0
Get pointer to basic entity data.
Deprecated interface functions.
static UId getHiBitNumberUId(const FieldBitNumber bit_number)
static UId getLoBitNumberUId(const FieldBitNumber bit_number)

◆ getPartEntities()

Range MoFEM::CommInterface::getPartEntities ( moab::Interface &  moab,
int  part 
)
static

Definition at line 1418 of file CommInterface.cpp.

1418 {
1419
1420 ParallelComm *pcomm = ParallelComm::get_pcomm(&moab, MYPCOMM_INDEX);
1421 if (pcomm == NULL)
1422 pcomm = new ParallelComm(&moab, PETSC_COMM_WORLD);
1423 if (pcomm->size() == 1) {
1424 Range ents;
1425 CHK_MOAB_THROW(moab.get_entities_by_handle(0, ents, false),
1426 "get_entities_by_handle failed");
1427 return subtract(ents, ents.subset_by_type(MBENTITYSET));
1428 }
1429
1430 Range proc_ents;
1431
1432 auto get_proc_ents = [&]() {
1434
1435 auto get_all_mesh_entities = [&]() {
1437 CHKERR moab.get_entities_by_handle(0, proc_ents, false);
1438 proc_ents = subtract(proc_ents, proc_ents.subset_by_type(MBENTITYSET));
1440 };
1441
1442 Tag part_tag = pcomm->part_tag();
1443 Range tagged_sets;
1444 auto rval =
1445 moab.get_entities_by_type_and_tag(0, MBENTITYSET, &part_tag, NULL, 1,
1446 tagged_sets, moab::Interface::UNION);
1447 if (rval == MB_TAG_NOT_FOUND || rval == MB_ENTITY_NOT_FOUND ||
1448 tagged_sets.empty()) {
1449 MOFEM_LOG("SELF", Sev::warning)
1450 << "Partition tag or partition sets not found, returning all mesh "
1451 "entities";
1452 CHKERR get_all_mesh_entities();
1454 }
1455 CHKERR rval;
1456
1457 for (auto &mit : tagged_sets) {
1458 int part_set;
1459 CHKERR moab.tag_get_data(part_tag, &mit, 1, &part_set);
1460 if (part_set == part) {
1461 rval = moab.get_entities_by_handle(mit, proc_ents, true);
1462 if (rval == MB_SUCCESS) {
1464 }
1465 if (rval == MB_ENTITY_NOT_FOUND) {
1466 MOFEM_LOG("SELF", Sev::warning)
1467 << "Partition set is stale, returning all mesh entities";
1468 proc_ents.clear();
1469 CHKERR get_all_mesh_entities();
1471 }
1472 CHKERR rval;
1473 }
1474 }
1475
1476 MOFEM_LOG("SELF", Sev::warning)
1477 << "Partition set for requested part not found, returning all mesh "
1478 "entities";
1479 CHKERR get_all_mesh_entities();
1482 };
1483
1484 CHK_THROW_MESSAGE(get_proc_ents(), "get_proc_ents failed");
1485
1486 return proc_ents;
1487}
#define MoFEMFunctionReturnHot(a)
Last executable line of each PETSc function used for error handling. Replaces return()
static MoFEMErrorCodeGeneric< moab::ErrorCode > rval

◆ loadFileRootProcAllRestDistributed()

MoFEMErrorCode MoFEM::CommInterface::loadFileRootProcAllRestDistributed ( moab::Interface &  moab,
const char *  file_name,
int  dim,
LoadFileFun  proc_skin_fun = defaultProcSkinFun,
const char *  options = "PARALLEL=BCAST;PARTITION=" 
)
static

Root proc has whole mesh, other procs only part of it.

Parameters
moab
file_name
dim
proc_skin_fun
options
Returns
MoFEMErrorCode

< cubit meshsets

Definition at line 1205 of file CommInterface.cpp.

1207 {
1209
1210 MOFEM_LOG_CHANNEL("WORLD");
1211 MOFEM_LOG_CHANNEL("SYNC");
1212
1213 MOFEM_LOG("SYNC", sev) << "Load file " << file_name;
1214 CHKERR moab.load_file(file_name, 0, options);
1216 MOFEM_LOG("SYNC", sev) << "Load file <- done";
1217 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, sev);
1218
1219 ParallelComm *pcomm = ParallelComm::get_pcomm(&moab, MYPCOMM_INDEX);
1220 if (pcomm == NULL)
1221 pcomm = new ParallelComm(&moab, PETSC_COMM_WORLD);
1222 if (pcomm->size() == 1)
1224
1225 Skinner skin(&moab);
1226
1227 auto print_range_on_procs = [&](const Range &range, std::string name) {
1228 MOFEM_LOG("SYNC", sev) << name << " on proc [" << pcomm->rank()
1229 << "] : " << range.size();
1230 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, sev);
1231 };
1232
1233 auto save_range_to_file = [&](const Range range, std::string name = "part") {
1234 if (!debug)
1235 return;
1236 int rr = pcomm->rank();
1237 ostringstream ss;
1238 ss << "out_" << name << "_" << rr << ".vtk";
1239 MOFEM_LOG("SYNC", sev) << "Save debug part mesh " << ss.str();
1240 EntityHandle meshset;
1241 CHKERR moab.create_meshset(MESHSET_SET, meshset);
1242 CHKERR moab.add_entities(meshset, range);
1243 if (!range.empty())
1244 CHKERR moab.write_file(ss.str().c_str(), "VTK", "", &meshset, 1);
1245 MOFEM_LOG("SYNC", sev) << "Empty range";
1246 CHKERR moab.delete_entities(&meshset, 1);
1247 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, sev);
1248 };
1249
1250 auto get_skin = [&](auto e) {
1251 Range s;
1252 CHKERR skin.find_skin(0, e.subset_by_dimension(dim), false, s);
1253 return s;
1254 };
1255
1256 auto get_adj = [&](auto ents, auto dim) {
1257 Range adj;
1258 CHKERR moab.get_adjacencies(ents, dim, false, adj, moab::Interface::UNION);
1259 return adj;
1260 };
1261
1262 Range all_ents;
1263 CHKERR moab.get_entities_by_handle(0, all_ents, false);
1264 save_range_to_file(all_ents, "all_ents");
1265
1266 Tag part_tag = pcomm->part_tag();
1267 Range tagged_sets, proc_ents, off_proc_ents;
1268
1269 CHKERR moab.get_entities_by_type_and_tag(0, MBENTITYSET, &part_tag, NULL, 1,
1270 tagged_sets, moab::Interface::UNION);
1271 print_range_on_procs(tagged_sets, "tagged_sets");
1272 for (auto &mit : tagged_sets) {
1273 int part;
1274 CHKERR moab.tag_get_data(part_tag, &mit, 1, &part);
1275 if (part == pcomm->rank()) {
1276 CHKERR moab.get_entities_by_handle(mit, proc_ents, true);
1277 } else {
1278 CHKERR moab.get_entities_by_handle(mit, off_proc_ents, true);
1279 }
1280 }
1281
1282 // set part tags to entities, they might be not set
1283 for (auto &mit : tagged_sets) {
1284 int part;
1285 CHKERR moab.tag_get_data(part_tag, &mit, 1, &part);
1286 Range ents;
1287 CHKERR moab.get_entities_by_handle(mit, ents, true);
1288 CHKERR moab.tag_clear_data(part_tag, ents, &part);
1289 }
1290
1291 print_range_on_procs(proc_ents, "proc_ents");
1292 save_range_to_file(proc_ents, "proc_ents");
1293
1294 auto get_proc_ents_skin = [&]() {
1295 std::array<Range, 4>
1296 proc_ents_skin; // stores only entities shared with other processors
1297 auto all_skin = get_skin(all_ents.subset_by_dimension(dim));
1298 auto proc_skin = get_skin(proc_ents.subset_by_dimension(dim));
1299 if (dim == 3) {
1300 proc_ents_skin[2] = subtract(proc_skin, all_skin); // faces
1301 proc_ents_skin[1] = get_adj(proc_ents_skin[dim - 1], 1); // edges
1302 }
1303 if (dim == 2) {
1304 proc_ents_skin[1] = subtract(proc_skin, all_skin); // edges
1305 }
1306 CHKERR moab.get_connectivity(proc_ents_skin[dim - 1], proc_ents_skin[0],
1307 false); // vertices
1308 return proc_ents_skin;
1309 };
1310
1311 auto add_post_proc_skin = [&](auto &&proc_ents_skin) {
1312 CubitMeshSet_multiIndex cubit_meshsets_index; ///< cubit meshsets
1313
1314 Tag nsTag, ssTag, nsTag_data, ssTag_data, bhTag, bhTag_header;
1315 CHKERR MeshsetsManager::getTags(moab, nsTag, ssTag, nsTag_data, ssTag_data,
1316 bhTag, bhTag_header, QUIET);
1317
1318 Range meshsets;
1319 CHKERR moab.get_entities_by_type(0, MBENTITYSET, meshsets, false);
1320 for (auto m : meshsets) {
1321 // check if meshset is cubit meshset
1322 CubitMeshSets block(moab, m);
1323 if ((block.cubitBcType & CubitBCType(NODESET | SIDESET | BLOCKSET))
1324 .any()) {
1325 auto p = cubit_meshsets_index.insert(block);
1326 if (!p.second) {
1327 // blockset/nodeset/sideset set exist, could be created on other
1328 // processor.
1329 Range ents;
1330 CHKERR moab.get_entities_by_handle(m, ents, true);
1331 CHKERR moab.add_entities(p.first->getMeshset(), ents);
1332 CHKERR moab.delete_entities(&m, 1);
1333 }
1334 }
1335 }
1336
1337 for (auto &m : cubit_meshsets_index) {
1338 MOFEM_LOG("WORLD", sev) << "LoadFile read " << m;
1339 }
1340 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, sev);
1341
1342 std::vector<const CubitMeshSets *> vec_ptr;
1343 for (auto &m : cubit_meshsets_index) {
1344 vec_ptr.push_back(&m);
1345 }
1347
1348 return proc_skin_fun(std::move(proc_ents_skin), std::move(vec_ptr));
1349 };
1350
1351 auto remove_off_proc_ents = [&](auto &all_ents, auto &off_proc_ents,
1352 auto &proc_ents_skin) {
1353 auto to_remove = off_proc_ents;
1354 for (auto d = dim - 1; d >= 0; --d) {
1355 to_remove = subtract(to_remove, proc_ents_skin[d]);
1356 }
1357
1358 Range meshsets;
1359 CHKERR moab.get_entities_by_type(0, MBENTITYSET, meshsets, true);
1360 for (auto m : meshsets) {
1361 CHKERR moab.remove_entities(m, to_remove);
1362 }
1363 for (int dd = dim; dd > 0; --dd) {
1364 CHKERR moab.delete_entities(to_remove.subset_by_dimension(dd));
1365 }
1366 };
1367
1368 auto proc_ents_skin = add_post_proc_skin(get_proc_ents_skin());
1369 for (auto d = dim - 1; d >= 0; --d) {
1370 save_range_to_file(proc_ents_skin[d], "proc_ents_skin" + std::to_string(d));
1371 }
1372
1373 if (pcomm->rank()) {
1374 remove_off_proc_ents(all_ents, off_proc_ents, proc_ents_skin);
1375 }
1376
1377 for (auto d = dim - 1; d >= 0; --d) {
1378 print_range_on_procs(proc_ents_skin[d],
1379 "proc_ents_skin by dim" + std::to_string(d));
1380 }
1381
1382 CHKERR pcomm->resolve_shared_ents(0, proc_ents, dim, -1,
1383 proc_ents_skin.data());
1384
1385 if (debug) {
1386
1387 // Create a tag
1388 auto gid_tag = moab.globalId_tag();
1389
1390 int def_val = -1;
1391 Tag tag_handle;
1392 CHKERR moab.tag_get_handle("TestGather", 1, MB_TYPE_INTEGER, tag_handle,
1393 MB_TAG_DENSE | MB_TAG_CREAT, &def_val);
1394 Range gather_ents;
1395 if (pcomm->rank() > 0) {
1396 gather_ents = proc_ents.subset_by_dimension(3);
1397 std::vector<int> vals(gather_ents.size());
1398 std::for_each(vals.begin(), vals.end(), [](auto &v) { v = std::rand(); });
1399 CHKERR moab.tag_set_data(tag_handle, gather_ents, vals.data());
1400 CHKERR pcomm->gather_data(gather_ents, tag_handle, gid_tag, 0, 0);
1401 } else {
1402 gather_ents = proc_ents.subset_by_dimension(3);
1403 CHKERR pcomm->gather_data(gather_ents, tag_handle, gid_tag, 0, 0);
1404 }
1405 }
1406
1407 Range all_ents_after;
1408 CHKERR moab.get_entities_by_handle(0, all_ents_after);
1409 save_range_to_file(all_ents_after.subset_by_dimension(3),
1410 "all_ents_part_after");
1411
1412 MOFEM_LOG("SYNC", sev) << "Resolved entities <- done";
1413 MOFEM_LOG_SEVERITY_SYNC(PETSC_COMM_WORLD, sev);
1414
1416}
@ QUIET
@ NODESET
@ SIDESET
@ BLOCKSET
#define MOFEM_LOG_CHANNEL(channel)
Set and reset channel.
MoFEMErrorCode getTags(int verb=-1)
Get tag handles used on meshsets.
const Tensor2_symmetric_Expr< const ddTensor0< T, Dim, i, j >, typename promote< T, double >::V, Dim, i, j > dd(const Tensor0< T * > &a, const Index< i, Dim > index1, const Index< j, Dim > index2, const Tensor1< int, Dim > &d_ijk, const Tensor1< double, Dim > &d_xyz)
Definition ddTensor0.hpp:33
std::bitset< 32 > CubitBCType
Definition Types.hpp:52
multi_index_container< CubitMeshSets, indexed_by< hashed_unique< tag< Meshset_mi_tag >, member< CubitMeshSets, EntityHandle, &CubitMeshSets::meshset > >, ordered_non_unique< tag< CubitMeshsetType_mi_tag >, const_mem_fun< CubitMeshSets, unsigned long int, &CubitMeshSets::getBcTypeULong > >, ordered_non_unique< tag< CubitMeshsetMaskedType_mi_tag >, const_mem_fun< CubitMeshSets, unsigned long int, &CubitMeshSets::getMaskedBcTypeULong > >, ordered_non_unique< tag< CubitMeshsets_name >, const_mem_fun< CubitMeshSets, std::string, &CubitMeshSets::getName > >, hashed_unique< tag< Composite_Cubit_msId_And_MeshsetType_mi_tag >, composite_key< CubitMeshSets, const_mem_fun< CubitMeshSets, int, &CubitMeshSets::getMeshsetId >, const_mem_fun< CubitMeshSets, unsigned long int, &CubitMeshSets::getMaskedBcTypeULong > > > > > CubitMeshSet_multiIndex
Stores data about meshsets (see CubitMeshSets) storing data about boundary conditions,...
FTensor::Index< 'm', 3 > m
static void sortMeshsets(std::vector< const CubitMeshSets * > &vec_ptr)

◆ makeEntitiesMultishared() [1/2]

MoFEMErrorCode MoFEM::CommInterface::makeEntitiesMultishared ( const EntityHandle entities,
const int  num_entities,
const int  owner_proc = 0,
int  verb = DEFAULT_VERBOSITY 
)

make entities from proc 0 shared on all proc

Note
collective - need to be run on all processors in communicator
Parameters
entities
num_entities
my_procdefault proc id to share from
verb
Returns
MoFEMErrorCode

Definition at line 646 of file CommInterface.cpp.

648 {
649 MoFEM::Interface &m_field = cOre;
651
652 if (m_field.get_comm_size() > 1) {
653
654 ParallelComm *pcomm = ParallelComm::get_pcomm(
655 &m_field.get_moab(), m_field.get_basic_entity_data_ptr()->pcommID);
656
657 Range all_ents_range;
658 all_ents_range.insert_list(entities, entities + num_entities);
659
660 auto get_tag = [&]() {
661 const int negone = -1;
662 Tag th;
663 m_field.get_moab().tag_get_handle("TMP_GLOBAL_ID_TAG_NAME", 1,
664 MB_TYPE_INTEGER, th,
665 MB_TAG_CREAT | MB_TAG_SPARSE, &negone);
666 return th;
667 };
668
669 auto delete_tag = [&](auto &&th_gid) {
671 CHKERR m_field.get_moab().tag_delete(th_gid);
673 };
674
675 auto resolve_shared_ents = [&](auto &&th_gid, auto &all_ents_range) {
676 auto set_gid = [&](auto &th_gid) {
677 std::vector<int> gids(num_entities);
678 for (size_t g = 0; g != all_ents_range.size(); ++g)
679 gids[g] = g + 1;
680 CHKERR m_field.get_moab().tag_set_data(th_gid, all_ents_range,
681 &*gids.begin());
682
683 return &th_gid;
684 };
685
686 auto get_skin_ents = [&](auto &all_ents_range) {
687 std::array<Range, 4> proc_ents_skin;
688 proc_ents_skin[3] = all_ents_range.subset_by_dimension(3);
689 proc_ents_skin[2] = all_ents_range.subset_by_dimension(2);
690 proc_ents_skin[1] = all_ents_range.subset_by_dimension(1);
691 proc_ents_skin[0] = all_ents_range.subset_by_dimension(0);
692 return proc_ents_skin;
693 };
694
695 auto resolve_dim = [&](auto &all_ents_range) {
696 for (int resolve_dim = 3; resolve_dim >= 0; --resolve_dim) {
697 if (all_ents_range.num_of_dimension(resolve_dim))
698 return resolve_dim;
699 }
700 return -1;
701 };
702
703 auto get_proc_ent = [&](auto &all_ents_range) {
704 Range proc_ent;
705 if (m_field.get_comm_rank() == owner_proc)
706 proc_ent = all_ents_range;
707 return proc_ent;
708 };
709
710 auto resolve_shared_ents = [&](auto &&proc_ents, auto &&skin_ents) {
711 return pcomm->resolve_shared_ents(
712 0, proc_ents, resolve_dim(all_ents_range),
713 resolve_dim(all_ents_range), skin_ents.data(), set_gid(th_gid));
714 };
715
716 CHKERR resolve_shared_ents(get_proc_ent(all_ents_range),
717 get_skin_ents(all_ents_range));
718
719 return th_gid;
720 };
721
722 CHKERR delete_tag(resolve_shared_ents(get_tag(), all_ents_range));
723
724 if (verb >= NOISY) {
725
726 auto print_owner = [&](const EntityHandle e) {
728 int moab_owner_proc;
729 EntityHandle moab_owner_handle;
730 CHKERR pcomm->get_owner_handle(e, moab_owner_proc, moab_owner_handle);
731
732 unsigned char pstatus = 0;
733
734 CHKERR m_field.get_moab().tag_get_data(pcomm->pstatus_tag(), &e, 1,
735 &pstatus);
736
737 std::vector<int> shprocs(MAX_SHARING_PROCS, 0);
738 std::vector<EntityHandle> shhandles(MAX_SHARING_PROCS, 0);
739
740 CHKERR m_field.get_moab().tag_get_data(pcomm->sharedp_tag(), &e, 1,
741 &shprocs[0]);
742 CHKERR m_field.get_moab().tag_get_data(pcomm->sharedh_tag(), &e, 1,
743 &shhandles[0]);
744 if (pstatus & PSTATUS_MULTISHARED) {
745 CHKERR m_field.get_moab().tag_get_data(pcomm->sharedps_tag(), &e, 1,
746 &shprocs[0]);
747 CHKERR m_field.get_moab().tag_get_data(pcomm->sharedhs_tag(), &e, 1,
748 &shhandles[0]);
749 }
750
751 std::ostringstream ss;
752
753 ss << "Rank " << m_field.get_comm_rank() << " ";
754 if (!(pstatus & PSTATUS_NOT_OWNED))
755 ss << "OWNER ";
756 if (pstatus & PSTATUS_SHARED)
757 ss << "PSTATUS_SHARED ";
758 if (pstatus & PSTATUS_MULTISHARED)
759 ss << "PSTATUS_MULTISHARED ";
760
761 ss << "owner " << moab_owner_proc << " (" << owner_proc << ") ";
762
763 ss << "shprocs: ";
764 for (size_t r = 0; r != m_field.get_comm_size() + 1; ++r)
765 ss << shprocs[r] << " ";
766
767 ss << "shhandles: ";
768 for (size_t r = 0; r != m_field.get_comm_size() + 1; ++r)
769 ss << shhandles[r] << " ";
770
771 ss << std::endl;
772 MOFEM_LOG("SYNC", Sev::noisy) << ss.str();
774
776 };
777
778 for (auto e : all_ents_range)
779 CHKERR print_owner(e);
780 }
781 }
782
784}
#define MOFEM_LOG_SYNCHRONISE(comm)
Synchronise "SYNC" channel.
@ NOISY
constexpr double g
virtual MPI_Comm & get_comm() const =0
virtual int get_comm_rank() const =0

◆ makeEntitiesMultishared() [2/2]

MoFEMErrorCode MoFEM::CommInterface::makeEntitiesMultishared ( Range entities,
const int  owner_proc = 0,
int  verb = DEFAULT_VERBOSITY 
)

make entities from proc 0 shared on all proc

Note
collective - need to be run on all processors in communicator
Parameters
entities
my_procdefault proc id to share from
verb
Returns
MoFEMErrorCode

Definition at line 786 of file CommInterface.cpp.

788 {
789 MoFEM::Interface &m_field = cOre;
791 if (m_field.get_comm_size() > 1) {
792 const int num_ents = entities.size();
793 std::vector<EntityHandle> vec_ents(num_ents);
794 std::copy(entities.begin(), entities.end(), vec_ents.begin());
795 CHKERR makeEntitiesMultishared(&*vec_ents.begin(), num_ents, owner_proc,
796 verb);
797 }
799}
MoFEMErrorCode makeEntitiesMultishared(const EntityHandle *entities, const int num_entities, const int owner_proc=0, int verb=DEFAULT_VERBOSITY)
make entities from proc 0 shared on all proc

◆ makeFieldEntitiesMultishared()

MoFEMErrorCode MoFEM::CommInterface::makeFieldEntitiesMultishared ( const std::string  field_name,
const int  owner_proc = 0,
int  verb = DEFAULT_VERBOSITY 
)

make field entities multi shared

Note
collective - need to be run on all processors in communicator
Parameters
field_name
owner_proc
verb
Returns
MoFEMErrorCode

Definition at line 802 of file CommInterface.cpp.

803 {
804 MoFEM::Interface &m_field = cOre;
806 if (m_field.get_comm_size() > 1) {
807 EntityHandle field_meshset = m_field.get_field_meshset(field_name);
808 std::vector<EntityHandle> field_ents;
809 CHKERR m_field.get_moab().get_entities_by_handle(field_meshset, field_ents,
810 true);
811 CHKERR makeEntitiesMultishared(&*field_ents.begin(), field_ents.size(),
812 owner_proc, verb);
813 }
815}
virtual EntityHandle get_field_meshset(const std::string name) const =0
get field meshset

◆ query_interface()

MoFEMErrorCode MoFEM::CommInterface::query_interface ( boost::typeindex::type_index  type_index,
UnknownInterface **  iface 
) const
virtual

Implements MoFEM::UnknownInterface.

Definition at line 9 of file CommInterface.cpp.

10 {
12 *iface = const_cast<CommInterface *>(this);
14}
#define MoFEMFunctionBeginHot
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
CommInterface(const MoFEM::Core &core)

◆ resolveParentEntities()

MoFEMErrorCode MoFEM::CommInterface::resolveParentEntities ( const Range ent,
int  verb = DEFAULT_VERBOSITY 
)

Synchronise parent entities.

Note
collective - need to be run on all processors in communicator

Exchange parent entity tag and bitref of entity. Note thar parent handle can be different on each processor.

Parameters
ent
verb
Returns
MoFEMErrorCode

Definition at line 249 of file CommInterface.cpp.

250 {
251 MoFEM::Interface &m_field = cOre;
252 ParallelComm *pcomm = ParallelComm::get_pcomm(
253 &m_field.get_moab(), m_field.get_basic_entity_data_ptr()->pcommID);
254
256
257 Range shared = ents;
258 CHKERR pcomm->filter_pstatus(shared, PSTATUS_NOT_OWNED, PSTATUS_NOT, -1,
259 nullptr);
260 CHKERR pcomm->filter_pstatus(shared, PSTATUS_SHARED | PSTATUS_MULTISHARED,
261 PSTATUS_OR, -1, nullptr);
262
263 auto th_RefParentHandle = cOre.get_th_RefParentHandle();
264 auto th_RefBitLevel = cOre.get_th_RefBitLevel();
265
266 auto get_pstatus = [&](const auto ent) {
267 unsigned char pstatus;
268 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->pstatus_tag(), &ent,
269 1, &pstatus),
270 "can not get pstatus");
271 return pstatus;
272 };
273
274 auto get_sharing_procs = [&](const auto ent, const auto pstatus) {
275 std::vector<int> sharing_procs(MAX_SHARING_PROCS, -1);
276 if (pstatus & PSTATUS_MULTISHARED) {
277 // entity is multi shared
278 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(
279 pcomm->sharedps_tag(), &ent, 1, &sharing_procs[0]),
280 "can not ger sharing_procs_ptr");
281 } else if (pstatus & PSTATUS_SHARED) {
282 // shared
283 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->sharedp_tag(), &ent,
284 1, &sharing_procs[0]),
285 "can not get sharing proc");
286 }
287 return sharing_procs;
288 };
289
290 auto get_sharing_handles = [&](const auto ent, const auto pstatus) {
291 std::vector<EntityHandle> sharing_handles(MAX_SHARING_PROCS, 0);
292 if (pstatus & PSTATUS_MULTISHARED) {
293 // entity is multi shared
294 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(
295 pcomm->sharedhs_tag(), &ent, 1, &sharing_handles[0]),
296 "get shared handles");
297 } else if (pstatus & PSTATUS_SHARED) {
298 // shared
299 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->sharedh_tag(), &ent,
300 1, &sharing_handles[0]),
301 "get sharing handle");
302 }
303 return sharing_handles;
304 };
305
306 auto get_parent_and_bit = [&](const auto ent) {
307 EntityHandle parent;
309 m_field.get_moab().tag_get_data(th_RefParentHandle, &ent, 1, &parent),
310 "get parent");
313 m_field.get_moab().tag_get_data(th_RefBitLevel, &ent, 1, &bit),
314 "get parent");
315 return std::make_pair(parent, bit);
316 };
317
318 auto set_parent = [&](const auto ent, const auto parent) {
319 return m_field.get_moab().tag_set_data(th_RefParentHandle, &ent, 1,
320 &parent);
321 };
322
323 auto set_bit = [&](const auto ent, const auto bit) {
324 return m_field.get_moab().tag_set_data(th_RefBitLevel, &ent, 1, &bit);
325 };
326
327 // make a buffer
328 std::vector<std::vector<unsigned long long>> sbuffer(m_field.get_comm_size());
329
330 for (auto ent : shared) {
331
332 auto pstatus = get_pstatus(ent);
333 auto sharing_procs = get_sharing_procs(ent, pstatus);
334 auto sharing_handles = get_sharing_handles(ent, pstatus);
335 auto [parent, bit] = get_parent_and_bit(ent);
336
337 if (verb >= NOISY)
338 MOFEM_LOG("SYNC", Sev::noisy) << "pstatus " << std::bitset<8>(pstatus);
339
340 if (parent) {
341 auto pstatus_parent = get_pstatus(parent);
342 auto sharing_procs_parent = get_sharing_procs(parent, pstatus_parent);
343 auto sharing_handles_parent = get_sharing_handles(parent, pstatus_parent);
344
345 for (int proc = 0; proc < MAX_SHARING_PROCS && -1 != sharing_procs[proc];
346 proc++) {
347 if (sharing_procs[proc] == -1)
348 SETERRQ(PETSC_COMM_SELF, MOFEM_IMPOSSIBLE_CASE,
349 "sharing processor not set");
350
351 if (sharing_procs[proc] != m_field.get_comm_rank()) {
352
353 auto it = std::find(sharing_procs_parent.begin(),
354 sharing_procs_parent.end(), sharing_procs[proc]);
355 if (it == sharing_procs_parent.end()) {
356 SETERRQ(PETSC_COMM_SELF, MOFEM_DATA_INCONSISTENCY,
357 "Sharing proc for parent entity can not be found proc = %u",
358 sharing_procs[proc]);
359 }
360
361 auto handle_on_sharing_proc = sharing_handles[proc];
362 auto parent_handle_on_sharing_proc =
363 sharing_handles_parent[std::distance(sharing_procs_parent.begin(),
364 it)];
365 sbuffer[sharing_procs[proc]].push_back(handle_on_sharing_proc);
366 sbuffer[sharing_procs[proc]].push_back(parent_handle_on_sharing_proc);
367 try {
368 sbuffer[sharing_procs[proc]].push_back(bit.to_ullong());
369 } catch (std::exception &ex) {
370 MOFEM_LOG("SELF", Sev::warning) << ex.what();
371 MOFEM_LOG("SELF", Sev::warning)
372 << "On " << ent << " "
373 << moab::CN::EntityTypeName(type_from_handle(ent));
374 MOFEM_LOG("SELF", Sev::warning) << "For bit ref " << bit;
375 }
376 if (verb >= NOISY)
377 MOFEM_LOG_C("SYNC", Sev::noisy, "send %lu (%lu) to %d at %d\n", ent,
378 handle_on_sharing_proc, sharing_procs[proc],
379 m_field.get_comm_rank());
380
381 if (!(pstatus & PSTATUS_MULTISHARED))
382 break;
383 }
384 }
385 } else {
386 for (int proc = 0; proc < MAX_SHARING_PROCS && -1 != sharing_procs[proc];
387 proc++) {
388 if (sharing_procs[proc] == -1)
389 SETERRQ(PETSC_COMM_SELF, MOFEM_IMPOSSIBLE_CASE,
390 "sharing processor not set");
391
392 if (sharing_procs[proc] != m_field.get_comm_rank()) {
393 auto handle_on_sharing_proc = sharing_handles[proc];
394 sbuffer[sharing_procs[proc]].push_back(handle_on_sharing_proc);
395 sbuffer[sharing_procs[proc]].push_back(parent);
396
397 try {
398 sbuffer[sharing_procs[proc]].push_back(bit.to_ullong());
399 } catch (std::exception &ex) {
400 MOFEM_LOG("SELF", Sev::warning) << ex.what();
401 MOFEM_LOG("SELF", Sev::warning)
402 << "On " << ent << " "
403 << moab::CN::EntityTypeName(type_from_handle(ent));
404 MOFEM_LOG("SELF", Sev::warning) << "For bit ref " << bit;
405 }
406
407 if (verb >= NOISY)
408 MOFEM_LOG_C("SYNC", Sev::noisy, "send %lu (%lu) to %d at %d\n", ent,
409 handle_on_sharing_proc, sharing_procs[proc],
410 m_field.get_comm_rank());
411
412 if (!(pstatus & PSTATUS_MULTISHARED))
413 break;
414 }
415 }
416 }
417 }
418
419 int nsends = 0; // number of messages to send
420 std::vector<int> sbuffer_lengths(
421 m_field.get_comm_size()); // length of the message to proc
422
423 const size_t block_size = sizeof(unsigned long long) / sizeof(int);
424 for (int proc = 0; proc < m_field.get_comm_size(); proc++) {
425
426 if (!sbuffer[proc].empty()) {
427
428 sbuffer_lengths[proc] = sbuffer[proc].size() * block_size;
429 nsends++;
430
431 } else {
432
433 sbuffer_lengths[proc] = 0;
434 }
435 }
436
437 // Make sure it is a PETSc m_field.get_comm()
438 MPI_Comm comm;
439 CHKERR PetscCommDuplicate(m_field.get_comm(), &comm, NULL);
440
441 std::vector<MPI_Status> status(m_field.get_comm_size());
442
443 // Computes the number of messages a node expects to receive
444 int nrecvs; // number of messages received
445 CHKERR PetscGatherNumberOfMessages(comm, NULL, &sbuffer_lengths[0], &nrecvs);
446
447 // Computes info about messages that a MPI-node will receive, including
448 // (from-id,length) pairs for each message.
449 int *onodes; // list of node-ids from which messages are expected
450 int *olengths; // corresponding message lengths
451 CHKERR PetscGatherMessageLengths(comm, nsends, nrecvs, &sbuffer_lengths[0],
452 &onodes, &olengths);
453
454 // Gets a unique new tag from a PETSc communicator. All processors that share
455 // the communicator MUST call this routine EXACTLY the same number of times.
456 // This tag should only be used with the current objects communicator; do NOT
457 // use it with any other MPI communicator.
458 int tag;
459 CHKERR PetscCommGetNewTag(comm, &tag);
460
461 // Allocate a buffer sufficient to hold messages of size specified in
462 // olengths. And post Irecvs on these buffers using node info from onodes
463 int **rbuf; // must bee freed by user
464 MPI_Request *r_waits; // must bee freed by user
465 // rbuf has a pointers to messages. It has size of of nrecvs (number of
466 // messages) +1. In the first index a block is allocated,
467 // such that rbuf[i] = rbuf[i-1]+olengths[i-1].
468 CHKERR PetscPostIrecvInt(comm, tag, nrecvs, onodes, olengths, &rbuf,
469 &r_waits);
470
471 MPI_Request *s_waits; // status of sens messages
472 CHKERR PetscMalloc1(nsends, &s_waits);
473
474 // Send messages
475 for (int proc = 0, kk = 0; proc < m_field.get_comm_size(); proc++) {
476 if (!sbuffer_lengths[proc])
477 continue; // no message to send to this proc
478 CHKERR MPI_Isend(&(sbuffer[proc])[0], // buffer to send
479 sbuffer_lengths[proc], // message length
480 MPIU_INT, proc, // to proc
481 tag, comm, s_waits + kk);
482 kk++;
483 }
484
485 // Wait for received
486 if (nrecvs)
487 CHKERR MPI_Waitall(nrecvs, r_waits, &status[0]);
488
489 // Wait for send messages
490 if (nsends)
491 CHKERR MPI_Waitall(nsends, s_waits, &status[0]);
492
493 if (verb >= VERBOSE) {
494 MOFEM_LOG_C("SYNC", Sev::verbose,
495 "Rank %d nb. shared to synchronise parents ents %zu\n",
496 m_field.get_comm_rank(), shared.size());
497 }
498
499 // synchronise range
500 for (int kk = 0; kk < nrecvs; kk++) {
501
502 int len = olengths[kk];
503 int *data_from_proc = rbuf[kk];
504
505 for (int ee = 0; ee < len;) {
506 EntityHandle ent;
507 EntityHandle parent;
508 unsigned long long uulong_bit;
509 bcopy(&data_from_proc[ee], &ent, sizeof(EntityHandle));
510 ee += block_size;
511 bcopy(&data_from_proc[ee], &parent, sizeof(EntityHandle));
512 ee += block_size;
513 bcopy(&data_from_proc[ee], &uulong_bit, sizeof(unsigned long long));
514 ee += block_size;
515
516 CHKERR set_parent(ent, parent);
517 CHKERR set_bit(ent, BitRefLevel(uulong_bit));
518
519 if (verb >= VERBOSE) {
520 MOFEM_LOG_C("SYNC", Sev::noisy, "received %lu (%lu) from %d at %d\n",
521 ent, parent, onodes[kk], m_field.get_comm_rank());
522 MOFEM_LOG("SYNC", Sev::noisy) << "Bit " << BitRefLevel(uulong_bit);
523 }
524 }
525 }
526
527 // Cleaning
528 CHKERR PetscFree(s_waits);
529 CHKERR PetscFree(rbuf[0]);
530 CHKERR PetscFree(rbuf);
531 CHKERR PetscFree(r_waits);
532 CHKERR PetscFree(onodes);
533 CHKERR PetscFree(olengths);
534 CHKERR PetscCommDestroy(&comm);
535
536 if (verb >= VERBOSE)
538
540}
#define MOFEM_LOG_C(channel, severity, format,...)
@ VERBOSE
@ MOFEM_IMPOSSIBLE_CASE
Definition definitions.h:35
auto bit
set bit
std::bitset< BITREFLEVEL_SIZE > BitRefLevel
Bit structure attached to each entity identifying to what mesh entity is attached.
Definition Types.hpp:40
auto type_from_handle(const EntityHandle h)
get type from entity handle
Tag get_th_RefBitLevel() const
Definition Core.hpp:203
Tag get_th_RefParentHandle() const
Definition Core.hpp:202

◆ setTagFromVector()

MoFEMErrorCode MoFEM::CommInterface::setTagFromVector ( moab::Interface &  moab,
EntitiesPetscVector vec,
Tag  tag 
)
static

Set the Tag From Vector object.

Parameters
moab
vec
tag

Example:

mField.get_moab(), face_exchange, tag_value_to_exchange);
static MoFEMErrorCode setTagFromVector(moab::Interface &moab, EntitiesPetscVector &vec, Tag tag)
Set the Tag From Vector object.
Returns
MoFEMErrorCode

Definition at line 1723 of file CommInterface.cpp.

1725 {
1727
1728 int local_size;
1729 CHKERR VecGetLocalSize(vec.second, &local_size);
1730 int nb_coeffs;
1731 CHKERR moab.tag_get_length(tag, nb_coeffs);
1732 if (vec.first.first.size() * nb_coeffs != local_size) {
1733 SETERRQ(PETSC_COMM_SELF, MOFEM_DATA_INCONSISTENCY,
1734 "Local size of vector does not match number of entities");
1735 }
1736
1737 auto set_tags_from_vec = [&]() {
1739 double *v_array;
1740 CHKERR VecGetArray(vec.second, &v_array);
1741 CHKERR moab.tag_set_data(tag, vec.first.first, v_array);
1742 CHKERR moab.tag_set_data(tag, vec.first.second, &v_array[local_size]);
1743 CHKERR VecRestoreArray(vec.second, &v_array);
1745 };
1746
1747 CHKERR set_tags_from_vec();
1748
1750}

◆ setVectorFromTag()

MoFEMErrorCode MoFEM::CommInterface::setVectorFromTag ( moab::Interface &  moab,
EntitiesPetscVector vec,
Tag  tag 
)
static

Set the Vector From Tag object.

Parameters
moab
vec
tag

Example:

mField.get_moab(), face_exchange, tag_value_to_exchange);
static MoFEMErrorCode setVectorFromTag(moab::Interface &moab, EntitiesPetscVector &vec, Tag tag)
Set the Vector From Tag object.
Returns
MoFEMErrorCode

Definition at line 1693 of file CommInterface.cpp.

1695 {
1697
1698 int local_size;
1699 CHKERR VecGetLocalSize(vec.second, &local_size);
1700 int nb_coeffs;
1701 CHKERR moab.tag_get_length(tag, nb_coeffs);
1702 if (vec.first.first.size() * nb_coeffs != local_size) {
1703 SETERRQ(PETSC_COMM_SELF, MOFEM_DATA_INCONSISTENCY,
1704 "Local size of vector does not match number of entities");
1705 }
1706
1707 auto set_vec_from_tags = [&]() {
1709 double *v_array;
1710 // set vector
1711 CHKERR VecGetArray(vec.second, &v_array);
1712 CHKERR moab.tag_get_data(tag, vec.first.first, v_array);
1713 CHKERR moab.tag_get_data(tag, vec.first.second, &v_array[local_size]);
1714 CHKERR VecRestoreArray(vec.second, &v_array);
1716 };
1717
1718 CHKERR set_vec_from_tags();
1719
1721}

◆ synchroniseEntities() [1/2]

MoFEMErrorCode MoFEM::CommInterface::synchroniseEntities ( Range ent,
int  verb = DEFAULT_VERBOSITY 
)

synchronize entity range on processors (collective)

Note
collective - need to be run on all processors in communicator
Parameters
entents to send and received
verb
Returns
MoFEMErrorCode

Definition at line 233 of file CommInterface.cpp.

233 {
234 return synchroniseEntities(ents, nullptr, verb);
235}
MoFEMErrorCode synchroniseEntities(Range &ent, std::map< int, Range > *received_ents, int verb=DEFAULT_VERBOSITY)
synchronize entity range on processors (collective)

◆ synchroniseEntities() [2/2]

MoFEMErrorCode MoFEM::CommInterface::synchroniseEntities ( Range ent,
std::map< int, Range > *  received_ents,
int  verb = DEFAULT_VERBOSITY 
)

synchronize entity range on processors (collective)

synchronize entity range on processors (collective)

Note
collective - need to be run on all processors in communicator
collective - need to be run on all processors in communicator
Parameters
entents to send and received
received_entspointer to map with received entities
verb
Returns
MoFEMErrorCode
Examples
mofem/tutorials/vec-7_shape_optimisation/adjoint.cpp.

Definition at line 19 of file CommInterface.cpp.

20 {
21 MoFEM::Interface &m_field = cOre;
22 ParallelComm *pcomm = ParallelComm::get_pcomm(
23 &m_field.get_moab(), m_field.get_basic_entity_data_ptr()->pcommID);
25
26 auto get_pstatus = [&](const auto ent) {
27 unsigned char pstatus;
28 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->pstatus_tag(), &ent,
29 1, &pstatus),
30 "can not get pstatus");
31 return pstatus;
32 };
33
34 auto get_sharing_procs = [&](const auto ent, const auto pstatus) {
35 std::vector<int> sharing_procs(MAX_SHARING_PROCS, -1);
36 if (pstatus & PSTATUS_MULTISHARED) {
37 // entity is multi shared
38 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(
39 pcomm->sharedps_tag(), &ent, 1, &sharing_procs[0]),
40 "can not ger sharing_procs_ptr");
41 } else if (pstatus & PSTATUS_SHARED) {
42 // shared
43 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->sharedp_tag(), &ent,
44 1, &sharing_procs[0]),
45 "can not get sharing proc");
46 }
47 return sharing_procs;
48 };
49
50 auto get_sharing_handles = [&](const auto ent, const auto pstatus) {
51 std::vector<EntityHandle> sharing_handles(MAX_SHARING_PROCS, 0);
52 if (pstatus & PSTATUS_MULTISHARED) {
53 // entity is multi shared
54 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(
55 pcomm->sharedhs_tag(), &ent, 1, &sharing_handles[0]),
56 "get shared handles");
57 } else if (pstatus & PSTATUS_SHARED) {
58 // shared
59 CHK_MOAB_THROW(m_field.get_moab().tag_get_data(pcomm->sharedh_tag(), &ent,
60 1, &sharing_handles[0]),
61 "get sharing handle");
62 }
63 return sharing_handles;
64 };
65
66 // make a buffer entities to send
67 std::vector<std::vector<EntityHandle>> sbuffer(m_field.get_comm_size());
68
69 for (auto ent : ents) {
70
71 auto pstatus = get_pstatus(ent);
72 if (pstatus) {
73 auto sharing_procs = get_sharing_procs(ent, pstatus);
74 auto sharing_handles = get_sharing_handles(ent, pstatus);
75
76 if (verb >= NOISY) {
77 MOFEM_LOG("SYNC", Sev::noisy) << "pstatus " << std::bitset<8>(pstatus);
78 }
79
80 for (int proc = 0; proc < MAX_SHARING_PROCS && -1 != sharing_procs[proc];
81 proc++) {
82 if (sharing_procs[proc] == -1)
83 SETERRQ(PETSC_COMM_SELF, MOFEM_IMPOSSIBLE_CASE,
84 "sharing processor not set");
85
86 if (sharing_procs[proc] == m_field.get_comm_rank())
87 continue;
88
89 const auto handle_on_sharing_proc = sharing_handles[proc];
90 // add entity to send, handle on the other side
91 sbuffer[sharing_procs[proc]].push_back(handle_on_sharing_proc);
92 if (verb >= NOISY) {
93 MOFEM_LOG_C("SYNC", Sev::noisy, "send %lu (%lu) to %d at %d\n", ent,
94 handle_on_sharing_proc, sharing_procs[proc],
95 m_field.get_comm_rank());
96 }
97
98 if (!(pstatus & PSTATUS_MULTISHARED))
99 break;
100 }
101 }
102 }
103 if (verb >= NOISY) {
104 MOFEM_LOG_SEVERITY_SYNC(m_field.get_comm(), Sev::noisy);
105 }
106
107 int nsends = 0; // number of messages to send
108 std::vector<int> sbuffer_lengths(
109 m_field.get_comm_size()); // length of the message to proc
110 const size_t block_size =
111 sizeof(EntityHandle) /
112 sizeof(int); // FIXME check if that works on given architecture!
113 for (int proc = 0; proc < m_field.get_comm_size(); proc++) {
114
115 if (!sbuffer[proc].empty()) {
116
117 sbuffer_lengths[proc] = sbuffer[proc].size() * block_size;
118 nsends++;
119
120 } else {
121
122 sbuffer_lengths[proc] = 0;
123 }
124 }
125
126 // Make sure it is a PETSc m_field.get_comm()
127 MPI_Comm comm;
128 CHKERR PetscCommDuplicate(m_field.get_comm(), &comm, NULL);
129
130 std::vector<MPI_Status> status(m_field.get_comm_size());
131
132 // Computes the number of messages a node expects to receive
133 int nrecvs; // number of messages received
134 CHKERR PetscGatherNumberOfMessages(comm, NULL, &sbuffer_lengths[0], &nrecvs);
135
136 // Computes info about messages that a MPI-node will receive, including
137 // (from-id,length) pairs for each message.
138 int *onodes; // list of node-ids from which messages are expected
139 int *olengths; // corresponding message lengths
140 CHKERR PetscGatherMessageLengths(comm, nsends, nrecvs, &sbuffer_lengths[0],
141 &onodes, &olengths);
142
143 // Gets a unique new tag from a PETSc communicator. All processors that share
144 // the communicator MUST call this routine EXACTLY the same number of times.
145 // This tag should only be used with the current objects communicator; do NOT
146 // use it with any other MPI communicator.
147 int tag;
148 CHKERR PetscCommGetNewTag(comm, &tag);
149
150 // Allocate a buffer sufficient to hold messages of size specified in
151 // olengths. And post Irecvs on these buffers using node info from onodes
152 int **rbuf; // must bee freed by user
153 MPI_Request *r_waits; // must bee freed by user
154 // rbuf has a pointers to messages. It has size of of nrecvs (number of
155 // messages) +1. In the first index a block is allocated,
156 // such that rbuf[i] = rbuf[i-1]+olengths[i-1].
157 CHKERR PetscPostIrecvInt(comm, tag, nrecvs, onodes, olengths, &rbuf,
158 &r_waits);
159
160 MPI_Request *s_waits; // status of sens messages
161 CHKERR PetscMalloc1(nsends, &s_waits);
162
163 // Send messages
164 for (int proc = 0, kk = 0; proc < m_field.get_comm_size(); proc++) {
165 if (!sbuffer_lengths[proc])
166 continue; // no message to send to this proc
167 CHKERR MPI_Isend(&(sbuffer[proc])[0], // buffer to send
168 sbuffer_lengths[proc], // message length
169 MPIU_INT, proc, // to proc
170 tag, comm, s_waits + kk);
171 kk++;
172 }
173
174 // Wait for received
175 if (nrecvs)
176 CHKERR MPI_Waitall(nrecvs, r_waits, &status[0]);
177
178 // Wait for send messages
179 if (nsends)
180 CHKERR MPI_Waitall(nsends, s_waits, &status[0]);
181
182 if (verb >= VERBOSE) {
183 MOFEM_LOG_C("SYNC", Sev::verbose, "Rank %d nb. before ents %zu\n",
184 m_field.get_comm_rank(), ents.size());
185 MOFEM_LOG_SEVERITY_SYNC(m_field.get_comm(), Sev::verbose);
186 }
187
188 // synchronise range
189 for (int kk = 0; kk < nrecvs; kk++) {
190
191 int len = olengths[kk];
192 int *data_from_proc = rbuf[kk];
193
194 for (int ee = 0; ee < len;) {
195 EntityHandle ent;
196 bcopy(&data_from_proc[ee], &ent, sizeof(EntityHandle));
197 ents.insert(ent);
198
199 if (received_ents) {
200 (*received_ents)[onodes[kk]].insert(ent);
201 }
202
203 ee += block_size;
204
205 if (verb >= VERBOSE) {
206 MOFEM_LOG_C("SYNC", Sev::noisy, "received %lu from %d at %d\n", ent,
207 onodes[kk], m_field.get_comm_rank());
208 }
209 }
210 }
211 if (verb >= VERBOSE) {
212 MOFEM_LOG_SEVERITY_SYNC(m_field.get_comm(), Sev::verbose);
213 }
214
215 if (verb >= VERBOSE) {
216 MOFEM_LOG_C("SYNC", Sev::verbose, "Rank %d nb. after ents %zu",
217 m_field.get_comm_rank(), ents.size());
218 MOFEM_LOG_SEVERITY_SYNC(m_field.get_comm(), Sev::verbose);
219 }
220
221 // Cleaning
222 CHKERR PetscFree(s_waits);
223 CHKERR PetscFree(rbuf[0]);
224 CHKERR PetscFree(rbuf);
225 CHKERR PetscFree(r_waits);
226 CHKERR PetscFree(onodes);
227 CHKERR PetscFree(olengths);
228 CHKERR PetscCommDestroy(&comm);
229
231}

◆ updateEntitiesPetscVector()

MoFEMErrorCode MoFEM::CommInterface::updateEntitiesPetscVector ( moab::Interface &  moab,
EntitiesPetscVector vec,
Tag  tag,
UpdateGhosts  update_gosts = defaultUpdateGhosts 
)
static

Exchange data between vector and data.

Parameters
tag

This reads values from the tag, exchanges ghost values, and writes the exchanged values back to the tag.

Example:

mField.get_moab(), face_exchange, tag_value_to_exchange);
Returns
MoFEMErrorCode

Definition at line 1766 of file CommInterface.cpp.

1768 {
1770
1771 CHKERR setVectorFromTag(moab, vec, tag);
1772 CHKERR update_ghosts(vec.second);
1773 CHKERR setTagFromVector(moab, vec, tag);
1774
1776}

Member Data Documentation

◆ cOre

MoFEM::Core& MoFEM::CommInterface::cOre

Definition at line 74 of file CommInterface.hpp.

◆ debug

bool MoFEM::CommInterface::debug = false
inlinestatic

Definition at line 68 of file CommInterface.hpp.

◆ dEbug

bool MoFEM::CommInterface::dEbug

Definition at line 75 of file CommInterface.hpp.

◆ sev

Sev MoFEM::CommInterface::sev = Sev::verbose
inlinestatic

Definition at line 69 of file CommInterface.hpp.


The documentation for this struct was generated from the following files: