262 enum bases { AINSWORTH, DEMKOWICZ, LASBASETOPT };
263 const char *list_bases[LASBASETOPT] = {
"ainsworth",
"demkowicz"};
264 PetscInt choice_base_value = AINSWORTH;
266 LASBASETOPT, &choice_base_value, PETSC_NULLPTR);
273 switch (choice_base_value) {
277 <<
"Set AINSWORTH_LEGENDRE_BASE for displacements";
282 <<
"Set DEMKOWICZ_JACOBI_BASE for displacements";
299 auto get_skin = [&]() {
304 CHKERR skin.find_skin(0, body_ents,
false, skin_ents);
308 auto filter_blocks = [&](
auto skin) {
309 bool is_contact_block =
false;
314 (boost::format(
"%s(.*)") %
"CONTACT").str()
323 <<
"Find contact block set: " <<
m->getName();
324 auto meshset =
m->getMeshset();
325 Range contact_meshset_range;
327 meshset,
SPACE_DIM - 1, contact_meshset_range,
true);
330 contact_meshset_range);
331 contact_range.merge(contact_meshset_range);
333 if (is_contact_block) {
335 <<
"Nb entities in contact surface: " << contact_range.size();
337 skin = intersect(skin, contact_range);
344 ParallelComm *pcomm =
346 CHKERR pcomm->filter_pstatus(skin, PSTATUS_SHARED | PSTATUS_MULTISHARED,
347 PSTATUS_NOT, -1, &boundary_ents);
348 return boundary_ents;
361#ifdef ENABLE_PYTHON_BINDING
362 sdfPythonPtr = boost::make_shared<ContactOps::SDFPython>();
363 CHKERR sdfPythonPtr->sdfInit(
"sdf.py");
364 ContactOps::sdfPythonWeakPtr = sdfPythonPtr;
372 auto project_ho_geometry = [&]() {
376 PetscBool project_geometry = PETSC_TRUE;
378 &project_geometry, PETSC_NULLPTR);
379 if (project_geometry) {
380 CHKERR project_ho_geometry();
394 VonMissesPlaneStress,
396 HeterogeneousParaboloidal,
399 const char *list_materials[LastModel] = {
"VonMisses",
"VonMissesPlaneStress",
400 "Paraboloidal",
"HeterogeneousParaboloidal"};
401 PetscInt choice_material = VonMisses;
403 LastModel, &choice_material, PETSC_NULLPTR);
405 switch (choice_material) {
407 cpPtr = createMaterial<J2Plasticity<3>>();
409 case VonMissesPlaneStress:
412 "VonMissesPlaneStrain is only for 2D case");
413 cpPtr = createMaterial<J2Plasticity<2>>();
416 cpPtr = createMaterial<ParaboloidalPlasticity>();
418 case HeterogeneousParaboloidal:
419 cpPtr = createMaterial<HeterogeneousParaboloidalPlasticity>();
426 cpPtr->integrationRule = [](int, int,
int p) {
return 2 * (p - 2); };
800 auto dm =
simple->getDM();
801 auto time_scale = boost::make_shared<TimeScale>();
805 auto create_post_proc_fe = [dm,
this,
simple]() {
809 auto post_proc_ele_domain = [
this](
auto &pip_domain,
auto &fe_name) {
812 pip_domain, {
H1,
HDIV},
"GEOMETRY");
817 auto grad_ptr = boost::make_shared<MatrixDouble>();
818 pip_domain.push_back(
828 pip_domain.push_back(op_this);
832 auto fe_physics = op_this->getThisFEPtr();
834 auto evaluate_stress_on_physical_element = [&]() {
836 fe_physics->getRuleHook =
cpPtr->integrationRule;
838 fe_physics->getOpPtrVector(), {H1});
839 auto common_data_ptr =
840 boost::make_shared<ADOLCPlasticity::CommonData>();
845 opFactoryDomainHenckyStrainRhs<SPACE_DIM, GAUSS, DomainEleOp>(
846 mField,
"U", fe_physics->getOpPtrVector(),
"ADOLCMAT", common_data_ptr,
cpPtr);
849 fe_physics->getOpPtrVector().push_back(
851 "U", common_data_ptr->getGradAtGaussPtsPtr()));
852 CHKERR cpPtr->addMatBlockOps(
mField, fe_physics->getOpPtrVector(),
"ADOLCMAT", Sev::inform);
853 fe_physics->getOpPtrVector().push_back(getRawPtrOpCalculateStress<SPACE_DIM, SMALL_STRAIN>(
856 return common_data_ptr;
859 auto dg_projection_froward_and_back = [&](
auto &common_data_ptr) {
862 auto entity_data_l2 =
863 boost::make_shared<EntitiesFieldData>(MBENTITYSET);
865 boost::make_shared<MatrixDouble>();
870 auto coeffs_ptr_stress = boost::make_shared<MatrixDouble>();
873 common_data_ptr->getStressMatrixPtr(), coeffs_ptr_stress, mass_ptr,
876 auto coeffs_ptr_plastic_strain = boost::make_shared<MatrixDouble>();
878 common_data_ptr->getPlasticStrainMatrixPtr(),
879 coeffs_ptr_plastic_strain, mass_ptr, entity_data_l2,
approxBase,
885 common_data_ptr->getStressMatrixPtr(), coeffs_ptr_stress,
888 common_data_ptr->getPlasticStrainMatrixPtr(),
889 coeffs_ptr_plastic_strain, entity_data_l2,
approxBase,
L2));
892 auto common_data_ptr = evaluate_stress_on_physical_element();
893 dg_projection_froward_and_back(common_data_ptr);
895 return boost::make_tuple(grad_ptr, common_data_ptr->getStressMatrixPtr(),
896 common_data_ptr->getPlasticStrainMatrixPtr());
902 auto add_post_proc_map = [&](
auto post_proc_fe,
auto u_ptr,
auto grad_ptr,
903 auto stress_ptr,
auto plastic_strain_ptr,
904 auto contact_stress_ptr,
auto X_ptr) {
906 post_proc_fe->getOpPtrVector().push_back(
908 new OpPPMapSPACE_DIM(
910 post_proc_fe->getPostProcMesh(), post_proc_fe->getMapGaussPts(),
914 {{
"U", u_ptr}, {
"GEOMETRY", X_ptr}},
916 {{
"GRAD", grad_ptr}, {
"SIGMA", contact_stress_ptr}},
926 post_proc_fe->getOpPtrVector().push_back(
930 post_proc_fe->getPostProcMesh(), post_proc_fe->getMapGaussPts(),
936 {{
"PK1", stress_ptr}},
938 {{
"PLASTIC_STRAIN", plastic_strain_ptr}}
944 post_proc_fe->getOpPtrVector().push_back(
948 post_proc_fe->getPostProcMesh(), post_proc_fe->getMapGaussPts(),
956 {{
"STRESS", stress_ptr}, {
"PLASTIC_STRAIN", plastic_strain_ptr}}
966 auto vol_post_proc = [
this,
simple, post_proc_ele_domain,
967 add_post_proc_map]() {
968 PetscBool post_proc_vol = PETSC_FALSE;
970 post_proc_vol = PETSC_TRUE;
973 &post_proc_vol, PETSC_NULLPTR);
974 if (post_proc_vol == PETSC_FALSE)
975 return boost::shared_ptr<PostProcEleDomain>();
976 auto post_proc_fe = boost::make_shared<PostProcEleDomain>(mField);
977 auto u_ptr = boost::make_shared<MatrixDouble>();
978 post_proc_fe->getOpPtrVector().push_back(
980 auto X_ptr = boost::make_shared<MatrixDouble>();
981 post_proc_fe->getOpPtrVector().push_back(
983 auto contact_stress_ptr = boost::make_shared<MatrixDouble>();
985 post_proc_fe->getOpPtrVector().push_back(
987 "SIGMA", contact_stress_ptr));
989 contact_stress_ptr =
nullptr;
991 auto [grad_ptr, stress_ptr, plastic_strain_ptr] = post_proc_ele_domain(
992 post_proc_fe->getOpPtrVector(),
simple->getDomainFEName());
994 return add_post_proc_map(post_proc_fe, u_ptr, grad_ptr, stress_ptr,
995 plastic_strain_ptr, contact_stress_ptr, X_ptr);
998 auto skin_post_proc = [
this,
simple, post_proc_ele_domain,
999 add_post_proc_map]() {
1002 PetscBool post_proc_skin = PETSC_TRUE;
1004 post_proc_skin = PETSC_FALSE;
1007 &post_proc_skin, PETSC_NULLPTR);
1009 if (post_proc_skin == PETSC_FALSE)
1010 return boost::shared_ptr<PostProcEleBdy>();
1012 auto post_proc_fe = boost::make_shared<PostProcEleBdy>(mField);
1013 auto u_ptr = boost::make_shared<MatrixDouble>();
1014 post_proc_fe->getOpPtrVector().push_back(
1016 auto X_ptr = boost::make_shared<MatrixDouble>();
1017 post_proc_fe->getOpPtrVector().push_back(
1019 auto contact_stress_ptr = boost::make_shared<MatrixDouble>();
1022 auto [grad_ptr, stress_ptr, plastic_strain_ptr] = post_proc_ele_domain(
1023 op_loop_side->getOpPtrVector(),
simple->getDomainFEName());
1025 op_loop_side->getOpPtrVector().push_back(
1027 "SIGMA", contact_stress_ptr));
1029 contact_stress_ptr =
nullptr;
1031 post_proc_fe->getOpPtrVector().push_back(op_loop_side);
1033 return add_post_proc_map(post_proc_fe, u_ptr, grad_ptr, stress_ptr,
1034 plastic_strain_ptr, contact_stress_ptr, X_ptr);
1037 return std::make_pair(vol_post_proc(), skin_post_proc());
1040 auto create_reaction_fe = [&]() {
1041 auto fe_ptr = boost::make_shared<DomainEle>(mField);
1042 fe_ptr->getRuleHook = cpPtr->integrationRule;
1044 auto &pip = fe_ptr->getOpPtrVector();
1046 auto common_data_ptr = boost::make_shared<ADOLCPlasticity::CommonData>();
1050 opFactoryDomainHenckyStrainRhs<SPACE_DIM, GAUSS, DomainEleOp>(
1051 mField,
"U", pip,
"ADOLCMAT", common_data_ptr, cpPtr);
1060 "U", common_data_ptr->getGradAtGaussPtsPtr()));
1061 CHKERR opFactoryDomainRhs<SPACE_DIM, PETSC, GAUSS, DomainEleOp>(
1062 mField,
"U", pip,
"ADOLCMAT", common_data_ptr, cpPtr);
1068 auto add_extra_finite_elements_to_ksp_solver_pipelines = [&]() {
1071 auto pre_proc_ptr = boost::make_shared<FEMethod>();
1072 auto post_proc_rhs_ptr = boost::make_shared<FEMethod>();
1073 auto post_proc_lhs_ptr = boost::make_shared<FEMethod>();
1075 auto get_bc_hook_rhs = [
this, pre_proc_ptr, time_scale]() {
1078 {time_scale},
false)();
1082 pre_proc_ptr->preProcessHook = get_bc_hook_rhs;
1084 auto get_post_proc_hook_rhs = [
this, post_proc_rhs_ptr]() {
1087 mField, post_proc_rhs_ptr,
nullptr, Sev::verbose)();
1089 mField, post_proc_rhs_ptr, 1.)();
1092 auto get_post_proc_hook_lhs = [
this, post_proc_lhs_ptr]() {
1095 mField, post_proc_lhs_ptr, 1.)();
1098 post_proc_rhs_ptr->postProcessHook = get_post_proc_hook_rhs;
1099 post_proc_lhs_ptr->postProcessHook = get_post_proc_hook_lhs;
1103 ts_ctx_ptr->getPreProcessIFunction().push_front(pre_proc_ptr);
1104 ts_ctx_ptr->getPreProcessIJacobian().push_front(pre_proc_ptr);
1105 ts_ctx_ptr->getPostProcessIFunction().push_back(post_proc_rhs_ptr);
1106 ts_ctx_ptr->getPostProcessIJacobian().push_back(post_proc_lhs_ptr);
1112 CHKERR add_extra_finite_elements_to_ksp_solver_pipelines();
1114 auto create_monitor_fe = [dm, time_scale](
auto &&post_proc_fe,
1115 auto &&reaction_fe) {
1116 return boost::make_shared<Monitor>(
1117 dm, post_proc_fe, reaction_fe,
1118 std::vector<boost::shared_ptr<ScalingMethod>>{time_scale});
1122 auto set_up_post_step = [&](
auto ts) {
1127 auto create_update_ptr = [&]() {
1128 auto fe_ptr = boost::make_shared<DomainEle>(mField);
1129 fe_ptr->getRuleHook = cpPtr->integrationRule;
1132 auto common_data_ptr = boost::make_shared<ADOLCPlasticity::CommonData>();
1137 mField,
"U", fe_ptr->getOpPtrVector(),
"ADOLCMAT", common_data_ptr,
1140 fe_ptr->getOpPtrVector().push_back(
1142 "U", common_data_ptr->getGradAtGaussPtsPtr()));
1143 CHKERR cpPtr->addMatBlockOps(mField, fe_ptr->getOpPtrVector(),
1144 "ADOLCMAT", Sev::noisy);
1145 fe_ptr->getOpPtrVector().push_back(
1146 getRawPtrOpCalculateStress<SPACE_DIM, SMALL_STRAIN>(mField, common_data_ptr,
1151 opFactoryDomainUpdate<SPACE_DIM>(mField, fe_ptr->getOpPtrVector(),
1152 "ADOLCMAT", common_data_ptr, cpPtr),
1163 auto ts_step_post_proc = [](TS ts) {
1172 CHKERR TSSetPostStep(ts, ts_step_post_proc);
1178 auto set_up_monitor = [&](
auto ts) {
1180 boost::shared_ptr<FEMethod> null_fe;
1182 create_monitor_fe(create_post_proc_fe(), create_reaction_fe());
1184 null_fe, monitor_ptr);
1188 auto set_section_monitor = [&](
auto solver) {
1191 CHKERR TSGetSNES(solver, &snes);
1192 CHKERR SNESMonitorSet(snes,
1195 (
void *)(snes_ctx_ptr.get()),
nullptr);
1199 auto set_up_adapt = [&](
auto ts) {
1203 CHKERR TSGetAdapt(ts, &adapt);
1208 auto ts = pipeline_mng->createTSIM();
1212 CHKERR TSSetMaxTime(ts, ftime);
1213 CHKERR TSSetExactFinalTime(ts, TS_EXACTFINALTIME_MATCHSTEP);
1216 CHKERR TSSetIJacobian(ts,
B,
B, PETSC_NULLPTR, PETSC_NULLPTR);
1221 CHKERR set_section_monitor(ts);
1224 CHKERR set_up_monitor(ts);
1225 CHKERR set_up_post_step(ts);
1227 CHKERR TSSetFromOptions(ts);
1229 CHKERR TSSolve(ts, NULL);
1232 CHKERR TSGetTime(ts, &ftime);
1234 PetscInt steps, snesfails, rejects, nonlinits, linits;
1235 CHKERR TSGetStepNumber(ts, &steps);
1236 CHKERR TSGetSNESFailures(ts, &snesfails);
1237 CHKERR TSGetStepRejections(ts, &rejects);
1238 CHKERR TSGetSNESIterations(ts, &nonlinits);
1239 CHKERR TSGetKSPIterations(ts, &linits);
1241 "steps %d (%d rejected, %d SNES fails), ftime %g, nonlinits "
1243 steps, rejects, snesfails, ftime, nonlinits, linits);