2727#include < aspect/mesh_deformation/interface.h>
2828
2929#include < deal.II/base/signaling_nan.h>
30+ #include < deal.II/lac/diagonal_matrix.h>
31+ #include < deal.II/lac/linear_operator.h>
3032#include < deal.II/lac/solver_gmres.h>
3133#include < deal.II/lac/solver_bicgstab.h>
3234#include < deal.II/lac/solver_cg.h>
3335#include < deal.II/fe/fe_values.h>
36+ #include < deal.II/lac/trilinos_vector.h>
3437
3538namespace aspect
3639{
3740 namespace internal
3841 {
42+
3943 /* *
4044 * Implement multiplication with Stokes part of system matrix. In essence, this
4145 * object represents a 2x2 block matrix that corresponds to the top left
@@ -163,6 +167,8 @@ namespace aspect
163167
164168 return dst.l2_norm ();
165169 }
170+
171+
166172
167173
168174 /* *
@@ -380,6 +386,25 @@ namespace aspect
380386 virtual unsigned int n_iterations () const =0;
381387
382388 };
389+ template <typename Range,
390+ typename Domain,
391+ typename Payload>
392+ LinearOperator<Range, Domain, Payload> diag_operator (LinearOperator<Range,Domain,Payload> &exemplar,TrilinosWrappers::MPI::Vector &diagonal)
393+ {
394+ LinearOperator<Range, Domain, Payload> return_op;
395+
396+
397+ return_op.reinit_range_vector = exemplar.reinit_range_vector ;
398+ return_op.reinit_domain_vector = exemplar.reinit_domain_vector ;
399+
400+ return_op.vmult = [&](Range &dest, const Domain &src)
401+ {
402+ dest = src;
403+ dest.scale (diagonal);
404+ };
405+ // std::cout << "ok" << std::endl;
406+ return return_op;
407+ }
383408
384409 /* *
385410 * This class approximates the Schur Complement inverse operator
@@ -458,7 +483,15 @@ namespace aspect
458483 SolverControl solver_control (5000 , 1e-6 * src.l2_norm (), false , true );
459484 SolverCG<TrilinosWrappers::MPI::Vector> solver (solver_control);
460485 // Solve with Schur Complement approximation
461- solver.solve (mp_matrix,
486+ auto Op_A=LinearOperator<TrilinosWrappers::MPI::Vector>(system_matrix.block (0 ,0 ));
487+ auto Op_BT = LinearOperator<TrilinosWrappers::MPI::Vector>(system_matrix.block (0 ,1 ));
488+ auto Op_B = LinearOperator<TrilinosWrappers::MPI::Vector>(system_matrix.block (1 ,0 ));
489+ auto Op_C = diag_operator (Op_A,inverse_lumped_mass_matrix);
490+ auto matrix = Op_B*Op_C*Op_BT;
491+
492+
493+
494+ solver.solve (matrix,
462495 ptmp,
463496 src,
464497 mp_preconditioner);
@@ -471,7 +504,7 @@ namespace aspect
471504 system_matrix.block (1 ,0 ).vmult (ptmp,wtmp);
472505
473506 dst=0 ;
474- solver.solve (mp_matrix ,
507+ solver.solve (matrix ,
475508 dst,
476509 ptmp,
477510 mp_preconditioner);
0 commit comments