Skip to content

Commit d524f88

Browse files
authored
Merge pull request #4127 from lindsayad/set-nullspace-for-J-and-P
Set nullspace for both J and P operators
2 parents 4787aa3 + 05df909 commit d524f88

File tree

1 file changed

+46
-35
lines changed

1 file changed

+46
-35
lines changed

src/solvers/petsc_nonlinear_solver.C

Lines changed: 46 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -1013,39 +1013,6 @@ PetscNonlinearSolver<T>::solve (SparseMatrix<T> & pre_in, // System Preconditi
10131013
if (this->jacobian || this->jacobian_object || this->residual_and_jacobian_object)
10141014
LibmeshPetscCall(SNESSetJacobian (_snes, pre->mat(), pre->mat(), libmesh_petsc_snes_jacobian, this));
10151015

1016-
1017-
// Only set the nullspace if we have a way of computing it and the result is non-empty.
1018-
if (this->nullspace || this->nullspace_object)
1019-
{
1020-
WrappedPetsc<MatNullSpace> msp;
1021-
this->build_mat_null_space(this->nullspace_object, this->nullspace, msp.get());
1022-
if (msp)
1023-
LibmeshPetscCall(MatSetNullSpace(pre->mat(), msp));
1024-
}
1025-
1026-
// Only set the transpose nullspace if we have a way of computing it and the result is non-empty.
1027-
if (this->transpose_nullspace || this->transpose_nullspace_object)
1028-
{
1029-
#if PETSC_VERSION_LESS_THAN(3,6,0)
1030-
libmesh_warning("MatSetTransposeNullSpace is only supported for PETSc >= 3.6, transpose nullspace will be ignored.");
1031-
#else
1032-
WrappedPetsc<MatNullSpace> msp;
1033-
this->build_mat_null_space(this->transpose_nullspace_object, this->transpose_nullspace, msp.get());
1034-
if (msp)
1035-
LibmeshPetscCall(MatSetTransposeNullSpace(pre->mat(), msp));
1036-
#endif
1037-
}
1038-
1039-
// Only set the nearnullspace if we have a way of computing it and the result is non-empty.
1040-
if (this->nearnullspace || this->nearnullspace_object)
1041-
{
1042-
WrappedPetsc<MatNullSpace> msp;
1043-
this->build_mat_null_space(this->nearnullspace_object, this->nearnullspace, msp.get());
1044-
1045-
if (msp)
1046-
LibmeshPetscCall(MatSetNearNullSpace(pre->mat(), msp));
1047-
}
1048-
10491016
// Have the Krylov subspace method use our good initial guess rather than 0
10501017
KSP ksp;
10511018
LibmeshPetscCall(SNESGetKSP (_snes, &ksp));
@@ -1120,8 +1087,8 @@ PetscNonlinearSolver<T>::solve (SparseMatrix<T> & pre_in, // System Preconditi
11201087
#endif
11211088
LibmeshPetscCall(SNESSetUp(_snes));
11221089

1123-
Mat J;
1124-
LibmeshPetscCall(SNESGetJacobian(_snes, &J, LIBMESH_PETSC_NULLPTR,
1090+
Mat J, P;
1091+
LibmeshPetscCall(SNESGetJacobian(_snes, &J, &P,
11251092
LIBMESH_PETSC_NULLPTR,
11261093
LIBMESH_PETSC_NULLPTR));
11271094
LibmeshPetscCall(MatMFFDSetFunction(J, libmesh_petsc_snes_mffd_interface, this));
@@ -1139,6 +1106,50 @@ PetscNonlinearSolver<T>::solve (SparseMatrix<T> & pre_in, // System Preconditi
11391106
#endif
11401107
#endif
11411108

1109+
// Only set the nullspace if we have a way of computing it and the result is non-empty.
1110+
if (this->nullspace || this->nullspace_object)
1111+
{
1112+
WrappedPetsc<MatNullSpace> msp;
1113+
this->build_mat_null_space(this->nullspace_object, this->nullspace, msp.get());
1114+
if (msp)
1115+
{
1116+
LibmeshPetscCall(MatSetNullSpace(J, msp));
1117+
if (P != J)
1118+
LibmeshPetscCall(MatSetNullSpace(P, msp));
1119+
}
1120+
}
1121+
1122+
// Only set the transpose nullspace if we have a way of computing it and the result is non-empty.
1123+
if (this->transpose_nullspace || this->transpose_nullspace_object)
1124+
{
1125+
#if PETSC_VERSION_LESS_THAN(3,6,0)
1126+
libmesh_warning("MatSetTransposeNullSpace is only supported for PETSc >= 3.6, transpose nullspace will be ignored.");
1127+
#else
1128+
WrappedPetsc<MatNullSpace> msp;
1129+
this->build_mat_null_space(this->transpose_nullspace_object, this->transpose_nullspace, msp.get());
1130+
if (msp)
1131+
{
1132+
LibmeshPetscCall(MatSetTransposeNullSpace(J, msp));
1133+
if (P != J)
1134+
LibmeshPetscCall(MatSetTransposeNullSpace(P, msp));
1135+
}
1136+
#endif
1137+
}
1138+
1139+
// Only set the nearnullspace if we have a way of computing it and the result is non-empty.
1140+
if (this->nearnullspace || this->nearnullspace_object)
1141+
{
1142+
WrappedPetsc<MatNullSpace> msp;
1143+
this->build_mat_null_space(this->nearnullspace_object, this->nearnullspace, msp.get());
1144+
1145+
if (msp)
1146+
{
1147+
LibmeshPetscCall(MatSetNearNullSpace(J, msp));
1148+
if (P != J)
1149+
LibmeshPetscCall(MatSetNearNullSpace(P, msp));
1150+
}
1151+
}
1152+
11421153
SNESLineSearch linesearch;
11431154
if (linesearch_object)
11441155
{

0 commit comments

Comments
 (0)