v0.9.1
EntsMultiIndices.cpp
Go to the documentation of this file.
1 /** \file EntsMultiIndices.cpp
2  * \brief Multi-index containers for entities
3  */
4 
5 /* MoFEM is free software: you can redistribute it and/or modify it under
6  * the terms of the GNU Lesser General Public License as published by the
7  * Free Software Foundation, either version 3 of the License, or (at your
8  * option) any later version.
9  *
10  * MoFEM is distributed in the hope that it will be useful, but WITHOUT
11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
12  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
13  * License for more details.
14  *
15  * You should have received a copy of the GNU Lesser General Public
16  * License along with MoFEM. If not, see <http://www.gnu.org/licenses/>
17  */
18 
19 #define IS_BUILDING_MB
20 #include <moab/Error.hpp>
21 
22 namespace MoFEM {
23 
24 static moab::Error error;
25 
26 inline void *get_tag_ptr(moab::Interface &moab, Tag th, EntityHandle ent,
27  int *tag_size) {
28  ApproximationOrder *ret_val;
29  rval = moab.tag_get_by_ptr(th, &ent, 1, (const void **)&ret_val, tag_size);
30  if (rval != MB_SUCCESS) {
31  *tag_size = 0;
32  return NULL;
33  } else {
34  return ret_val;
35  }
36 }
37 
39  const int pcomm_id)
40  : moab(const_cast<moab::Interface &>(moab)), pcommID(pcomm_id),
41  distributedMesh(true) {
42  rval = moab.tag_get_handle("_RefParentHandle", th_RefParentHandle);
44  rval = moab.tag_get_handle("_RefBitLevel", th_RefBitLevel);
46 }
47 
48 // basic moab ent
50  const boost::shared_ptr<BasicEntityData> &basic_data_ptr,
51  const EntityHandle ent)
52  : basicDataPtr(basic_data_ptr), ent(ent) {
53  switch (getEntType()) {
54  case MBVERTEX:
55  case MBEDGE:
56  case MBTRI:
57  case MBQUAD:
58  case MBTET:
59  case MBPRISM:
60  case MBENTITYSET:
61  break;
62  default:
63  THROW_MESSAGE("this entity type is currently not implemented");
64  }
65  ParallelComm *pcomm =
66  ParallelComm::get_pcomm(&basicDataPtr->moab, basicDataPtr->pcommID);
67  if (pcomm == NULL)
68  THROW_MESSAGE("pcomm is null");
69  rval = pcomm->get_owner_handle(ent, owner_proc, moab_owner_handle);
72 }
73 
74 unsigned char BasicEntity::getPStatus() const {
75  ParallelComm *pcomm =
76  ParallelComm::get_pcomm(&basicDataPtr->moab, basicDataPtr->pcommID);
77  return *((unsigned char *)MoFEM::get_tag_ptr(
78  basicDataPtr->moab, pcomm->pstatus_tag(), ent, NULL));
79 }
80 
81 // ref moab ent
83 RefEntity::RefEntity(const boost::shared_ptr<BasicEntityData> &basic_data_ptr,
84  const EntityHandle ent)
85  : BasicEntity(basic_data_ptr, ent) {}
86 
88  return static_cast<EntityHandle *>(get_tag_ptr(
89  basicDataPtr->moab, basicDataPtr->th_RefParentHandle, ent, NULL));
90 }
91 
93  return static_cast<BitRefLevel *>(
94  get_tag_ptr(basicDataPtr->moab, basicDataPtr->th_RefBitLevel, ent, NULL));
95 }
96 
98  std::vector<EntityHandle> vec_patent_ent) {
99 
101  Tag th_ref_parent_handle;
102  CHKERR moab.tag_get_handle("_RefParentHandle", th_ref_parent_handle);
103  vec_patent_ent.resize(ents.size());
104  CHKERR moab.tag_get_data(th_ref_parent_handle, ents,
105  &*vec_patent_ent.begin());
107 }
108 
111  std::vector<BitRefLevel> &vec_bit_ref_level) {
112 
114  Tag th_ref_bit_level;
115  CHKERR moab.tag_get_handle("_RefBitLevel", th_ref_bit_level);
116  vec_bit_ref_level.resize(ents.size());
117  CHKERR moab.tag_get_data(th_ref_bit_level, ents, &*vec_bit_ref_level.begin());
119 }
120 
122  moab::Interface &moab, Range ents,
123  std::vector<const BitRefLevel *> &vec_ptr_bit_ref_level) {
125  Tag th_ref_bit_level;
126  CHKERR moab.tag_get_handle("_RefBitLevel", th_ref_bit_level);
127  vec_ptr_bit_ref_level.resize(ents.size());
128  CHKERR moab.tag_get_by_ptr(
129  th_ref_bit_level, ents,
130  reinterpret_cast<const void **>(&*vec_ptr_bit_ref_level.begin()));
132 }
133 
134 std::ostream &operator<<(std::ostream &os, const RefEntity &e) {
135  os << "ent " << e.ent;
136  os << " pstatus " << std::bitset<8>(e.getPStatus());
137  os << " owner ent " << e.getOwnerEnt();
138  os << " owner proc " << e.getOwnerProc();
139  os << " parent ent " << e.getParentEnt();
140  // os << " BitRefLevel " << e.getBitRefLevel();
141  os << " ent type " << e.getEntType();
142  os << " ent parent type " << e.getParentEntType();
143  return os;
144 }
145 
146 // moab ent
148  const boost::shared_ptr<Field> &field_ptr,
149  const boost::shared_ptr<RefEntity> &ref_ents_ptr,
150  boost::shared_ptr<double *const> &&field_data_adaptor_ptr,
151  boost::shared_ptr<const int> &&t_max_order_ptr)
153  ref_ents_ptr),
154  tagMaxOrderPtr(t_max_order_ptr),
155  fieldDataAdaptorPtr(field_data_adaptor_ptr) {
157 
158  if (PetscUnlikely(!fieldDataAdaptorPtr))
159  THROW_MESSAGE("Pointer to field data adaptor not set");
160 
161  if (PetscUnlikely(!tagMaxOrderPtr))
162  THROW_MESSAGE("Pointer to max order not set");
163 }
164 
165 boost::shared_ptr<FieldData *const> FieldEntity::makeSharedFieldDataAdaptorPtr(
166  const boost::shared_ptr<Field> &field_ptr,
167  const boost::shared_ptr<RefEntity> &ref_ents_ptr) {
168  int size;
169  double *ptr;
170  switch (ref_ents_ptr->getEntType()) {
171  case MBVERTEX:
172  size = field_ptr->getNbOfCoeffs();
173  ptr = static_cast<FieldData *>(
174  MoFEM::get_tag_ptr(field_ptr->moab, field_ptr->th_FieldDataVerts,
175  ref_ents_ptr->ent, &size));
176  break;
177  default:
178  ptr = static_cast<FieldData *>(MoFEM::get_tag_ptr(
179  field_ptr->moab, field_ptr->th_FieldData, ref_ents_ptr->ent, &size));
180  }
181  return boost::make_shared<FieldData *const>(ptr);
182 }
183 
184 std::ostream &operator<<(std::ostream &os, const FieldEntity &e) {
185  os << "ent_global_uid "
186  << (UId)e.getGlobalUniqueId()
187  // << " ent_local_uid " << (UId)e.get_local_unique_id()
188  << " entity " << e.getEnt() << " type " << e.getEntType() << " pstatus "
189  << std::bitset<8>(e.getPStatus()) << " owner handle " << e.getOwnerEnt()
190  << " owner proc " << e.getOwnerProc() << " order " << e.getMaxOrder()
191  << " " << *e.sFieldPtr;
192  return os;
193 }
194 
196 
197  moab::Interface &moab = e->sPtr->basicDataPtr->moab;
198  const EntityHandle ent = e->getEnt();
199  *const_cast<ApproximationOrder *>(e->getMaxOrderPtr()) = order;
200  std::size_t nb_dofs = e->getOrderNbDofs(order) * e->getNbOfCoeffs();
201 
202  double *tag_field_data = nullptr;
203  int tag_field_data_size = 0;
204 
205  auto set_verts = [&]() {
206  if (e->sFieldPtr->th_FieldDataVertsType == MB_TAG_SPARSE) {
207  // Get pointer and size of field values tag
208  rval = moab.tag_get_by_ptr(e->sFieldPtr->th_FieldDataVerts, &ent, 1,
209  (const void **)&tag_field_data,
210  &tag_field_data_size);
211  if (nb_dofs) {
212  if (nb_dofs != tag_field_data_size) {
213  rval = moab.tag_set_data(e->sFieldPtr->th_FieldDataVerts, &ent, 1,
214  &*data.begin());
215  MOAB_THROW(rval);
216  }
217  } else if (rval == MB_SUCCESS) {
218  rval = moab.tag_delete_data(e->sFieldPtr->th_FieldDataVerts, &ent, 1);
219  MOAB_THROW(rval);
220  }
221  } else {
222  rval = moab.tag_get_by_ptr(e->sFieldPtr->th_FieldDataVerts, &ent, 1,
223  (const void **)&tag_field_data);
224  MOAB_THROW(rval);
225  rval = moab.tag_set_data(e->sFieldPtr->th_FieldDataVerts, &ent, 1,
226  tag_field_data);
227  MOAB_THROW(rval);
228  }
229  };
230 
231  auto set_default = [&]() {
232  if (reduceTagSize || nb_dofs) {
233 
234  // Get pointer and size of field values tag
235  rval = moab.tag_get_by_ptr(e->sFieldPtr->th_FieldData, &ent, 1,
236  (const void **)&tag_field_data,
237  &tag_field_data_size);
238 
239  if ((reduceTagSize && nb_dofs != tag_field_data_size) ||
240  nb_dofs > tag_field_data_size) {
241 
242  // Tag exist and are some data on it
243  if (rval == MB_SUCCESS) {
244  // Size of tag is different than new size, so copy data to new
245  // container
246  data.resize(tag_field_data_size);
247  FieldData *ptr_begin = static_cast<FieldData *>(tag_field_data);
248  FieldData *ptr_end =
249  static_cast<FieldData *>(tag_field_data) + tag_field_data_size;
250  std::copy(ptr_begin, ptr_end, data.begin());
251  }
252 
253  if (rval != MB_SUCCESS || nb_dofs) {
254 
255  // Set field dof data
256  data.resize(nb_dofs, 0);
257  int tag_size[1];
258  tag_size[0] = data.size();
259  void const *tag_data[] = {&data[0]};
260  rval = moab.tag_set_by_ptr(e->sFieldPtr->th_FieldData, &ent, 1,
261  tag_data, tag_size);
262  MOAB_THROW(rval);
263  rval = moab.tag_get_by_ptr(e->sFieldPtr->th_FieldData, &ent, 1,
264  (const void **)&tag_field_data,
265  &tag_field_data_size);
266  MOAB_THROW(rval);
267 
268  } else {
269 
270  rval = moab.tag_delete_data(e->sFieldPtr->th_FieldData, &ent, 1);
271  MOAB_THROW(rval);
272  }
273  }
274  }
275  };
276 
277  switch (e->getEntType()) {
278  case MBVERTEX:
279  set_verts();
280  break;
281  default:
282  set_default();
283  }
284 
285  if (nb_dofs)
286  const_cast<double *&>(*(e->getEntFieldDataPtr())) = tag_field_data;
287  else
288  const_cast<double *&>(*(e->getEntFieldDataPtr())) = nullptr;
289 }
290 
291 } // namespace MoFEM
const BitRefLevel & getBitRefLevel() const
Get entity ref bit refinement signature.
unsigned char getPStatus() const
get pstatus This tag stores various aspects of parallel status in bits; see also define following,...
boost::shared_ptr< T > sPtr
Deprecated interface functions.
RefEntity(const boost::shared_ptr< BasicEntityData > &basic_data_ptr, const EntityHandle ent)
int getOrderNbDofs(ApproximationOrder order) const
Get number of DOFs on entity for given order of approximation.
this struct keeps basic methods for moab entity
Provide data structure for (tensor) field approximation.The Field is intended to provide support for ...
int ApproximationOrder
Approximation on the entity.
Definition: Types.hpp:37
EntityHandle * getParentEntPtr() const
Get pointer to parent entity tag.
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
Definition: definitions.h:483
UId getGlobalUniqueIdCalculate() const
Calculate global UId.
FieldCoefficientsNumber getNbOfCoeffs() const
BasicEntity(const boost::shared_ptr< BasicEntityData > &basic_data_ptr, const EntityHandle ent)
#define THROW_MESSAGE(a)
Throw MoFEM exception.
Definition: definitions.h:626
FieldEntity(const boost::shared_ptr< Field > &field_ptr, const boost::shared_ptr< RefEntity > &ref_ents_ptr, boost::shared_ptr< double *const > &&field_data_adaptor_ptr, boost::shared_ptr< const int > &&t_max_order_ptr)
Struct keeps handle to entity in the field.
UId globalUId
Global unique id for this entity.
#define MOAB_THROW(a)
Check error code of MoAB function and throw MoFEM exception.
Definition: definitions.h:608
Pointer interface for MoFEM::Field.
const UId & getGlobalUniqueId() const
Get global unique id.
Struct keeps handle to refined handle.
implementation of Data Operators for Forces and Sources
Definition: Common.hpp:21
moab::Interface & moab
MoFEMErrorCode getParentEnt(moab::Interface &moab, Range ents, std::vector< EntityHandle > vec_patent_ent)
EntityHandle getOwnerEnt() const
std::bitset< BITREFEDGES_SIZE > BitRefEdges
Definition: Types.hpp:44
static MoFEMErrorCodeGeneric< moab::ErrorCode > rval
Definition: Exceptions.hpp:85
std::ostream & operator<<(std::ostream &os, const DataForcesAndSourcesCore::EntData &e)
const ApproximationOrder * getMaxOrderPtr() const
Get pinter to Tag keeping approximation order.
ApproximationOrder getMaxOrder() const
Get order set to the entity (Allocated tag size for such number)
int part_proc
this can be changed on distributed
EntityType getEntType() const
Get entity type.
int owner_proc
this never can not be changed if distributed mesh
EntityHandle getOwnerEnt() const
Owner handle on this or other processors.
PetscErrorCode MoFEMErrorCode
MoFEM/PETSc error code.
Definition: Exceptions.hpp:67
BasicEntityData(const moab::Interface &mfield, const int pcomm_id=MYPCOMM_INDEX)
static MoFEMErrorCode getParentEnt(Interface &moab, Range ents, std::vector< EntityHandle > vec_patent_ent)
boost::shared_ptr< FieldData *const > & getEntFieldDataPtr() const
Get shared ptr to vector adaptor pointing to the field tag data on entity.
EntityType getParentEntType() const
Get patent entity.
interface to RefEntity
static moab::Error error
EntityHandle moab_owner_handle
#define CHKERR
Inline error check.
Definition: definitions.h:602
static boost::shared_ptr< FieldData *const > makeSharedFieldDataAdaptorPtr(const boost::shared_ptr< Field > &field_ptr, const boost::shared_ptr< RefEntity > &ref_ents_ptr)
Return shared pointer to entity field data vector adaptor.
unsigned char getPStatus() const
void operator()(boost::shared_ptr< FieldEntity > &e)
std::bitset< BITREFLEVEL_SIZE > BitRefLevel
Bit structure attached to each entity identifying to what mesh entity is attached.
Definition: Types.hpp:50
const ApproximationOrder order
void * get_tag_ptr(moab::Interface &moab, Tag th, EntityHandle ent, int *tag_size)
DeprecatedCoreInterface Interface
Definition: Interface.hpp:1879
EntityHandle getEnt() const
Get entity handle.
int getOwnerProc() const
Get processor owning entity.
#define MoFEMFunctionBegin
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
Definition: definitions.h:413
boost::shared_ptr< BasicEntityData > basicDataPtr
static BitRefEdges DummyBitRefEdges
boost::shared_ptr< FieldData *const > fieldDataAdaptorPtr
boost::shared_ptr< const ApproximationOrder > tagMaxOrderPtr
uint128_t UId
Unique Id.
Definition: Types.hpp:41
boost::shared_ptr< T > sFieldPtr
std::vector< FieldData > data
BitRefLevel * getBitRefLevelPtr() const
Get pointer to bit ref level tag.