[petsc-dev] [petsc-users] Shell preconditioner within a fieldsplit

Patrick Sanan patrick.sanan at gmail.com
Mon Nov 14 01:25:28 CST 2016


PCMAT seems abstraction-breaking (and the man page even admits it is
"strange" :D )

The preconditioner Mat B is thought of as an approximation (maybe a
perfect one) to the operator A, to be used to construct
preconditioners. PCMAT uses B as an approximation to the *inverse* of
A (loosely speaking). That's confusing, and worse it ruins a central
feature of PETSc, which is the ability to change the preconditioner at
runtime; the meaning of B changes depending on which PC implementation
you use.

Proposed change: Have PCMAT (like analogous object PCKSP) store its
own Mat object and introduce API functions to interact with this
internal Mat. To make sure that any user code which happens to use
PCMAT doesn't see an unexplained change in behavior, do not set a
default internal Mat, and produce an informative error if
PCApply_Mat() is called without first calling the new function
PCMatSetMat().

On Mon, Nov 14, 2016 at 7:04 AM, Dave May <dave.mayhem23 at gmail.com> wrote:
> Looks like you want the contents of your mat shell, specifically the op Ax,
> to define the action of the preconditioner.
>
> You need to either create a PCShell (rather than a MatShell), and define the
> operation called by PCApply(), or keep you current shell but change
> "preonly" to "mat".
>
> http://www.mcs.anl.gov/petsc/petsc-current/docs/manualpages/PC/PCMAT.html#PCMAT
>
> Thanks
> Dave
>
> On Mon, 14 Nov 2016 at 06:36, Safin, Artur <aks084000 at utdallas.edu> wrote:
>>
>> Hello,
>>
>>
>> What is the proper way to set up a shell preconditioner within a
>> fielsplit? I have tried it on my own, but do not get the proper behavior.
>> The relevant portion looks like this:
>>
>>
>> __________________________________________________________________
>>
>> // Global System
>> KSPSetOperators(ksp, A, A);
>>
>> // Skipped code..
>>
>>
>>
>> // Shell Preconditioner for the pressure sub-block
>>
>> KSP *subksp;
>>
>> PCFieldSplitGetSubKSP(pc, NULL, &subksp);
>>
>> Mat pressureA;
>> KSPSetType(subksp[0], "preonly");
>> MatCreateShell(MPI_COMM_WORLD, n_local_P_dofs, n_local_P_dofs, ,
>> PETSC_DETERMINE, PETSC_DETERMINE, &pressureA);
>> MatShellSetOperation(pressureA, MATOP_MULT, (void(*)(void))
>> PressureBlock);
>> KSPSetOperators(subksp[0], pressureA, pressureA);
>>
>> // Skipped code..
>>
>>
>>
>> KSPSetUp(ksp);
>>
>> KSPSolve(ksp, b, x);
>>
>> __________________________________________________________________
>>
>>
>> The fieldsplit component works fine; the solver however does not go into
>> the custom function PressureBlock(), so I am curious as to what the correct
>> approach is.
>>
>>
>> Best,
>>
>>
>> Artur



More information about the petsc-dev mailing list