8namespace BcManagerImplTools {
11 for (
auto d : {3, 2, 1})
12 if (ents.num_of_dimension(d))
19 CHK_MOAB_THROW(moab.get_connectivity(ents, verts,
true),
"get verts");
21 for (
size_t d = 1; d <
dim; ++d) {
22 for (
auto dd = d + 1; dd <=
dim; ++dd) {
23 CHK_MOAB_THROW(moab.get_adjacencies(ents.subset_by_dimension(dd), d,
24 false, verts, moab::Interface::UNION),
44 auto core_log = logging::core::get();
62 MOFEM_LOG(
"BcMngWorld", Sev::noisy) <<
"BC manager created";
67 ierr = PetscOptionsBegin(PETSC_COMM_WORLD,
"",
"BcManager options",
"none");
68 ierr = PetscOptionsEnd();
74 const std::string problem_name,
const std::string block_name,
75 const std::string
field_name,
int lo,
int hi,
bool get_low_dim_ents,
76 bool is_distributed_mesh) {
84 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
86 if (is_distributed_mesh)
87 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
90 return prb_mng->removeDofsOnEntitiesNotDistributed(
97 (boost::format(
"%s(.*)") % block_name).str()
102 const std::string bc_id =
103 problem_name +
"_" +
field_name +
"_" +
m->getName();
112 const std::string block_name,
115 bool get_low_dim_ents) {
124 auto fix_disp = [&]() {
127 auto mark_fix_dofs = [&](std::vector<unsigned char> &marked_field_dofs,
128 const auto lo,
const auto hi) {
129 return prb_mng->modifyMarkDofs(problem_name,
ROW,
field_name, lo, hi,
134 auto iterate_meshsets = [&](
auto &&meshset_vec_ptr) {
136 for (
auto m : meshset_vec_ptr) {
137 auto bc = boost::make_shared<BCs>();
140 CHKERR m->getAttributes(bc->bcAttributes);
142 if (problem_name.size())
143 CHKERR mark_fix_dofs(bc->bcMarkers, lo, hi);
145 <<
"Found block " <<
m->getName() <<
" number of attributes "
146 << bc->bcAttributes.size();
148 if (get_low_dim_ents) {
151 bc->bcEnts.swap(low_dim_ents);
156 if (problem_name.size())
158 bc->bcEnts, bc->bcMarkers);
160 const std::string bc_id =
161 problem_name +
"_" +
field_name +
"_" +
m->getName();
171 (boost::format(
"%s(.*)") % block_name).str()
185boost::shared_ptr<BcManager::BCs>
189 auto bc = bc_it->second;
193 return boost::shared_ptr<BCs>();
200 for (
auto ®_name : bc_regex_vec) {
201 if (std::regex_match(b.first, reg_name)) {
202 ents.merge(b.second->bcEnts);
215 for (
auto ®_name : bc_regex_vec) {
216 if (std::regex_match(b.first, reg_name)) {
217 if (!boundary_marker_ptr)
218 boundary_marker_ptr =
219 boost::make_shared<std::vector<char unsigned>>();
220 boundary_marker_ptr->resize(b.second->bcMarkers.size(), 0);
221 for (
int i = 0;
i != b.second->bcMarkers.size(); ++
i) {
222 (*boundary_marker_ptr)[
i] |= b.second->bcMarkers[
i];
228 return boundary_marker_ptr;
232 const std::vector<BcManager::BcMarkerPtr> &boundary_markers_ptr_vec) {
233 auto boundary_marker_ptr = boost::make_shared<std::vector<char unsigned>>();
234 for (
auto &bcm : boundary_markers_ptr_vec) {
235 boundary_marker_ptr->resize(bcm->size(), 0);
236 for (
int i = 0;
i != bcm->size(); ++
i)
237 (*boundary_marker_ptr)[
i] |= (*bcm)[
i];
239 return boundary_marker_ptr;
243 const std::string block_name,
245 const std::string problem_name,
int lo,
249 const std::string bc_id =
250 block_prefix +
"_" +
field_name +
"_" + block_name +
"(.*)";
254 if (std::regex_match(bc.first, std::regex(bc_id))) {
255 bc_ents.merge(*(bc.second->getBcEntsPtr()));
257 <<
"Get entities from block and add to IS. Block name " << bc.first;
262 auto get_is = [&]() {
269 CHKERR ISExpand(is_bc, is_expand, &is_tmp);
283 const std::string block_name,
292BcManager::removeBlockDOFsOnEntities<BcMeshsetType<DISPLACEMENTSET>>(
293 const std::string problem_name,
const std::string
field_name,
294 bool get_low_dim_ents,
bool block_name_field_prefix,
295 bool is_distributed_mesh) {
300 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<DISPLACEMENTSET>>(
301 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
303 std::array<Range, 3> ents_to_remove;
310 const std::string bc_id =
311 problem_name +
"_" +
field_name +
"_DISPLACEMENTSET" +
312 boost::lexical_cast<std::string>(
m->getMeshsetId());
314 auto bc = bcMapByBlockName.at(bc_id);
317 if (bc->dispBcPtr->data.flag1) {
318 ents_to_remove[0].merge(bc->bcEnts);
320 if (bc->dispBcPtr->data.flag2) {
321 ents_to_remove[1].merge(bc->bcEnts);
323 if (bc->dispBcPtr->data.flag3) {
324 ents_to_remove[2].merge(bc->bcEnts);
326 if (bc->dispBcPtr->data.flag4) {
327 ents_to_remove[1].merge(bc->bcEnts);
328 ents_to_remove[2].merge(bc->bcEnts);
330 if (bc->dispBcPtr->data.flag5) {
331 ents_to_remove[0].merge(bc->bcEnts);
332 ents_to_remove[2].merge(bc->bcEnts);
334 if (bc->dispBcPtr->data.flag6) {
335 ents_to_remove[0].merge(bc->bcEnts);
336 ents_to_remove[1].merge(bc->bcEnts);
339 bc->bcMarkers = std::vector<unsigned char>();
342 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
344 if (is_distributed_mesh)
345 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
348 return prb_mng->removeDofsOnEntitiesNotDistributed(
352 CHKERR remove_dofs_on_ents(ents_to_remove[0], 0, 0);
353 CHKERR remove_dofs_on_ents(ents_to_remove[1], 1, 1);
354 CHKERR remove_dofs_on_ents(ents_to_remove[2], 2, 2);
361BcManager::removeBlockDOFsOnEntities<BcMeshsetType<TEMPERATURESET>>(
362 const std::string problem_name,
const std::string
field_name,
363 bool get_low_dim_ents,
bool block_name_field_prefix,
364 bool is_distributed_mesh) {
369 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<TEMPERATURESET>>(
370 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
372 Range ents_to_remove;
380 const std::string bc_id =
381 problem_name +
"_" +
field_name +
"_TEMPERATURESET" +
382 boost::lexical_cast<std::string>(
m->getMeshsetId());
383 auto bc = bcMapByBlockName.at(bc_id);
384 ents_to_remove.merge(bc->bcEnts);
385 bc->bcMarkers = std::vector<unsigned char>();
388 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
390 if (is_distributed_mesh)
391 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
394 return prb_mng->removeDofsOnEntitiesNotDistributed(
405 const std::string problem_name,
const std::string
field_name,
406 bool get_low_dim_ents,
bool block_name_field_prefix,
407 bool is_distributed_mesh) {
412 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<HEATFLUXSET>>(
413 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
415 Range ents_to_remove;
423 const std::string bc_id =
424 problem_name +
"_" +
field_name +
"_HEATFLUXSET" +
425 boost::lexical_cast<std::string>(
m->getMeshsetId());
426 auto bc = bcMapByBlockName.at(bc_id);
427 ents_to_remove.merge(bc->bcEnts);
428 bc->bcMarkers = std::vector<unsigned char>();
431 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
433 if (is_distributed_mesh)
434 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
437 return prb_mng->removeDofsOnEntitiesNotDistributed(
448BcManager::removeBlockDOFsOnEntities<BcDisplacementMeshsetType<BLOCKSET>>(
449 const std::string problem_name,
const std::string
field_name,
450 bool get_low_dim_ents,
bool block_name_field_prefix,
451 bool is_distributed_mesh) {
456 CHKERR pushMarkDOFsOnEntities<BcDisplacementMeshsetType<BLOCKSET>>(
457 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
459 std::array<Range, 3> ents_to_remove;
466 const auto block_name =
m->getName();
468 std::string bc_id = problem_name +
"_" +
field_name +
"_" + block_name;
469 std::string regex_str;
470 if (block_name_field_prefix) {
471 regex_str = (boost::format(
"%s_%s_%s_((FIX_(ALL|X|Y|Z))|("
472 "DISPLACEMENT|ROTATE))(.*)") %
476 regex_str = (boost::format(
"%s_%s_((FIX_(ALL|X|Y|Z))|("
477 "DISPLACEMENT|ROTATE))(.*)") %
482 if (std::regex_match(bc_id, std::regex(regex_str))) {
484 auto bc = bcMapByBlockName.at(bc_id);
486 if (
auto disp_bc = bc->dispBcPtr) {
487 if (disp_bc->data.flag1) {
488 ents_to_remove[0].merge(bc->bcEnts);
490 if (disp_bc->data.flag2) {
491 ents_to_remove[1].merge(bc->bcEnts);
493 if (disp_bc->data.flag3) {
494 ents_to_remove[2].merge(bc->bcEnts);
496 if (disp_bc->data.flag4) {
497 ents_to_remove[1].merge(bc->bcEnts);
498 ents_to_remove[2].merge(bc->bcEnts);
500 if (disp_bc->data.flag5) {
501 ents_to_remove[0].merge(bc->bcEnts);
502 ents_to_remove[2].merge(bc->bcEnts);
504 if (disp_bc->data.flag6) {
505 ents_to_remove[0].merge(bc->bcEnts);
506 ents_to_remove[1].merge(bc->bcEnts);
510 "BC type not implemented");
515 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
517 if (is_distributed_mesh)
518 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
521 return prb_mng->removeDofsOnEntitiesNotDistributed(
525 CHKERR remove_dofs_on_ents(ents_to_remove[0], 0, 0);
526 CHKERR remove_dofs_on_ents(ents_to_remove[1], 1, 1);
527 CHKERR remove_dofs_on_ents(ents_to_remove[2], 2, 2);
534BcManager::removeBlockDOFsOnEntities<BcScalarMeshsetType<BLOCKSET>>(
535 const std::string problem_name,
const std::string block_name,
536 const std::string
field_name,
bool get_low_dim_ents,
537 bool is_distributed_mesh) {
542 CHKERR pushMarkDOFsOnEntities<BcScalarMeshsetType<BLOCKSET>>(
543 problem_name, block_name,
field_name, get_low_dim_ents);
545 Range ents_to_remove;
552 std::string bc_id = problem_name +
"_" +
field_name +
"_" +
m->getName();
554 auto str = boost::format(
"%s_%s_%s(.*)")
558 if (std::regex_match(bc_id, std::regex(str.str()))) {
560 auto bc = bcMapByBlockName.at(bc_id);
562 if (
auto temp_bc = bc->tempBcPtr) {
563 if (temp_bc->data.flag1) {
564 ents_to_remove.merge(bc->bcEnts);
568 "BC type not implemented");
573 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
575 if (is_distributed_mesh)
576 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
579 return prb_mng->removeDofsOnEntitiesNotDistributed(
590BcManager::pushMarkDOFsOnEntities<BcMeshsetType<DISPLACEMENTSET>>(
591 const std::string problem_name,
const std::string
field_name,
592 bool get_low_dim_ents,
bool block_name_field_prefix) {
601 if (block_name_field_prefix)
603 <<
"Argument block_name_field_prefix=true has no effect";
605 auto fix_disp = [&]() {
608 auto iterate_meshsets = [&](
auto &&meshset_vec_ptr) {
610 for (
auto m : meshset_vec_ptr) {
611 auto bc = boost::make_shared<BCs>();
614 bc->dispBcPtr = boost::make_shared<DisplacementCubitBcData>();
615 CHKERR m->getBcDataStructure(*(bc->dispBcPtr));
618 <<
"Found block DISPLACEMENTSET id = " <<
m->getMeshsetId();
619 MOFEM_LOG(
"BcMngWorld", Sev::verbose) << *bc->dispBcPtr;
622 <<
"Found block DISPLACEMENTSET id = " <<
m->getMeshsetId()
623 <<
" nb. of entities " << bc->bcEnts.size()
624 <<
" highest dim of entities "
626 MOFEM_LOG(
"BcMngSync", Sev::noisy) << *bc->dispBcPtr;
629 if (problem_name.size()) {
631 if (bc->dispBcPtr->data.flag1)
635 if (bc->dispBcPtr->data.flag2)
639 if (bc->dispBcPtr->data.flag3)
643 if (bc->dispBcPtr->data.flag4) {
652 if (bc->dispBcPtr->data.flag5) {
661 if (bc->dispBcPtr->data.flag6) {
672 if (get_low_dim_ents) {
675 bc->bcEnts.swap(low_dim_ents);
680 if (problem_name.size())
682 bc->bcEnts, bc->bcMarkers);
684 const std::string bc_id =
685 problem_name +
"_" +
field_name +
"_DISPLACEMENTSET" +
686 boost::lexical_cast<std::string>(
m->getMeshsetId());
687 bcMapByBlockName[bc_id] = bc;
709 const std::string problem_name,
const std::string
field_name,
710 bool get_low_dim_ents,
bool block_name_field_prefix) {
715 if (block_name_field_prefix)
717 <<
"Argument block_name_field_prefix=true has no effect";
719 auto fix_temp = [&]() {
722 auto iterate_meshsets = [&](
auto &&meshset_vec_ptr) {
724 for (
auto m : meshset_vec_ptr) {
725 auto bc = boost::make_shared<BCs>();
728 bc->tempBcPtr = boost::make_shared<TemperatureCubitBcData>();
729 CHKERR m->getBcDataStructure(*(bc->tempBcPtr));
732 <<
"Found block TEMPERATURESET id = " <<
m->getMeshsetId();
733 MOFEM_LOG(
"BcMngWorld", Sev::verbose) << *bc->tempBcPtr;
735 CHKERR prb_mng->modifyMarkDofs(
739 if (get_low_dim_ents) {
742 bc->bcEnts.swap(low_dim_ents);
748 bc->bcEnts, bc->bcMarkers);
750 const std::string bc_id =
751 problem_name +
"_" +
field_name +
"_TEMPERATURESET" +
752 boost::lexical_cast<std::string>(
m->getMeshsetId());
753 bcMapByBlockName[bc_id] = bc;
775 const std::string problem_name,
const std::string
field_name,
776 bool get_low_dim_ents,
bool block_name_field_prefix) {
781 if (block_name_field_prefix)
783 <<
"Argument block_name_field_prefix=true has no effect";
785 auto fix_disp = [&]() {
788 auto iterate_meshsets = [&](
auto &&meshset_vec_ptr) {
790 for (
auto m : meshset_vec_ptr) {
791 auto bc = boost::make_shared<BCs>();
794 bc->heatFluxBcPtr = boost::make_shared<HeatFluxCubitBcData>();
795 CHKERR m->getBcDataStructure(*(bc->heatFluxBcPtr));
797 CHKERR prb_mng->modifyMarkDofs(
802 <<
"Found block HEATFLUX id = " <<
m->getMeshsetId();
803 MOFEM_LOG(
"BcMngWorld", Sev::verbose) << *bc->heatFluxBcPtr;
805 if (get_low_dim_ents) {
808 bc->bcEnts.swap(low_dim_ents);
814 bc->bcEnts, bc->bcMarkers);
816 const std::string bc_id =
817 problem_name +
"_" +
field_name +
"_HEATFLUXSET" +
818 boost::lexical_cast<std::string>(
m->getMeshsetId());
819 bcMapByBlockName[bc_id] = bc;
841BcManager::pushMarkDOFsOnEntities<BcDisplacementMeshsetType<BLOCKSET>>(
842 const std::string problem_name,
const std::string
field_name,
843 bool get_low_dim_ents,
bool block_name_field_prefix) {
846 auto mark_dofs = [&](
const string block_name,
const int &idx_0,
849 if (block_name_field_prefix) {
850 const string field_block =
field_name +
"_" + block_name;
852 idx_0, idx_1, get_low_dim_ents);
856 idx_1, get_low_dim_ents);
862 CHKERR mark_dofs(
"FIX_X", 0, 0);
863 CHKERR mark_dofs(
"FIX_Y", 1, 1);
864 CHKERR mark_dofs(
"FIX_Z", 2, 2);
868 CHKERR mark_dofs(
"ROTATE_X", 1, 1);
869 CHKERR mark_dofs(
"ROTATE_X", 2, 2);
870 CHKERR mark_dofs(
"ROTATE_Y", 0, 0);
871 CHKERR mark_dofs(
"ROTATE_Y", 2, 2);
872 CHKERR mark_dofs(
"ROTATE_Z", 0, 0);
873 CHKERR mark_dofs(
"ROTATE_Z", 1, 1);
876 std::string regex_str;
877 if (block_name_field_prefix) {
878 regex_str = (boost::format(
"%s_%s_%s_(.*)") % problem_name %
field_name %
882 regex_str = (boost::format(
"%s_%s_(.*)") % problem_name %
field_name).str();
885 for (
auto &
m : bcMapByBlockName) {
886 auto &bc_id =
m.first;
887 if (std::regex_match(bc_id, std::regex(regex_str))) {
889 if (std::regex_match(bc_id, std::regex(
"(.*)_FIX_X(.*)"))) {
890 bc->dispBcPtr = boost::make_shared<DisplacementCubitBcData>();
891 bc->dispBcPtr->data.flag1 = 1;
892 if (bc->bcAttributes.empty()) {
893 bc->dispBcPtr->data.value1 = 0;
895 <<
"Expected one attribute on block but have "
896 << bc->bcAttributes.size();
897 }
else if (bc->bcAttributes.size() >= 1) {
898 bc->dispBcPtr->data.value1 = bc->bcAttributes[0];
900 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add X " << bc_id;
901 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *bc->dispBcPtr;
902 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_FIX_Y(.*)"))) {
903 bc->dispBcPtr = boost::make_shared<DisplacementCubitBcData>();
904 bc->dispBcPtr->data.flag2 = 1;
905 if (bc->bcAttributes.empty()) {
906 bc->dispBcPtr->data.value2 = 0;
908 <<
"Expected one attribute on block but have "
909 << bc->bcAttributes.size();
910 }
else if (bc->bcAttributes.size() == 1) {
911 bc->dispBcPtr->data.value2 = bc->bcAttributes[0];
912 }
else if (bc->bcAttributes.size() >= 2) {
913 bc->dispBcPtr->data.value2 = bc->bcAttributes[1];
915 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add Y " << bc_id;
916 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
917 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_FIX_Z(.*)"))) {
918 bc->dispBcPtr = boost::make_shared<DisplacementCubitBcData>();
919 bc->dispBcPtr->data.flag3 = 1;
920 if (bc->bcAttributes.empty()) {
921 bc->dispBcPtr->data.value3 = 0;
923 <<
"Expected one attribute on block but have "
924 << bc->bcAttributes.size();
925 }
else if (bc->bcAttributes.size() == 1) {
926 bc->dispBcPtr->data.value3 = bc->bcAttributes[0];
927 }
else if (bc->bcAttributes.size() == 3) {
928 bc->dispBcPtr->data.value3 = bc->bcAttributes[2];
930 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add Z " << bc_id;
931 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
932 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_FIX_ALL(.*)"))) {
933 bc->dispBcPtr = boost::make_shared<DisplacementCubitBcData>();
934 bc->dispBcPtr->data.flag1 = 1;
935 bc->dispBcPtr->data.flag2 = 1;
936 bc->dispBcPtr->data.flag3 = 1;
937 if (bc->bcAttributes.size() >= 1) {
938 bc->dispBcPtr->data.value1 = bc->bcAttributes[0];
940 if (bc->bcAttributes.size() >= 2) {
941 bc->dispBcPtr->data.value2 = bc->bcAttributes[1];
943 if (bc->bcAttributes.size() >= 3) {
944 bc->dispBcPtr->data.value3 = bc->bcAttributes[2];
946 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add ALL " << bc_id;
947 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
948 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_ROTATE_X(.*)"))) {
950 boost::make_shared<DisplacementCubitBcDataWithRotation>();
951 bc->dispBcPtr->data.flag4 = 1;
952 bc->dispBcPtr->data.flag5 = 0;
953 bc->dispBcPtr->data.flag6 = 0;
956 if (bc->bcAttributes.empty()) {
957 bc->dispBcPtr->data.value4 = 0;
959 <<
"Expected one attribute on block on block (angle (1 or 3), "
960 "center coords(3) but have "
961 << bc->bcAttributes.size();
962 }
else if (bc->bcAttributes.size() >= 1) {
963 bc->dispBcPtr->data.value4 = bc->bcAttributes[0];
965 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add X " << bc_id;
966 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *bc->dispBcPtr;
967 if (bc->bcAttributes.size() == 4 || bc->bcAttributes.size() == 6) {
968 if (
auto ext_disp_bc =
970 bc->dispBcPtr.get())) {
971 auto &
o = ext_disp_bc->rotOffset;
972 for (
int a = 0;
a != 3; ++
a)
973 o[
a] = bc->bcAttributes[bc->bcAttributes.size() - 3 +
a];
975 <<
"Add Rotate X Center: " <<
o[0] <<
" " <<
o[1] <<
" "
979 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_ROTATE_Y(.*)"))) {
981 boost::make_shared<DisplacementCubitBcDataWithRotation>();
982 bc->dispBcPtr->data.flag4 = 0;
983 bc->dispBcPtr->data.flag5 = 1;
984 bc->dispBcPtr->data.flag6 = 0;
987 if (bc->bcAttributes.empty()) {
988 bc->dispBcPtr->data.value5 = 0;
990 <<
"Expected one attribute on block on block (angle (1 or 3), "
991 "center coords(3) but have "
992 << bc->bcAttributes.size();
993 }
else if (bc->bcAttributes.size() == 1 ||
994 bc->bcAttributes.size() == 4) {
995 bc->dispBcPtr->data.value5 = bc->bcAttributes[0];
996 }
else if (bc->bcAttributes.size() == 6) {
997 bc->dispBcPtr->data.value5 = bc->bcAttributes[1];
999 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add Y " << bc_id;
1000 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
1001 if (bc->bcAttributes.size() == 4 || bc->bcAttributes.size() == 6) {
1002 if (
auto ext_disp_bc =
1004 bc->dispBcPtr.get())) {
1005 auto &
o = ext_disp_bc->rotOffset;
1006 for (
int a = 0;
a != 3; ++
a)
1007 o[
a] = bc->bcAttributes[bc->bcAttributes.size() - 3 +
a];
1009 <<
"Add Rotate Y Center: " <<
o[0] <<
" " <<
o[1] <<
" "
1013 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_ROTATE_Z(.*)"))) {
1015 boost::make_shared<DisplacementCubitBcDataWithRotation>();
1016 bc->dispBcPtr->data.flag4 = 0;
1017 bc->dispBcPtr->data.flag5 = 0;
1018 bc->dispBcPtr->data.flag6 = 1;
1021 if (bc->bcAttributes.empty()) {
1022 bc->dispBcPtr->data.value6 = 0;
1024 <<
"Expected one attribute on block (angle (1 or 3), center "
1025 "coords(3) but have "
1026 << bc->bcAttributes.size();
1027 }
else if (bc->bcAttributes.size() == 1 ||
1028 bc->bcAttributes.size() == 4) {
1029 bc->dispBcPtr->data.value6 = bc->bcAttributes[0];
1030 }
else if (bc->bcAttributes.size() == 3 ||
1031 bc->bcAttributes.size() == 6) {
1032 bc->dispBcPtr->data.value6 = bc->bcAttributes[2];
1034 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add Z " << bc_id;
1035 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
1036 if (bc->bcAttributes.size() == 4 || bc->bcAttributes.size() == 6) {
1037 if (
auto ext_disp_bc =
1039 bc->dispBcPtr.get())) {
1040 auto &
o = ext_disp_bc->rotOffset;
1041 for (
int a = 0;
a != 3; ++
a)
1042 o[
a] = bc->bcAttributes[bc->bcAttributes.size() - 3 +
a];
1044 <<
"Add Rotate Z Center: " <<
o[0] <<
" " <<
o[1] <<
" "
1048 }
else if (std::regex_match(bc_id, std::regex(
"(.*)_ROTATE_ALL(.*)"))) {
1050 boost::make_shared<DisplacementCubitBcDataWithRotation>();
1051 bc->dispBcPtr->data.flag4 = 1;
1052 bc->dispBcPtr->data.flag5 = 1;
1053 bc->dispBcPtr->data.flag6 = 1;
1054 if (bc->bcAttributes.size() >= 1) {
1055 bc->dispBcPtr->data.value4 = bc->bcAttributes[0];
1057 if (bc->bcAttributes.size() >= 2) {
1058 bc->dispBcPtr->data.value5 = bc->bcAttributes[1];
1060 if (bc->bcAttributes.size() >= 3) {
1061 bc->dispBcPtr->data.value6 = bc->bcAttributes[2];
1063 MOFEM_LOG(
"BcMngWorld", Sev::inform) <<
"Add ALL " << bc_id;
1064 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *(bc->dispBcPtr);
1065 if (bc->bcAttributes.size() > 3) {
1066 if (
auto ext_disp_bc =
1068 bc->dispBcPtr.get())) {
1069 auto &
o = ext_disp_bc->rotOffset;
1070 for (
int a = 0;
a != 3; ++
a)
1071 o[
a] = bc->bcAttributes[3 +
a];
1073 <<
"Add Rotate ALL Center: " <<
o[0] <<
" " <<
o[1] <<
" "
1086 const std::string problem_name,
const std::string block_name,
1087 const std::string
field_name,
bool get_low_dim_ents) {
1094 (boost::format(
"%s_%s_%s(.*)") % problem_name %
field_name % block_name)
1097 for (
auto &
m : bcMapByBlockName) {
1099 auto &bc_id =
m.first;
1101 if (std::regex_match(bc_id, std::regex(regex_str))) {
1103 auto &bc =
m.second;
1104 bc->tempBcPtr = boost::make_shared<TemperatureCubitBcData>();
1105 bc->tempBcPtr->data.flag1 = 1;
1106 if (bc->bcAttributes.empty()) {
1107 bc->tempBcPtr->data.value1 = 0;
1109 <<
"Expected one attribute on block but have "
1110 << bc->bcAttributes.size();
1111 }
else if (bc->bcAttributes.size() >= 1) {
1112 bc->tempBcPtr->data.value1 = bc->bcAttributes[0];
1122 const std::string problem_name,
const std::string
field_name,
1123 bool get_low_dim_ents,
bool block_name_field_prefix) {
1126 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<DISPLACEMENTSET>>(
1127 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1129 CHKERR pushMarkDOFsOnEntities<BcDisplacementMeshsetType<BLOCKSET>>(
1130 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1136 const std::string problem_name,
const std::string
field_name,
1137 bool get_low_dim_ents,
bool block_name_field_prefix,
1138 bool is_distributed_mesh) {
1141 CHKERR removeBlockDOFsOnEntities<BcMeshsetType<DISPLACEMENTSET>>(
1142 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1143 is_distributed_mesh);
1145 CHKERR removeBlockDOFsOnEntities<BcDisplacementMeshsetType<BLOCKSET>>(
1146 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1147 is_distributed_mesh);
1154 const std::string problem_name,
const std::string
field_name,
1155 bool get_low_dim_ents,
bool block_name_field_prefix) {
1157 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<TEMPERATURESET>>(
1158 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1160 auto get_block_name = [&]() {
1161 if (block_name_field_prefix)
1162 return (boost::format(
"%s_FIX_SCALAR") %
field_name).str();
1167 CHKERR pushMarkDOFsOnEntities<BcScalarMeshsetType<BLOCKSET>>(
1168 problem_name, get_block_name(),
field_name, get_low_dim_ents);
1174 const std::string problem_name,
const std::string
field_name,
1175 bool get_low_dim_ents,
bool block_name_field_prefix,
1176 bool is_distributed_mesh) {
1178 CHKERR removeBlockDOFsOnEntities<BcMeshsetType<TEMPERATURESET>>(
1179 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1180 is_distributed_mesh);
1182 auto get_block_name = [&]() {
1183 if (block_name_field_prefix)
1184 return (boost::format(
"%s_FIX_SCALAR") %
field_name).str();
1189 CHKERR removeBlockDOFsOnEntities<BcScalarMeshsetType<BLOCKSET>>(
1190 problem_name, get_block_name(),
field_name, get_low_dim_ents,
1191 is_distributed_mesh);
1197 const std::string problem_name,
const std::string
field_name,
1198 bool get_low_dim_ents,
bool block_name_field_prefix) {
1200 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<HEATFLUXSET>>(
1201 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1207 const std::string problem_name,
const std::string
field_name,
1208 bool get_low_dim_ents,
bool block_name_field_prefix,
1209 bool is_distributed_mesh) {
1211 CHKERR removeBlockDOFsOnEntities<BcMeshsetType<HEATFLUXSET>>(
1212 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1213 is_distributed_mesh);
1217std::pair<std::string, std::string>
1219 const std::string prb_name) {
1223 auto field_rgx_str =
1224 (boost::format(
"%s_([a-zA-Z0-9]*)_(.*)") % prb_name).str();
1225 std::regex field_rgx(field_rgx_str);
1226 std::smatch match_field_name;
1228 std::string block_name;
1230 if (std::regex_search(block_id, match_field_name, field_rgx)) {
1232 block_name = match_field_name[2];
1235 "Field name and block name can not be resolved");
1238 return std::make_pair(
field_name, block_name);
1243 const std::string problem_name,
const std::string
field_name,
1244 bool get_low_dim_ents,
bool block_name_field_prefix) {
1249 if (problem_name.empty())
1250 MOFEM_LOG(
"BcMngWorld", Sev::warning) <<
"Argument problem_name is empty";
1252 if (block_name_field_prefix)
1254 <<
"Argument block_name_field_prefix=true has no effect";
1256 auto fix_force = [&]() {
1259 auto iterate_meshsets = [&](
auto &&meshset_vec_ptr) {
1261 for (
auto m : meshset_vec_ptr) {
1262 auto bc = boost::make_shared<BCs>();
1265 bc->forceBcPtr = boost::make_shared<ForceCubitBcData>();
1266 CHKERR m->getBcDataStructure(*(bc->forceBcPtr));
1269 <<
"Found block FORCESET id = " <<
m->getMeshsetId();
1270 MOFEM_LOG(
"BcMngWorld", Sev::verbose) << *bc->forceBcPtr;
1273 <<
"Found block FORCESET id = " <<
m->getMeshsetId()
1274 <<
" nb. of entities " << bc->bcEnts.size()
1275 <<
" highest dim of entities "
1277 MOFEM_LOG(
"BcMngSync", Sev::noisy) << *bc->forceBcPtr;
1280 if (problem_name.size()) {
1282 if (bc->forceBcPtr->data.value2 > 0)
1286 if (bc->forceBcPtr->data.value3 > 0)
1290 if (bc->forceBcPtr->data.value4 > 0)
1295 if (bc->forceBcPtr->data.value5 > 0) {
1304 if (bc->forceBcPtr->data.value5) {
1313 if (bc->forceBcPtr->data.value6) {
1324 if (get_low_dim_ents) {
1327 bc->bcEnts.swap(low_dim_ents);
1332 if (problem_name.size())
1334 bc->bcEnts, bc->bcMarkers);
1336 const std::string bc_id =
1337 problem_name +
"_" +
field_name +
"_FORCESET" +
1338 boost::lexical_cast<std::string>(
m->getMeshsetId());
1339 bcMapByBlockName[bc_id] = bc;
1361 const std::string problem_name,
const std::string
field_name,
1362 bool get_low_dim_ents,
bool block_name_field_prefix) {
1367 if (problem_name.size() == 0)
1368 MOFEM_LOG(
"BcMngWorld", Sev::warning) <<
"Argument problem_name is empty";
1370 auto get_force_block = [&](
auto block_name) {
1376 (boost::format(
"%s(.*)") % block_name).str()
1382 const auto block_name =
m->getName();
1385 <<
"Found force block " << block_name;
1387 auto bc = boost::make_shared<BCs>();
1391 CHKERR m->getAttributes(bc->bcAttributes);
1392 if (bc->bcAttributes.size() != 3) {
1394 "Expect three block attributes for force block");
1397 bc->forceBcPtr = boost::make_shared<ForceCubitBcData>();
1399 bc->forceBcPtr->data.value1 = 1;
1400 bc->forceBcPtr->data.value3 = bc->bcAttributes[0];
1401 bc->forceBcPtr->data.value4 = bc->bcAttributes[1];
1402 bc->forceBcPtr->data.value5 = bc->bcAttributes[2];
1404 MOFEM_LOG(
"BcMngWorld", Sev::inform) << *bc->forceBcPtr;
1406 <<
"Found block FORCESET id = " <<
m->getMeshsetId()
1407 <<
" nb. of entities " << bc->bcEnts.size()
1408 <<
" highest dim of entities "
1410 MOFEM_LOG(
"BcMngSync", Sev::noisy) << *bc->forceBcPtr;
1413 if (problem_name.size()) {
1415 if (bc->forceBcPtr->data.value2 > 0)
1419 if (bc->forceBcPtr->data.value3 > 0)
1423 if (bc->forceBcPtr->data.value4 > 0)
1429 if (get_low_dim_ents) {
1432 bc->bcEnts.swap(low_dim_ents);
1437 if (problem_name.size())
1439 bc->bcEnts, bc->bcMarkers);
1441 const std::string bc_id =
1442 problem_name +
"_" +
field_name +
"_" + block_name;
1443 bcMapByBlockName[bc_id] = bc;
1448 CHKERR get_force_block(
"FORCE");
1455 const std::string problem_name,
const std::string
field_name,
1456 bool get_low_dim_ents,
bool block_name_field_prefix) {
1459 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<FORCESET>>(
1460 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1462 CHKERR pushMarkDOFsOnEntities<BcForceMeshsetType<BLOCKSET>>(
1463 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix);
1470 const std::string problem_name,
const std::string
field_name,
1471 bool get_low_dim_ents,
bool block_name_field_prefix,
1472 bool is_distributed_mesh) {
1477 CHKERR pushMarkDOFsOnEntities<BcMeshsetType<FORCESET>>(
1480 std::array<Range, 3> ents_to_remove;
1487 const auto block_name =
m->getName();
1488 std::string bc_id = problem_name +
"_" +
field_name +
"_" + block_name;
1490 auto str = boost::format(
"%s_%s_%s(.*)")
1494 if (std::regex_match(bc_id, std::regex(str.str()))) {
1496 auto bc = bcMapByBlockName.at(bc_id);
1498 if (
auto force_bc = bc->forceBcPtr) {
1499 if (force_bc->data.value3 > 0) {
1500 ents_to_remove[0].merge(bc->bcEnts);
1502 if (force_bc->data.value4 > 0) {
1503 ents_to_remove[1].merge(bc->bcEnts);
1505 if (force_bc->data.value5 > 0) {
1506 ents_to_remove[2].merge(bc->bcEnts);
1510 "BC type not implemented");
1515 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
1517 if (is_distributed_mesh)
1518 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
1521 return prb_mng->removeDofsOnEntitiesNotDistributed(
1525 CHKERR remove_dofs_on_ents(ents_to_remove[0], 0, 0);
1526 CHKERR remove_dofs_on_ents(ents_to_remove[1], 1, 1);
1527 CHKERR remove_dofs_on_ents(ents_to_remove[2], 2, 2);
1534BcManager::removeBlockDOFsOnEntities<BcForceMeshsetType<BLOCKSET>>(
1535 const std::string problem_name,
const std::string
field_name,
1536 bool get_low_dim_ents,
bool block_name_field_prefix,
1537 bool is_distributed_mesh) {
1542 CHKERR pushMarkDOFsOnEntities<BcForceMeshsetType<BLOCKSET>>(
1545 std::array<Range, 3> ents_to_remove;
1552 const auto block_name =
m->getName();
1553 std::string bc_id = problem_name +
"_" +
field_name +
"_" + block_name;
1555 auto str = boost::format(
"%s_%s_%s(.*)")
1559 if (std::regex_match(bc_id, std::regex(str.str()))) {
1561 auto bc = bcMapByBlockName.at(bc_id);
1563 if (
auto force_bc = bc->forceBcPtr) {
1564 if (force_bc->data.value3 > 0) {
1565 ents_to_remove[0].merge(bc->bcEnts);
1567 if (force_bc->data.value4 > 0) {
1568 ents_to_remove[1].merge(bc->bcEnts);
1570 if (force_bc->data.value5 > 0) {
1571 ents_to_remove[2].merge(bc->bcEnts);
1575 "BC type not implemented");
1580 auto remove_dofs_on_ents = [&](
const Range &ents,
const int lo,
1582 if (is_distributed_mesh)
1583 return prb_mng->removeDofsOnEntities(problem_name,
field_name, ents, lo,
1586 return prb_mng->removeDofsOnEntitiesNotDistributed(
1590 CHKERR remove_dofs_on_ents(ents_to_remove[0], 0, 0);
1591 CHKERR remove_dofs_on_ents(ents_to_remove[1], 1, 1);
1592 CHKERR remove_dofs_on_ents(ents_to_remove[2], 2, 2);
1599 const std::string problem_name,
const std::string
field_name,
1600 bool get_low_dim_ents,
bool block_name_field_prefix,
1601 bool is_distributed_mesh) {
1604 CHKERR removeBlockDOFsOnEntities<BcMeshsetType<FORCESET>>(
1605 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1606 is_distributed_mesh);
1608 CHKERR removeBlockDOFsOnEntities<BcForceMeshsetType<BLOCKSET>>(
1609 problem_name,
field_name, get_low_dim_ents, block_name_field_prefix,
1610 is_distributed_mesh);
#define MOFEM_LOG_SEVERITY_SYNC(comm, severity)
Synchronise "SYNC" on curtain severity level.
#define MAX_DOFS_ON_ENTITY
Maximal number of DOFs on entity.
#define CHK_THROW_MESSAGE(err, msg)
Check and throw MoFEM exception.
#define MoFEMFunctionReturnHot(a)
Last executable line of each PETSc function used for error handling. Replaces return()
#define MoFEMFunctionBegin
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
#define CHKERRG(n)
Check error code of MoFEM/MOAB/PETSc function.
#define CHK_MOAB_THROW(err, msg)
Check error code of MoAB function and throw MoFEM exception.
@ MOFEM_DATA_INCONSISTENCY
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
#define CHKERR
Inline error check.
#define MoFEMFunctionBeginHot
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
FTensor::Index< 'm', SPACE_DIM > m
static LoggerType & setLog(const std::string channel)
Set ans resset chanel logger.
#define MOFEM_LOG(channel, severity)
Log.
#define MOFEM_LOG_TAG(channel, tag)
Tag channel.
MoFEMErrorCode getCubitMeshsetPtr(const int ms_id, const CubitBCType cubit_bc_type, const CubitMeshSets **cubit_meshset_ptr) const
get cubit meshset
FTensor::Index< 'i', SPACE_DIM > i
static MoFEMErrorCodeGeneric< PetscErrorCode > ierr
PetscErrorCode MoFEMErrorCode
MoFEM/PETSc error code.
implementation of Data Operators for Forces and Sources
constexpr auto field_name
Simple interface for fast problem set-up.
Range getMergedBlocksRange(std::vector< std::regex > bc_regex_vec)
Merge block ranges.
boost::shared_ptr< std::vector< char unsigned > > BcMarkerPtr
MoFEMErrorCode getOptions()
get options
BcMarkerPtr getMergedBlocksMarker(std::vector< std::regex > bc_regex_vec)
Get the Merged Boundary Marker object.
static std::pair< std::string, std::string > extractStringFromBlockId(const std::string block_id, const std::string prb_name)
Extract block name and block name form block id.
BcMapByBlockName bcMapByBlockName
SmartPetscObj< IS > getBlockIS(const std::string block_prefix, const std::string block_name, const std::string field_name, const std::string problem_name, int lo, int hi, SmartPetscObj< IS > is_expand=SmartPetscObj< IS >())
Get block IS.
MoFEMErrorCode removeBlockDOFsOnEntities(const std::string problem_name, const std::string block_name, const std::string field_name, int lo, int hi, bool get_low_dim_ents=true, bool is_distributed_mesh=true)
Remove DOFs from problem.
BcManager(const MoFEM::Core &core)
MoFEMErrorCode query_interface(boost::typeindex::type_index type_index, UnknownInterface **iface) const
boost::shared_ptr< BCs > popMarkDOFsOnEntities(const std::string block_name)
Get bc data and remove element.
MoFEMErrorCode pushMarkDOFsOnEntities(const std::string problem_name, const std::string block_name, const std::string field_name, int lo, int hi, bool get_low_dim_ents=true)
Mark block DOFs.
BcMapByBlockName & getBcMapByBlockName()
Get the bc map.
virtual moab::Interface & get_moab()=0
virtual MPI_Comm & get_comm() const =0
Deprecated interface functions.
A specialized version of DisplacementCubitBcData that includes an additional rotation offset.
Section manager is used to create indexes and sections.
static boost::shared_ptr< SinkType > createSink(boost::shared_ptr< std::ostream > stream_ptr, std::string comm_filter)
Create a sink object.
static boost::shared_ptr< std::ostream > getStrmWorld()
Get the strm world object.
static boost::shared_ptr< std::ostream > getStrmSync()
Get the strm sync object.
static bool checkIfChannelExist(const std::string channel)
Check if channel exist.
static boost::shared_ptr< std::ostream > getStrmSelf()
Get the strm self object.
Interface for managing meshsets containing materials and boundary conditions.
Problem manager is used to build and partition problems.
intrusive_ptr for managing petsc objects
base class for all interface classes
MoFEMErrorCode getInterface(IFACE *&iface) const
Get interface refernce to pointer of interface.