16static char help[] =
"...\n\n";
21 ? AssemblyType::BLOCK_MAT
29 IntegrationType::GAUSS;
45 static boost::shared_ptr<SetUpSchur>
57int main(
int argc,
char *argv[]) {
64 DMType dm_name =
"DMMOFEM";
66 DMType dm_name_mg =
"DMMOFEM_MG";
70 moab::Core mb_instance;
71 moab::Interface &moab = mb_instance;
74 auto core_log = logging::core::get();
90 simple->getAddBoundaryFE() =
true;
93 auto add_shared_entities_on_skeleton = [&]() {
95 auto boundary_meshset =
simple->getBoundaryMeshSet();
96 auto skeleton_meshset =
simple->getSkeletonMeshSet();
102 0,
simple->getDim() - 1, skeleton_ents,
true);
103 skeleton_ents = subtract(skeleton_ents, bdy_ents);
105 CHKERR m_field.
get_moab().add_entities(skeleton_meshset, skeleton_ents);
109 CHKERR add_shared_entities_on_skeleton();
119 const char *list_bases[] = {
"ainsworth",
"ainsworth_lobatto",
"demkowicz",
122 PetscInt choice_base_value = AINSWORTH;
124 LASBASETOP, &choice_base_value, &flg);
126 if (flg != PETSC_TRUE)
129 if (choice_base_value == AINSWORTH)
131 if (choice_base_value == AINSWORTH_LOBATTO)
133 else if (choice_base_value == DEMKOWICZ)
135 else if (choice_base_value == BERNSTEIN)
138 enum spaces { hdiv, hcurl, last_space };
139 const char *list_spaces[] = {
"hdiv",
"hcurl"};
140 PetscInt choice_space_value = hdiv;
142 last_space, &choice_space_value, &flg);
143 if (flg != PETSC_TRUE)
146 if (choice_space_value == hdiv)
148 else if (choice_space_value == hcurl)
154 CHKERR simple->addDomainBrokenField(
"BROKEN", space, base, 1);
178 auto assemble_domain_lhs = [&](
auto &pip) {
185 IT>::OpMixDivTimesScalar<SPACE_DIM>;
191 pip.push_back(
new OpHdivHdiv(
"BROKEN",
"BROKEN", beta));
192 auto unity = []()
constexpr {
return 1; };
193 pip.push_back(
new OpHdivU(
"BROKEN",
"U", unity,
true));
201 op_loop_skeleton_side->getOpPtrVector(), {});
205 auto broken_data_ptr =
206 boost::make_shared<std::vector<BrokenBaseSideData>>();
211 op_loop_domain_side->getOpPtrVector(), {HDIV});
212 op_loop_domain_side->getOpPtrVector().push_back(
215 op_loop_skeleton_side->getOpPtrVector().push_back(op_loop_domain_side);
217 IT>::OpBrokenSpaceConstrain<1>;
218 op_loop_skeleton_side->getOpPtrVector().push_back(
219 new OpC(
"HYBRID", broken_data_ptr, 1.,
true,
false));
223 constexpr int partition = 1;
225 op_print->doWorkRhsHook = [&](
DataOperator *base_op_ptr,
int side,
229 if (
auto op_ptr =
dynamic_cast<BdyEleOp *
>(base_op_ptr)) {
230 auto fe_method = op_ptr->getFEMethod();
231 auto num_fe = fe_method->numeredEntFiniteElementPtr;
234 if (num_fe->getPStatus() & PSTATUS_SHARED)
235 MOFEM_LOG(
"SELF", Sev::inform) <<
"Num FE: " << *num_fe;
240 op_loop_skeleton_side->getOpPtrVector().push_back(op_print);
243 pip.push_back(op_loop_skeleton_side);
248 auto assemble_domain_rhs = [&](
auto &pip) {
253 auto source = [&](
const double x,
const double y,
254 const double z)
constexpr {
263 CHKERR assemble_domain_lhs(pip_mng->getOpDomainLhsPipeline());
264 CHKERR assemble_domain_rhs(pip_mng->getOpDomainRhsPipeline());
271 TetPolynomialBase::switchCacheBaseOn<HDIV>(
272 {pip_mng->getDomainLhsFE().get(), pip_mng->getDomainRhsFE().get()});
273 TetPolynomialBase::switchCacheBaseOn<L2>(
274 {pip_mng->getDomainLhsFE().get(), pip_mng->getDomainRhsFE().get()});
278 "pipeline_manager_graph.dot", pip_mng);
284 auto ksp = pip_mng->createKSP();
286 CHKERR KSPSetFromOptions(ksp);
287 BOOST_LOG_SCOPED_THREAD_ATTR(
"Timeline", attrs::timer());
288 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSetUp";
290 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSetUp <= Done";
292 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSolve";
293 CHKERR KSPSolve(ksp, f, x);
294 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSolve <= Done";
296 CHKERR VecGhostUpdateBegin(x, INSERT_VALUES, SCATTER_FORWARD);
297 CHKERR VecGhostUpdateEnd(x, INSERT_VALUES, SCATTER_FORWARD);
303 CHKERR KSPGetDM(ksp, &dm);
309 auto ksp = pip_mng->createKSP();
311 BOOST_LOG_SCOPED_THREAD_ATTR(
"Timeline", attrs::timer());
312 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSetUp";
313 CHKERR schur_ptr->setUp(ksp);
314 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSetUp <= Done";
316 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSolve";
317 CHKERR KSPSolve(ksp, f, x);
318 MOFEM_LOG(
"TIMER", Sev::inform) <<
"KSPSolve <= Done";
320 CHKERR VecGhostUpdateBegin(x, INSERT_VALUES, SCATTER_FORWARD);
321 CHKERR VecGhostUpdateEnd(x, INSERT_VALUES, SCATTER_FORWARD);
327 CHKERR KSPGetDM(ksp, &dm);
334 auto check_residual = [&](
auto x,
auto f) {
340 auto &domain_rhs = pip_mng->getOpDomainRhsPipeline();
346 auto div_flux_ptr = boost::make_shared<VectorDouble>();
348 "BROKEN", div_flux_ptr));
352 domain_rhs.push_back(
new OpUDivFlux(
"U", div_flux_ptr, beta));
353 auto source = [&](
const double x,
const double y,
354 const double z)
constexpr {
return 1; };
360 IT>::OpMixDivTimesU<3, 1, SPACE_DIM>;
363 auto flux_ptr = boost::make_shared<MatrixDouble>();
364 domain_rhs.push_back(
366 boost::shared_ptr<VectorDouble> u_ptr =
367 boost::make_shared<VectorDouble>();
369 domain_rhs.push_back(
new OpHDivH(
"BROKEN", u_ptr, beta));
370 domain_rhs.push_back(
new OpHdivFlux(
"BROKEN", flux_ptr, beta));
378 op_loop_skeleton_side->getOpPtrVector(), {});
382 auto broken_data_ptr =
383 boost::make_shared<std::vector<BrokenBaseSideData>>();
388 op_loop_domain_side->getOpPtrVector(), {HDIV});
389 op_loop_domain_side->getOpPtrVector().push_back(
391 auto flux_mat_ptr = boost::make_shared<MatrixDouble>();
392 op_loop_domain_side->getOpPtrVector().push_back(
394 op_loop_domain_side->getOpPtrVector().push_back(
398 op_loop_skeleton_side->getOpPtrVector().push_back(op_loop_domain_side);
400 IT>::OpBrokenSpaceConstrainDHybrid<1>;
402 IT>::OpBrokenSpaceConstrainDFlux<1>;
403 op_loop_skeleton_side->getOpPtrVector().push_back(
404 new OpC_dHybrid(
"HYBRID", broken_data_ptr, 1.));
405 auto hybrid_ptr = boost::make_shared<MatrixDouble>();
406 op_loop_skeleton_side->getOpPtrVector().push_back(
408 op_loop_skeleton_side->getOpPtrVector().push_back(
409 new OpC_dBroken(broken_data_ptr, hybrid_ptr, 1.));
412 domain_rhs.push_back(op_loop_skeleton_side);
415 CHKERR VecGhostUpdateBegin(f, INSERT_VALUES, SCATTER_FORWARD);
416 CHKERR VecGhostUpdateEnd(f, INSERT_VALUES, SCATTER_FORWARD);
418 pip_mng->getDomainRhsFE()->f = f;
419 pip_mng->getSkeletonRhsFE()->f = f;
420 pip_mng->getDomainRhsFE()->x = x;
421 pip_mng->getSkeletonRhsFE()->x = x;
424 simple->getDomainFEName(),
425 pip_mng->getDomainRhsFE());
427 CHKERR VecGhostUpdateBegin(f, ADD_VALUES, SCATTER_REVERSE);
428 CHKERR VecGhostUpdateEnd(f, ADD_VALUES, SCATTER_REVERSE);
429 CHKERR VecAssemblyBegin(f);
433 CHKERR VecNorm(f, NORM_2, &fnrm);
434 MOFEM_LOG_C(
"AT", Sev::inform,
"Residual %3.4e", fnrm);
436 constexpr double eps = 1e-8;
439 "Residual norm larger than accepted");
442 "domain_rhs_graph.dot",
"OpDomainRhsPipeline",
443 pip_mng->getOpDomainRhsPipeline());
448 auto calculate_error = [&]() {
452 auto &domain_rhs = pip_mng->getOpDomainRhsPipeline();
458 auto u_grad_ptr = boost::make_shared<MatrixDouble>();
459 auto flux_val_ptr = boost::make_shared<MatrixDouble>();
460 auto div_val_ptr = boost::make_shared<VectorDouble>();
461 auto source_ptr = boost::make_shared<VectorDouble>();
463 domain_rhs.push_back(
465 domain_rhs.push_back(
468 "BROKEN", div_val_ptr));
469 auto source = [&](
const double x,
const double y,
470 const double z)
constexpr {
return -1; };
473 enum { DIV, GRAD, LAST };
476 domain_rhs.push_back(
479 u_grad_ptr, mpi_vec, GRAD, flux_val_ptr));
482 simple->getDomainFEName(),
483 pip_mng->getDomainRhsFE());
484 CHKERR VecAssemblyBegin(mpi_vec);
485 CHKERR VecAssemblyEnd(mpi_vec);
488 const double *error_ind;
489 CHKERR VecGetArrayRead(mpi_vec, &error_ind);
491 <<
"Approximation error ||div flux - source||: "
492 << std::sqrt(error_ind[DIV]);
493 MOFEM_LOG(
"AT", Sev::inform) <<
"Approximation error ||grad-flux||: "
494 << std::sqrt(error_ind[GRAD]);
495 CHKERR VecRestoreArrayRead(mpi_vec, &error_ind);
501 auto get_post_proc_fe = [&]() {
504 auto post_proc_fe = boost::make_shared<PostProcEle>(m_field);
510 post_proc_fe->getOpPtrVector().push_back(op_loop_side);
513 op_loop_side->getOpPtrVector(), {HDIV});
514 auto u_vec_ptr = boost::make_shared<VectorDouble>();
515 auto flux_mat_ptr = boost::make_shared<MatrixDouble>();
516 op_loop_side->getOpPtrVector().push_back(
518 op_loop_side->getOpPtrVector().push_back(
520 op_loop_side->getOpPtrVector().push_back(
524 post_proc_fe->getPostProcMesh(),
526 post_proc_fe->getMapGaussPts(),
530 {{
"BROKEN", flux_mat_ptr}},
539 auto post_proc_fe = get_post_proc_fe();
541 simple->getBoundaryFEName(), post_proc_fe);
542 CHKERR post_proc_fe->writeFile(
"out_result.h5m");
545 CHKERR check_residual(x, f);
570 CHKERR KSPSetFromOptions(ksp);
572 CHKERR KSPGetPC(ksp, &pc);
574 PetscBool is_pcfs = PETSC_FALSE;
575 PetscObjectTypeCompare((PetscObject)pc, PCFIELDSPLIT, &is_pcfs);
578 MOFEM_LOG(
"AT", Sev::inform) <<
"Setup Schur pc";
580 auto create_sub_dm = [&]() {
583 auto create_dm = [&](
585 std::string problem_name,
586 std::vector<std::string> fe_names,
587 std::vector<std::string> fields,
593 auto create_dm_imp = [&]() {
597 for (
auto fe : fe_names) {
601 for (
auto field : fields) {
610 "Error in creating schurDM. It is possible that schurDM is "
615 auto schur_dm = create_dm(
619 {
simple->getDomainFEName(),
simple->getSkeletonFEName()},
625 auto block_dm = create_dm(
629 {
simple->getDomainFEName(),
simple->getSkeletonFEName()},
635 return std::make_tuple(schur_dm, block_dm);
638 auto get_nested_mat_data = [&](
auto schur_dm,
auto block_dm) {
646 simple->getDomainFEName(),
650 {
"BROKEN",
"BROKEN"},
661 simple->getSkeletonFEName(),
665 {
"BROKEN",
"HYBRID"}, {
"HYBRID",
"BROKEN"}
677 {schur_dm, block_dm}, block_mat_data,
679 {
"BROKEN",
"U"}, {
nullptr,
nullptr}, true
684 auto set_ops = [&](
auto schur_dm) {
689 boost::shared_ptr<BlockStructure> block_data;
693 pip_mng->getOpDomainLhsPipeline().push_front(
695 pip_mng->getOpDomainLhsPipeline().push_back(
703 auto pre_proc_schur_lhs_ptr = boost::make_shared<FEMethod>();
704 auto post_proc_schur_lhs_ptr = boost::make_shared<FEMethod>();
706 pre_proc_schur_lhs_ptr->preProcessHook = [
this]() {
709 MOFEM_LOG(
"AT", Sev::verbose) <<
"Lhs Assemble Begin";
713 post_proc_schur_lhs_ptr->postProcessHook = [
this, ao_up,
714 post_proc_schur_lhs_ptr]() {
716 MOFEM_LOG(
"AT", Sev::verbose) <<
"Lhs Assemble End";
719 CHKERR MatAssemblyBegin(S, MAT_FINAL_ASSEMBLY);
720 CHKERR MatAssemblyEnd(S, MAT_FINAL_ASSEMBLY);
722 auto S_from_block =
matDuplicate(S, MAT_SHARE_NONZERO_PATTERN);
725 S_from_block, {
"BROKEN",
"U"},
726 {nullptr, nullptr}, ao_up);
727 CHKERR MatAssemblyBegin(S_from_block, MAT_FINAL_ASSEMBLY);
728 CHKERR MatAssemblyEnd(S_from_block, MAT_FINAL_ASSEMBLY);
729 CHKERR MatAYPX(S_from_block, -1, S, DIFFERENT_NONZERO_PATTERN);
731 CHKERR MatNorm(S_from_block, NORM_FROBENIUS, &norm);
732 MOFEM_LOG(
"AT", Sev::inform) <<
"Norm of difference: " << norm;
736 "Norm of difference between Schur and block matrix is larger "
741 {
"BROKEN",
"U"}, {nullptr, nullptr}, ao_up);
742 CHKERR MatAssemblyBegin(S, MAT_FINAL_ASSEMBLY);
743 CHKERR MatAssemblyEnd(S, MAT_FINAL_ASSEMBLY);
746 MOFEM_LOG(
"AT", Sev::verbose) <<
"Lhs Assemble Finish";
751 ksp_ctx_ptr->getPreProcSetOperators().push_front(pre_proc_schur_lhs_ptr);
752 ksp_ctx_ptr->getPostProcSetOperators().push_back(post_proc_schur_lhs_ptr);
757 auto set_pc = [&](
auto pc,
auto block_dm) {
759 auto block_is =
getDMSubData(block_dm)->getSmartRowIs();
760 CHKERR PCFieldSplitSetIS(pc, NULL, block_is);
761 CHKERR PCFieldSplitSetSchurPre(pc, PC_FIELDSPLIT_SCHUR_PRE_USER, S);
767 auto [schur_dm, block_dm] = create_sub_dm();
769 auto nested_mat_data = get_nested_mat_data(schur_dm, block_dm);
773 CHKERR MatSetDM(S, PETSC_NULLPTR);
777 CHKERR MatSetBlockSize(S, bs);
780 CHKERR set_pc(pc, block_dm);
782 CHKERR KSPGetDM(ksp, &solver_dm);
784 CHKERR DMSetMatType(solver_dm, MATSHELL);
786 auto get_pc = [](
auto ksp) {
788 CHKERR KSPGetPC(ksp, &pc_raw);
792 auto set_diagonal_pc = [&](
auto pc) {
798 CHKERR PCSetOperators(pc, A, P);
802 CHKERR PCFieldSplitSchurGetSubKSP(pc, PETSC_NULLPTR, &subksp);
809 auto set_mg_for_schur_complement = [&](
auto pc,
auto schur_dm,
auto S) {
813 CHKERR PCFieldSplitSchurGetSubKSP(pc, PETSC_NULLPTR, &subksp);
814 auto subpc = get_pc(subksp[1]);
816 auto set_pc_p_mg = [](
auto dm,
auto pc,
auto S) {
819 PetscBool same = PETSC_FALSE;
820 PetscObjectTypeCompare((PetscObject)pc, PCMG, &same);
822 MOFEM_LOG(
"TIMER", Sev::inform) <<
"Set up MG";
825 CHKERR PCSetFromOptions(pc);
830 PetscBool same = PETSC_FALSE;
831 PetscObjectTypeCompare((PetscObject)subpc, PCKSP, &same);
833 CHKERR PCSetFromOptions(subpc);
835 CHKERR PCKSPGetKSP(subpc, &inner_ksp);
836 CHKERR KSPSetFromOptions(inner_ksp);
838 CHKERR KSPGetPC(inner_ksp, &inner_pc);
839 CHKERR PCSetFromOptions(inner_pc);
840 CHKERR set_pc_p_mg(schur_dm, inner_pc, S);
849 CHKERR set_diagonal_pc(pc);
850 CHKERR set_mg_for_schur_complement(pc, schur_dm, S);
855 "PC is not set to PCFIELDSPLIT");
860boost::shared_ptr<SetUpSchur>
862 return boost::shared_ptr<SetUpSchur>(
new SetUpSchurImpl(m_field));
#define MOFEM_LOG_C(channel, severity, format,...)
void simple(double P1[], double P2[], double P3[], double c[], const int N)
FormsIntegrators< DomainEleOp >::Assembly< PETSC >::LinearForm< GAUSS >::OpSource< 1, FIELD_DIM > OpDomainSource
ElementsAndOps< SPACE_DIM >::DomainEle DomainEle
ElementsAndOps< SPACE_DIM >::BoundaryEle BoundaryEle
#define CATCH_ERRORS
Catch errors.
FieldApproximationBase
approximation base
@ AINSWORTH_LEGENDRE_BASE
Ainsworth Cole (Legendre) approx. base .
@ AINSWORTH_BERNSTEIN_BEZIER_BASE
#define CHK_THROW_MESSAGE(err, msg)
Check and throw MoFEM exception.
FieldSpace
approximation spaces
@ L2
field with C-1 continuity
@ HCURL
field with continuous tangents
@ HDIV
field with continuous normal traction
#define MoFEMFunctionBegin
First executable line of each MoFEM function, used for error handling. Final line of MoFEM functions ...
@ MOFEM_ATOM_TEST_INVALID
#define MoFEMFunctionReturn(a)
Last executable line of each PETSc function used for error handling. Replaces return()
#define CHKERR
Inline error check.
PetscErrorCode DMMoFEMCreateSubDM(DM subdm, DM dm, const char problem_name[])
Must be called by user to set Sub DM MoFEM data structures.
PetscErrorCode DMMoFEMAddElement(DM dm, std::string fe_name)
add element to dm
PetscErrorCode DMMoFEMSetSquareProblem(DM dm, PetscBool square_problem)
set squared problem
PetscErrorCode DMMoFEMAddSubFieldRow(DM dm, const char field_name[])
PetscErrorCode DMoFEMMeshToLocalVector(DM dm, Vec l, InsertMode mode, ScatterMode scatter_mode, RowColData rc=RowColData::COL)
set local (or ghosted) vector values on mesh for partition only
PetscErrorCode DMRegister_MoFEM(const char sname[])
Register MoFEM problem.
MoFEMErrorCode DMRegister_MGViaApproxOrders(const char sname[])
Register DM for Multi-Grid via approximation orders.
PetscErrorCode DMoFEMLoopFiniteElements(DM dm, const char fe_name[], MoFEM::FEMethod *method, CacheTupleWeakPtr cache_ptr=CacheTupleSharedPtr())
Executes FEMethod for finite elements in DM.
auto createDMVector(DM dm, RowColData rc=RowColData::COL)
Get smart vector from DM.
PetscErrorCode DMMoFEMAddSubFieldCol(DM dm, const char field_name[])
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 removeSideDOFs(const std::string problem_name, const std::string block_name, const std::string field_name, int bridge_dim, int lo, int hi, bool is_distributed_mesh=true)
Remove DOFs on side entities from problem.
#define NBFACETRI_L2(P)
Number of base functions on triangle for L2 space.
#define NBEDGE_L2(P)
Number of base functions on edge from L2 space.
FormsIntegrators< DomainEleOp >::Assembly< PETSC >::BiLinearForm< GAUSS >::OpMixDivTimesScalar< 2 > OpHdivU
PetscErrorCode MoFEMErrorCode
MoFEM/PETSc error code.
implementation of Data Operators for Forces and Sources
OpSchurAssembleBase * createOpSchurAssembleEnd(std::vector< std::string > fields_name, std::vector< boost::shared_ptr< Range > > field_ents, SmartPetscObj< AO > ao, SmartPetscObj< Mat > schur, bool sym_schur, bool symm_op)
Construct a new Op Schur Assemble End object.
PetscErrorCode PetscOptionsGetInt(PetscOptions *, const char pre[], const char name[], PetscInt *ivalue, PetscBool *set)
MoFEMErrorCode DMMoFEMGetBlocMatData(DM dm, boost::shared_ptr< BlockStructure > &)
Get data for block mat.
MoFEMErrorCode setSchurA00MatSolvePC(SmartPetscObj< PC > pc)
Set PC for A00 block.
SmartPetscObj< Vec > vectorDuplicate(Vec vec)
Create duplicate vector of smart vector.
boost::shared_ptr< PCMGSetUpViaApproxOrdersCtx > createPCMGSetUpViaApproxOrdersCtx(DM dm, Mat A, bool use_shell_mat)
createPCMGSetUpViaApproxOrdersCtx
auto createVectorMPI(MPI_Comm comm, PetscInt n, PetscInt N)
Create MPI Vector.
auto getDMKspCtx(DM dm)
Get KSP context data structure used by DM.
auto createDMHybridisedL2Matrix(DM dm)
Get smart hybridised L2 matrix from DM.
auto getDMSubData(DM dm)
Get sub problem data structure.
MoFEMErrorCode PCMGSetUpViaApproxOrders(PC pc, boost::shared_ptr< PCMGSetUpViaApproxOrdersCtx > ctx, int verb)
Function build MG structure.
boost::shared_ptr< BlockStructure > createBlockMatStructure(DM dm, SchurFEOpsFEandFields schur_fe_op_vec)
Create a Mat Diag Blocks object.
boost::shared_ptr< NestSchurData > createSchurNestedMatrixStruture(std::pair< SmartPetscObj< DM >, SmartPetscObj< DM > > dms, boost::shared_ptr< BlockStructure > block_mat_data_ptr, std::vector< std::string > fields_names, std::vector< boost::shared_ptr< Range > > field_ents, bool add_preconditioner_block)
Get the Schur Nest Mat Array object.
auto createAOMappingIS(IS isapp, IS ispetsc)
Creates an application mapping using two index sets.
PetscErrorCode PetscOptionsGetEList(PetscOptions *, const char pre[], const char name[], const char *const *list, PetscInt next, PetscInt *value, PetscBool *set)
SmartPetscObj< Mat > matDuplicate(Mat mat, MatDuplicateOption op)
MoFEMErrorCode DMMoFEMSetNestSchurData(DM dm, boost::shared_ptr< NestSchurData >)
auto createDMNestSchurMat(DM dm)
auto createDM(MPI_Comm comm, const std::string dm_type_name)
Creates smart DM object.
MoFEMErrorCode assembleBlockMatSchur(MoFEM::Interface &m_field, Mat B, Mat S, std::vector< std::string > fields_name, std::vector< boost::shared_ptr< Range > > field_ents, SmartPetscObj< AO > ao)
Assemble Schur matrix.
OpSchurAssembleBase * createOpSchurAssembleBegin()
auto createDMBlockMat(DM dm)
OpPostProcMapInMoab< SPACE_DIM, SPACE_DIM > OpPPMap
PipelineManager::ElementsAndOpsByDim< SPACE_DIM >::FaceSideEle EleOnSide
FormsIntegrators< DomainEleOp >::Assembly< PETSC >::LinearForm< GAUSS >::OpBaseTimesVector< 3, 3, 3 > OpHdivFlux
Integrating Rhs flux base (1/k) flux (FLUX)
FormsIntegrators< DomainEleOp >::Assembly< PETSC >::LinearForm< GAUSS >::OpMixDivTimesU< 3, 1, SPACE_DIM > OpHDivH
Integrate Rhs div flux base times temperature (T)
FormsIntegrators< DomainEleOp >::Assembly< PETSC >::BiLinearForm< GAUSS >::OpMass< 3, 3 > OpHdivHdiv
Integrate Lhs base of flux (1/k) base of flux (FLUX x FLUX)
Add operators pushing bases from local to physical configuration.
Boundary condition manager for finite element problem setup.
virtual moab::Interface & get_moab()=0
virtual MPI_Comm & get_comm() const =0
virtual int get_comm_rank() const =0
static MoFEMErrorCode Initialize(int *argc, char ***args, const char file[], const char help[])
Initializes the MoFEM database PETSc, MOAB and MPI.
static MoFEMErrorCode Finalize()
Checks for options to be called at the conclusion of the program.
base operator to do operations at Gauss Pt. level
Deprecated interface functions.
Data on single entity (This is passed as argument to DataOperator::doWork)
std::map< EntityHandle, std::vector< boost::weak_ptr< NumeredEntFiniteElement > > > AdjCache
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.
Operator for broken loop side.
Get norm of input VectorDouble for Tensor0.
Get norm of input MatrixDouble for Tensor1.
Calculate tenor field using vectorial base, i.e. Hdiv/Hcurl.
Get vector field for H-div approximation.
Calculate divergence of vector field.
Get field gradients at integration pts for scalar field rank 0, i.e. vector field.
Specialization for double precision scalar field values calculation.
Specialization for MatrixDouble vector field values calculation.
Get values from scalar function at integration points and save them to VectorDouble for Tensor0.
Element used to execute operators on side of the element.
Post post-proc data at points from hash maps.
static MoFEMErrorCode writeKSPGraphGraphviz(KspCtx *ksp_ctx, std::string filename)
KSP graph to Graphviz file.
static MoFEMErrorCode writeGraphGraphviz(std::string filename, std::string pip_name, const boost::ptr_deque< ForcesAndSourcesCore::UserDataOperator > &pip)
Pipeline graph to Graphviz file.
static MoFEMErrorCode writePiplineManagerGraphGraphviz(std::string filename, PipelineManager *pip_mng)
Write pipeline manager graph to Graphviz file.
Template struct for dimension-specific finite element types.
PipelineManager interface.
Simple interface for fast problem set-up.
MoFEMErrorCode getOptions()
get options
intrusive_ptr for managing petsc objects
MoFEMErrorCode getInterface(IFACE *&iface) const
Get interface reference to pointer of interface.
virtual ~SetUpSchurImpl()=default
SetUpSchurImpl(MoFEM::Interface &m_field)
MoFEMErrorCode setUp(SmartPetscObj< KSP >)
MoFEM::Interface & mField
[Push operators to pipeline]
virtual MoFEMErrorCode setUp(SmartPetscObj< KSP >)=0
virtual ~SetUpSchur()=default
static boost::shared_ptr< SetUpSchur > createSetUpSchur(MoFEM::Interface &m_field)
constexpr AssemblyType AT
constexpr IntegrationType IT
constexpr AssemblyType BlockAssemblyType
BoundaryEle::UserDataOperator BdyEleOp
#define EXECUTABLE_DIMENSION