1fe1899a2SJed Brown #include <petscdmshell.h> /*I "petscdmshell.h" I*/ 207475bc1SBarry Smith #include <petscmat.h> 3af0996ceSBarry Smith #include <petsc/private/dmimpl.h> 4fe1899a2SJed Brown 5fe1899a2SJed Brown typedef struct { 6fe1899a2SJed Brown Vec Xglobal; 7dc43b69eSJed Brown Vec Xlocal; 8fe1899a2SJed Brown Mat A; 9a94b16f6SRichard Tran Mills VecScatter gtol; 10a94b16f6SRichard Tran Mills VecScatter ltog; 11f089877aSRichard Tran Mills VecScatter ltol; 12fef3a512SBarry Smith void *ctx; 1309904cd0SBarry Smith PetscErrorCode (*destroyctx)(void *); 14fe1899a2SJed Brown } DM_Shell; 15fe1899a2SJed Brown 167a108d1dSBarry Smith /*@ 17*20f4b53cSBarry Smith DMGlobalToLocalBeginDefaultShell - Uses the GlobalToLocal `VecScatter` context set by the user to begin a global to local scatter 18*20f4b53cSBarry Smith 198d359177SBarry Smith Collective 208d359177SBarry Smith 214165533cSJose E. Roman Input Parameters: 22*20f4b53cSBarry Smith + dm - `DMSHELL` 238d359177SBarry Smith . g - global vector 24*20f4b53cSBarry Smith . mode - `InsertMode` 258d359177SBarry Smith - l - local vector 268d359177SBarry Smith 277a108d1dSBarry Smith Level: advanced 288d359177SBarry Smith 29*20f4b53cSBarry Smith Note: 30*20f4b53cSBarry Smith This is not normally called directly by user code, generally user code calls `DMGlobalToLocalBegin()` and `DMGlobalToLocalEnd()`. If the user provides their own custom routines to `DMShellSetLocalToGlobal()` then those routines might have reason to call this function. 317a108d1dSBarry Smith 32*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMGlobalToLocalEndDefaultShell()` 338d359177SBarry Smith @*/ 34d71ae5a4SJacob Faibussowitsch PetscErrorCode DMGlobalToLocalBeginDefaultShell(DM dm, Vec g, InsertMode mode, Vec l) 35d71ae5a4SJacob Faibussowitsch { 368d359177SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 378d359177SBarry Smith 388d359177SBarry Smith PetscFunctionBegin; 397a8be351SBarry Smith PetscCheck(shell->gtol, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetGlobalToLocalVecScatter()"); 409566063dSJacob Faibussowitsch PetscCall(VecScatterBegin(shell->gtol, g, l, mode, SCATTER_FORWARD)); 413ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 428d359177SBarry Smith } 438d359177SBarry Smith 447a108d1dSBarry Smith /*@ 45*20f4b53cSBarry Smith DMGlobalToLocalEndDefaultShell - Uses the GlobalToLocal `VecScatter` context set by the user to end a global to local scatter 468d359177SBarry Smith Collective 478d359177SBarry Smith 484165533cSJose E. Roman Input Parameters: 49*20f4b53cSBarry Smith + dm - `DMSHELL` 508d359177SBarry Smith . g - global vector 51*20f4b53cSBarry Smith . mode - `InsertMode` 528d359177SBarry Smith - l - local vector 538d359177SBarry Smith 547a108d1dSBarry Smith Level: advanced 558d359177SBarry Smith 56*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMGlobalToLocalBeginDefaultShell()` 578d359177SBarry Smith @*/ 58d71ae5a4SJacob Faibussowitsch PetscErrorCode DMGlobalToLocalEndDefaultShell(DM dm, Vec g, InsertMode mode, Vec l) 59d71ae5a4SJacob Faibussowitsch { 608d359177SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 618d359177SBarry Smith 628d359177SBarry Smith PetscFunctionBegin; 637a8be351SBarry Smith PetscCheck(shell->gtol, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetGlobalToLocalVecScatter()"); 649566063dSJacob Faibussowitsch PetscCall(VecScatterEnd(shell->gtol, g, l, mode, SCATTER_FORWARD)); 653ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 668d359177SBarry Smith } 678d359177SBarry Smith 68c5076b69SRichard Tran Mills /*@ 69*20f4b53cSBarry Smith DMLocalToGlobalBeginDefaultShell - Uses the LocalToGlobal `VecScatter` context set by the user to begin a local to global scatter 70c5076b69SRichard Tran Mills Collective 71c5076b69SRichard Tran Mills 724165533cSJose E. Roman Input Parameters: 73*20f4b53cSBarry Smith + dm - `DMSHELL` 74c5076b69SRichard Tran Mills . l - local vector 75*20f4b53cSBarry Smith . mode - `InsertMode` 76c5076b69SRichard Tran Mills - g - global vector 77c5076b69SRichard Tran Mills 78c5076b69SRichard Tran Mills Level: advanced 79c5076b69SRichard Tran Mills 80*20f4b53cSBarry Smith Note: 81*20f4b53cSBarry Smith This is not normally called directly by user code, generally user code calls `DMLocalToGlobalBegin()` and `DMLocalToGlobalEnd()`. If the user provides their own custom routines to `DMShellSetLocalToGlobal()` then those routines might have reason to call this function. 82c5076b69SRichard Tran Mills 83*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMLocalToGlobalEndDefaultShell()` 84c5076b69SRichard Tran Mills @*/ 85d71ae5a4SJacob Faibussowitsch PetscErrorCode DMLocalToGlobalBeginDefaultShell(DM dm, Vec l, InsertMode mode, Vec g) 86d71ae5a4SJacob Faibussowitsch { 87c5076b69SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 88c5076b69SRichard Tran Mills 89c5076b69SRichard Tran Mills PetscFunctionBegin; 907a8be351SBarry Smith PetscCheck(shell->ltog, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetLocalToGlobalVecScatter()"); 919566063dSJacob Faibussowitsch PetscCall(VecScatterBegin(shell->ltog, l, g, mode, SCATTER_FORWARD)); 923ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 93c5076b69SRichard Tran Mills } 94c5076b69SRichard Tran Mills 95c5076b69SRichard Tran Mills /*@ 96*20f4b53cSBarry Smith DMLocalToGlobalEndDefaultShell - Uses the LocalToGlobal `VecScatter` context set by the user to end a local to global scatter 97c5076b69SRichard Tran Mills Collective 98c5076b69SRichard Tran Mills 994165533cSJose E. Roman Input Parameters: 100*20f4b53cSBarry Smith + dm - `DMSHELL` 101c5076b69SRichard Tran Mills . l - local vector 102*20f4b53cSBarry Smith . mode - `InsertMode` 103c5076b69SRichard Tran Mills - g - global vector 104c5076b69SRichard Tran Mills 105c5076b69SRichard Tran Mills Level: advanced 106c5076b69SRichard Tran Mills 107*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMLocalToGlobalBeginDefaultShell()` 108c5076b69SRichard Tran Mills @*/ 109d71ae5a4SJacob Faibussowitsch PetscErrorCode DMLocalToGlobalEndDefaultShell(DM dm, Vec l, InsertMode mode, Vec g) 110d71ae5a4SJacob Faibussowitsch { 111c5076b69SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 112c5076b69SRichard Tran Mills 113c5076b69SRichard Tran Mills PetscFunctionBegin; 1147a8be351SBarry Smith PetscCheck(shell->ltog, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetLocalToGlobalVecScatter()"); 1159566063dSJacob Faibussowitsch PetscCall(VecScatterEnd(shell->ltog, l, g, mode, SCATTER_FORWARD)); 1163ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 117c5076b69SRichard Tran Mills } 118c5076b69SRichard Tran Mills 119f3db62a7SRichard Tran Mills /*@ 120*20f4b53cSBarry Smith DMLocalToLocalBeginDefaultShell - Uses the LocalToLocal `VecScatter` context set by the user to begin a local to local scatter 121f3db62a7SRichard Tran Mills Collective 122f3db62a7SRichard Tran Mills 1234165533cSJose E. Roman Input Parameters: 124*20f4b53cSBarry Smith + dm - `DMSHELL` 125f3db62a7SRichard Tran Mills . g - the original local vector 126*20f4b53cSBarry Smith - mode - `InsertMode` 127f3db62a7SRichard Tran Mills 128f3db62a7SRichard Tran Mills Output Parameter: 129f3db62a7SRichard Tran Mills . l - the local vector with correct ghost values 130f3db62a7SRichard Tran Mills 131f3db62a7SRichard Tran Mills Level: advanced 132f3db62a7SRichard Tran Mills 133*20f4b53cSBarry Smith Note: 134*20f4b53cSBarry Smith This is not normally called directly by user code, generally user code calls `DMLocalToLocalBegin()` and `DMLocalToLocalEnd()`. If the user provides their own custom routines to `DMShellSetLocalToLocal()` then those routines might have reason to call this function. 135f3db62a7SRichard Tran Mills 136*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMLocalToLocalEndDefaultShell()` 137f3db62a7SRichard Tran Mills @*/ 138d71ae5a4SJacob Faibussowitsch PetscErrorCode DMLocalToLocalBeginDefaultShell(DM dm, Vec g, InsertMode mode, Vec l) 139d71ae5a4SJacob Faibussowitsch { 140f3db62a7SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 141f3db62a7SRichard Tran Mills 142f3db62a7SRichard Tran Mills PetscFunctionBegin; 1437a8be351SBarry Smith PetscCheck(shell->ltol, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetLocalToLocalVecScatter()"); 1449566063dSJacob Faibussowitsch PetscCall(VecScatterBegin(shell->ltol, g, l, mode, SCATTER_FORWARD)); 1453ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 146f3db62a7SRichard Tran Mills } 147f3db62a7SRichard Tran Mills 148f3db62a7SRichard Tran Mills /*@ 149*20f4b53cSBarry Smith DMLocalToLocalEndDefaultShell - Uses the LocalToLocal `VecScatter` context set by the user to end a local to local scatter 150f3db62a7SRichard Tran Mills Collective 151f3db62a7SRichard Tran Mills 1524165533cSJose E. Roman Input Parameters: 153*20f4b53cSBarry Smith + dm - `DMSHELL` 154f3db62a7SRichard Tran Mills . g - the original local vector 155*20f4b53cSBarry Smith - mode - `InsertMode` 156f3db62a7SRichard Tran Mills 157f3db62a7SRichard Tran Mills Output Parameter: 158f3db62a7SRichard Tran Mills . l - the local vector with correct ghost values 159f3db62a7SRichard Tran Mills 160f3db62a7SRichard Tran Mills Level: advanced 161f3db62a7SRichard Tran Mills 162*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMLocalToLocalBeginDefaultShell()` 163f3db62a7SRichard Tran Mills @*/ 164d71ae5a4SJacob Faibussowitsch PetscErrorCode DMLocalToLocalEndDefaultShell(DM dm, Vec g, InsertMode mode, Vec l) 165d71ae5a4SJacob Faibussowitsch { 166f3db62a7SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 167f3db62a7SRichard Tran Mills 168f3db62a7SRichard Tran Mills PetscFunctionBegin; 1697a8be351SBarry Smith PetscCheck(shell->ltol, ((PetscObject)dm)->comm, PETSC_ERR_ARG_WRONGSTATE, "Cannot be used without first setting the scatter context via DMShellSetGlobalToLocalVecScatter()"); 1709566063dSJacob Faibussowitsch PetscCall(VecScatterEnd(shell->ltol, g, l, mode, SCATTER_FORWARD)); 1713ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 172f3db62a7SRichard Tran Mills } 173c5076b69SRichard Tran Mills 174d71ae5a4SJacob Faibussowitsch static PetscErrorCode DMCreateMatrix_Shell(DM dm, Mat *J) 175d71ae5a4SJacob Faibussowitsch { 176fe1899a2SJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 177fe1899a2SJed Brown Mat A; 178fe1899a2SJed Brown 179fe1899a2SJed Brown PetscFunctionBegin; 180fe1899a2SJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 181064a246eSJacob Faibussowitsch PetscValidPointer(J, 2); 1827bde9f88SJed Brown if (!shell->A) { 1837bde9f88SJed Brown if (shell->Xglobal) { 1847bde9f88SJed Brown PetscInt m, M; 1859566063dSJacob Faibussowitsch PetscCall(PetscInfo(dm, "Naively creating matrix using global vector distribution without preallocation\n")); 1869566063dSJacob Faibussowitsch PetscCall(VecGetSize(shell->Xglobal, &M)); 1879566063dSJacob Faibussowitsch PetscCall(VecGetLocalSize(shell->Xglobal, &m)); 1889566063dSJacob Faibussowitsch PetscCall(MatCreate(PetscObjectComm((PetscObject)dm), &shell->A)); 1899566063dSJacob Faibussowitsch PetscCall(MatSetSizes(shell->A, m, m, M, M)); 1909566063dSJacob Faibussowitsch PetscCall(MatSetType(shell->A, dm->mattype)); 1919566063dSJacob Faibussowitsch PetscCall(MatSetUp(shell->A)); 192ce94432eSBarry Smith } else SETERRQ(PetscObjectComm((PetscObject)dm), PETSC_ERR_USER, "Must call DMShellSetMatrix(), DMShellSetCreateMatrix(), or provide a vector"); 1937bde9f88SJed Brown } 194fe1899a2SJed Brown A = shell->A; 1959566063dSJacob Faibussowitsch PetscCall(MatDuplicate(A, MAT_SHARE_NONZERO_PATTERN, J)); 1969566063dSJacob Faibussowitsch PetscCall(MatSetDM(*J, dm)); 1973ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 198fe1899a2SJed Brown } 199fe1899a2SJed Brown 200d71ae5a4SJacob Faibussowitsch PetscErrorCode DMCreateGlobalVector_Shell(DM dm, Vec *gvec) 201d71ae5a4SJacob Faibussowitsch { 202fe1899a2SJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 203fe1899a2SJed Brown Vec X; 204fe1899a2SJed Brown 205fe1899a2SJed Brown PetscFunctionBegin; 206fe1899a2SJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 207fe1899a2SJed Brown PetscValidPointer(gvec, 2); 208ea78f98cSLisandro Dalcin *gvec = NULL; 209fe1899a2SJed Brown X = shell->Xglobal; 2107a8be351SBarry Smith PetscCheck(X, PetscObjectComm((PetscObject)dm), PETSC_ERR_USER, "Must call DMShellSetGlobalVector() or DMShellSetCreateGlobalVector()"); 21106f803f6SStefano Zampini /* Need to create a copy in order to attach the DM to the vector */ 2129566063dSJacob Faibussowitsch PetscCall(VecDuplicate(X, gvec)); 2139566063dSJacob Faibussowitsch PetscCall(VecZeroEntries(*gvec)); 2149566063dSJacob Faibussowitsch PetscCall(VecSetDM(*gvec, dm)); 2153ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 216fe1899a2SJed Brown } 217fe1899a2SJed Brown 218d71ae5a4SJacob Faibussowitsch PetscErrorCode DMCreateLocalVector_Shell(DM dm, Vec *gvec) 219d71ae5a4SJacob Faibussowitsch { 220dc43b69eSJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 221dc43b69eSJed Brown Vec X; 222dc43b69eSJed Brown 223dc43b69eSJed Brown PetscFunctionBegin; 224dc43b69eSJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 225dc43b69eSJed Brown PetscValidPointer(gvec, 2); 226ea78f98cSLisandro Dalcin *gvec = NULL; 227dc43b69eSJed Brown X = shell->Xlocal; 2287a8be351SBarry Smith PetscCheck(X, PetscObjectComm((PetscObject)dm), PETSC_ERR_USER, "Must call DMShellSetLocalVector() or DMShellSetCreateLocalVector()"); 22906f803f6SStefano Zampini /* Need to create a copy in order to attach the DM to the vector */ 2309566063dSJacob Faibussowitsch PetscCall(VecDuplicate(X, gvec)); 2319566063dSJacob Faibussowitsch PetscCall(VecZeroEntries(*gvec)); 2329566063dSJacob Faibussowitsch PetscCall(VecSetDM(*gvec, dm)); 2333ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 234dc43b69eSJed Brown } 235dc43b69eSJed Brown 236fef3a512SBarry Smith /*@ 23709904cd0SBarry Smith DMShellSetDestroyContext - set a function that destroys the context provided with `DMShellSetContext()` 23809904cd0SBarry Smith 23909904cd0SBarry Smith Collective 24009904cd0SBarry Smith 24109904cd0SBarry Smith Input Parameters: 24209904cd0SBarry Smith . ctx - the context 24309904cd0SBarry Smith 24409904cd0SBarry Smith Level: advanced 24509904cd0SBarry Smith 246*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetContext()`, `DMShellGetContext()` 24709904cd0SBarry Smith @*/ 248d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetDestroyContext(DM dm, PetscErrorCode (*destroyctx)(void *)) 249d71ae5a4SJacob Faibussowitsch { 25009904cd0SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 25109904cd0SBarry Smith PetscBool isshell; 25209904cd0SBarry Smith 25309904cd0SBarry Smith PetscFunctionBegin; 25409904cd0SBarry Smith PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 25509904cd0SBarry Smith PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 2563ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 25709904cd0SBarry Smith shell->destroyctx = destroyctx; 2583ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 25909904cd0SBarry Smith } 26009904cd0SBarry Smith 26109904cd0SBarry Smith /*@ 262*20f4b53cSBarry Smith DMShellSetContext - set some data to be usable by this `DMSHELL` 263fef3a512SBarry Smith 264fef3a512SBarry Smith Collective 265fef3a512SBarry Smith 2664165533cSJose E. Roman Input Parameters: 267*20f4b53cSBarry Smith + dm - `DMSHELL` 268fef3a512SBarry Smith - ctx - the context 269fef3a512SBarry Smith 270fef3a512SBarry Smith Level: advanced 271fef3a512SBarry Smith 272*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateMatrix()`, `DMShellGetContext()` 273fef3a512SBarry Smith @*/ 274d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetContext(DM dm, void *ctx) 275d71ae5a4SJacob Faibussowitsch { 276fef3a512SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 277fef3a512SBarry Smith PetscBool isshell; 278fef3a512SBarry Smith 279fef3a512SBarry Smith PetscFunctionBegin; 280fef3a512SBarry Smith PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 2819566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 2823ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 283fef3a512SBarry Smith shell->ctx = ctx; 2843ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 285fef3a512SBarry Smith } 286fef3a512SBarry Smith 287fef3a512SBarry Smith /*@ 288*20f4b53cSBarry Smith DMShellGetContext - Returns the user-provided context associated to the `DMSHELL` 289fef3a512SBarry Smith 290fef3a512SBarry Smith Collective 291fef3a512SBarry Smith 2924165533cSJose E. Roman Input Parameter: 293*20f4b53cSBarry Smith . dm - `DMSHELL` 294fef3a512SBarry Smith 2954165533cSJose E. Roman Output Parameter: 296fef3a512SBarry Smith . ctx - the context 297fef3a512SBarry Smith 298fef3a512SBarry Smith Level: advanced 299fef3a512SBarry Smith 300*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateMatrix()`, `DMShellSetContext()` 301fef3a512SBarry Smith @*/ 302d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetContext(DM dm, void *ctx) 303d71ae5a4SJacob Faibussowitsch { 304fef3a512SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 305fef3a512SBarry Smith PetscBool isshell; 306fef3a512SBarry Smith 307fef3a512SBarry Smith PetscFunctionBegin; 308fef3a512SBarry Smith PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 3099566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 3107a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 3113ec1f749SStefano Zampini *(void **)ctx = shell->ctx; 3123ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 313fef3a512SBarry Smith } 314fef3a512SBarry Smith 315fe1899a2SJed Brown /*@ 316*20f4b53cSBarry Smith DMShellSetMatrix - sets a template matrix associated with the `DMSHELL` 317fe1899a2SJed Brown 318fe1899a2SJed Brown Collective 319fe1899a2SJed Brown 3204165533cSJose E. Roman Input Parameters: 321*20f4b53cSBarry Smith + dm - `DMSHELL` 322fe1899a2SJed Brown - J - template matrix 323fe1899a2SJed Brown 324fe1899a2SJed Brown Level: advanced 325fe1899a2SJed Brown 32606f803f6SStefano Zampini Developer Notes: 327*20f4b53cSBarry Smith To avoid circular references, if `J` is already associated to the same `DM`, then `MatDuplicate`(`SHARE_NONZERO_PATTERN`) is called, followed by removing the `DM` reference from the private template. 32806f803f6SStefano Zampini 329*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateMatrix()`, `DMShellSetCreateMatrix()`, `DMShellSetContext()`, `DMShellGetContext()` 330fe1899a2SJed Brown @*/ 331d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetMatrix(DM dm, Mat J) 332d71ae5a4SJacob Faibussowitsch { 333fe1899a2SJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 3348c87107bSJed Brown PetscBool isshell; 33506f803f6SStefano Zampini DM mdm; 336fe1899a2SJed Brown 337fe1899a2SJed Brown PetscFunctionBegin; 3388c87107bSJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 3398c87107bSJed Brown PetscValidHeaderSpecific(J, MAT_CLASSID, 2); 3409566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 3413ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 3423ba16761SJacob Faibussowitsch if (J == shell->A) PetscFunctionReturn(PETSC_SUCCESS); 3439566063dSJacob Faibussowitsch PetscCall(MatGetDM(J, &mdm)); 3449566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)J)); 3459566063dSJacob Faibussowitsch PetscCall(MatDestroy(&shell->A)); 34606f803f6SStefano Zampini if (mdm == dm) { 3479566063dSJacob Faibussowitsch PetscCall(MatDuplicate(J, MAT_SHARE_NONZERO_PATTERN, &shell->A)); 3489566063dSJacob Faibussowitsch PetscCall(MatSetDM(shell->A, NULL)); 34906f803f6SStefano Zampini } else shell->A = J; 3503ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 351fe1899a2SJed Brown } 352fe1899a2SJed Brown 353fe1899a2SJed Brown /*@C 354*20f4b53cSBarry Smith DMShellSetCreateMatrix - sets the routine to create a matrix associated with the `DMSHELL` 355fe1899a2SJed Brown 356*20f4b53cSBarry Smith Logically Collective 357fe1899a2SJed Brown 3584165533cSJose E. Roman Input Parameters: 359*20f4b53cSBarry Smith + dm - the `DMSHELL` 360fe1899a2SJed Brown - func - the function to create a matrix 361fe1899a2SJed Brown 362fe1899a2SJed Brown Level: advanced 363fe1899a2SJed Brown 364*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateMatrix()`, `DMShellSetMatrix()`, `DMShellSetContext()`, `DMShellGetContext()` 365fe1899a2SJed Brown @*/ 366d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateMatrix(DM dm, PetscErrorCode (*func)(DM, Mat *)) 367d71ae5a4SJacob Faibussowitsch { 368fe1899a2SJed Brown PetscFunctionBegin; 369fe1899a2SJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 370fe1899a2SJed Brown dm->ops->creatematrix = func; 3713ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 372fe1899a2SJed Brown } 373fe1899a2SJed Brown 374fe1899a2SJed Brown /*@ 375*20f4b53cSBarry Smith DMShellSetGlobalVector - sets a template global vector associated with the `DMSHELL` 376fe1899a2SJed Brown 377*20f4b53cSBarry Smith Logically Collective 378fe1899a2SJed Brown 3794165533cSJose E. Roman Input Parameters: 380*20f4b53cSBarry Smith + dm - `DMSHELL` 381fe1899a2SJed Brown - X - template vector 382fe1899a2SJed Brown 383fe1899a2SJed Brown Level: advanced 384fe1899a2SJed Brown 385*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateGlobalVector()`, `DMShellSetMatrix()`, `DMShellSetCreateGlobalVector()` 386fe1899a2SJed Brown @*/ 387d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetGlobalVector(DM dm, Vec X) 388d71ae5a4SJacob Faibussowitsch { 389fe1899a2SJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 3908c87107bSJed Brown PetscBool isshell; 391cca7ec1eSBarry Smith DM vdm; 392fe1899a2SJed Brown 393fe1899a2SJed Brown PetscFunctionBegin; 3948c87107bSJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 3958c87107bSJed Brown PetscValidHeaderSpecific(X, VEC_CLASSID, 2); 3969566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 3973ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 3989566063dSJacob Faibussowitsch PetscCall(VecGetDM(X, &vdm)); 399cca7ec1eSBarry Smith /* 400cca7ec1eSBarry Smith if the vector proposed as the new base global vector for the DM is a DM vector associated 401cca7ec1eSBarry Smith with the same DM then the current base global vector for the DM is ok and if we replace it with the new one 402cca7ec1eSBarry Smith we get a circular dependency that prevents the DM from being destroy when it should be. 403cca7ec1eSBarry Smith This occurs when SNESSet/GetNPC() is used with a SNES that does not have a user provided 404cca7ec1eSBarry Smith DM attached to it since the inner SNES (which shares the DM with the outer SNES) tries 405cca7ec1eSBarry Smith to set its input vector (which is associated with the DM) as the base global vector. 406cca7ec1eSBarry Smith Thanks to Juan P. Mendez Granado Re: [petsc-maint] Nonlinear conjugate gradien 407cca7ec1eSBarry Smith for pointing out the problem. 408cca7ec1eSBarry Smith */ 4093ba16761SJacob Faibussowitsch if (vdm == dm) PetscFunctionReturn(PETSC_SUCCESS); 4109566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)X)); 4119566063dSJacob Faibussowitsch PetscCall(VecDestroy(&shell->Xglobal)); 412fe1899a2SJed Brown shell->Xglobal = X; 4133ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 414fe1899a2SJed Brown } 415fe1899a2SJed Brown 41604d741b1SMatthew G. Knepley /*@ 417*20f4b53cSBarry Smith DMShellGetGlobalVector - Returns the template global vector associated with the `DMSHELL`, or `NULL` if it was not set 41804d741b1SMatthew G. Knepley 419*20f4b53cSBarry Smith Not Collective 42004d741b1SMatthew G. Knepley 4214165533cSJose E. Roman Input Parameters: 422*20f4b53cSBarry Smith + dm - `DMSHELL` 42304d741b1SMatthew G. Knepley - X - template vector 42404d741b1SMatthew G. Knepley 42504d741b1SMatthew G. Knepley Level: advanced 42604d741b1SMatthew G. Knepley 427*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetGlobalVector()`, `DMShellSetCreateGlobalVector()`, `DMCreateGlobalVector()` 42804d741b1SMatthew G. Knepley @*/ 429d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetGlobalVector(DM dm, Vec *X) 430d71ae5a4SJacob Faibussowitsch { 43104d741b1SMatthew G. Knepley DM_Shell *shell = (DM_Shell *)dm->data; 43204d741b1SMatthew G. Knepley PetscBool isshell; 43304d741b1SMatthew G. Knepley 43404d741b1SMatthew G. Knepley PetscFunctionBegin; 43504d741b1SMatthew G. Knepley PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 43604d741b1SMatthew G. Knepley PetscValidPointer(X, 2); 4379566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 4383ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 43904d741b1SMatthew G. Knepley *X = shell->Xglobal; 4403ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 44104d741b1SMatthew G. Knepley } 44204d741b1SMatthew G. Knepley 443fe1899a2SJed Brown /*@C 444*20f4b53cSBarry Smith DMShellSetCreateGlobalVector - sets the routine to create a global vector associated with the `DMSHELL` 445fe1899a2SJed Brown 446fe1899a2SJed Brown Logically Collective 447fe1899a2SJed Brown 4484165533cSJose E. Roman Input Parameters: 449*20f4b53cSBarry Smith + dm - the `DMSHELL` 450fe1899a2SJed Brown - func - the creation routine 451fe1899a2SJed Brown 452fe1899a2SJed Brown Level: advanced 453fe1899a2SJed Brown 454*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetGlobalVector()`, `DMShellSetCreateMatrix()`, `DMShellSetContext()`, `DMShellGetContext()` 455fe1899a2SJed Brown @*/ 456d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateGlobalVector(DM dm, PetscErrorCode (*func)(DM, Vec *)) 457d71ae5a4SJacob Faibussowitsch { 458fe1899a2SJed Brown PetscFunctionBegin; 459fe1899a2SJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 460fe1899a2SJed Brown dm->ops->createglobalvector = func; 4613ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 462fe1899a2SJed Brown } 463fe1899a2SJed Brown 464dc43b69eSJed Brown /*@ 465*20f4b53cSBarry Smith DMShellSetLocalVector - sets a template local vector associated with the `DMSHELL` 466dc43b69eSJed Brown 467*20f4b53cSBarry Smith Logically Collective 468dc43b69eSJed Brown 4694165533cSJose E. Roman Input Parameters: 470*20f4b53cSBarry Smith + dm - `DMSHELL` 471dc43b69eSJed Brown - X - template vector 472dc43b69eSJed Brown 473dc43b69eSJed Brown Level: advanced 474dc43b69eSJed Brown 475*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateLocalVector()`, `DMShellSetMatrix()`, `DMShellSetCreateLocalVector()` 476dc43b69eSJed Brown @*/ 477d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetLocalVector(DM dm, Vec X) 478d71ae5a4SJacob Faibussowitsch { 479dc43b69eSJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 480dc43b69eSJed Brown PetscBool isshell; 481cca7ec1eSBarry Smith DM vdm; 482dc43b69eSJed Brown 483dc43b69eSJed Brown PetscFunctionBegin; 484dc43b69eSJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 485dc43b69eSJed Brown PetscValidHeaderSpecific(X, VEC_CLASSID, 2); 4869566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 4873ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 4889566063dSJacob Faibussowitsch PetscCall(VecGetDM(X, &vdm)); 489cca7ec1eSBarry Smith /* 490cca7ec1eSBarry Smith if the vector proposed as the new base global vector for the DM is a DM vector associated 491cca7ec1eSBarry Smith with the same DM then the current base global vector for the DM is ok and if we replace it with the new one 492cca7ec1eSBarry Smith we get a circular dependency that prevents the DM from being destroy when it should be. 493cca7ec1eSBarry Smith This occurs when SNESSet/GetNPC() is used with a SNES that does not have a user provided 494cca7ec1eSBarry Smith DM attached to it since the inner SNES (which shares the DM with the outer SNES) tries 495cca7ec1eSBarry Smith to set its input vector (which is associated with the DM) as the base global vector. 496cca7ec1eSBarry Smith Thanks to Juan P. Mendez Granado Re: [petsc-maint] Nonlinear conjugate gradien 497cca7ec1eSBarry Smith for pointing out the problem. 498cca7ec1eSBarry Smith */ 4993ba16761SJacob Faibussowitsch if (vdm == dm) PetscFunctionReturn(PETSC_SUCCESS); 5009566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)X)); 5019566063dSJacob Faibussowitsch PetscCall(VecDestroy(&shell->Xlocal)); 502dc43b69eSJed Brown shell->Xlocal = X; 5033ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 504dc43b69eSJed Brown } 505dc43b69eSJed Brown 506dc43b69eSJed Brown /*@C 507*20f4b53cSBarry Smith DMShellSetCreateLocalVector - sets the routine to create a local vector associated with the `DMSHELL` 508dc43b69eSJed Brown 509dc43b69eSJed Brown Logically Collective 510dc43b69eSJed Brown 5114165533cSJose E. Roman Input Parameters: 512*20f4b53cSBarry Smith + dm - the `DMSHELL` 513dc43b69eSJed Brown - func - the creation routine 514dc43b69eSJed Brown 515dc43b69eSJed Brown Level: advanced 516dc43b69eSJed Brown 517*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetLocalVector()`, `DMShellSetCreateMatrix()`, `DMShellSetContext()`, `DMShellGetContext()` 518dc43b69eSJed Brown @*/ 519d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateLocalVector(DM dm, PetscErrorCode (*func)(DM, Vec *)) 520d71ae5a4SJacob Faibussowitsch { 521dc43b69eSJed Brown PetscFunctionBegin; 522dc43b69eSJed Brown PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 523dc43b69eSJed Brown dm->ops->createlocalvector = func; 5243ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 525dc43b69eSJed Brown } 526dc43b69eSJed Brown 5278339e6d0SRichard Tran Mills /*@C 5288339e6d0SRichard Tran Mills DMShellSetGlobalToLocal - Sets the routines used to perform a global to local scatter 5298339e6d0SRichard Tran Mills 530d083f849SBarry Smith Logically Collective on dm 5318339e6d0SRichard Tran Mills 5324165533cSJose E. Roman Input Parameters 533*20f4b53cSBarry Smith + dm - the `DMSHELL` 5348339e6d0SRichard Tran Mills . begin - the routine that begins the global to local scatter 5358339e6d0SRichard Tran Mills - end - the routine that ends the global to local scatter 5368339e6d0SRichard Tran Mills 5378339e6d0SRichard Tran Mills Level: advanced 5388339e6d0SRichard Tran Mills 539*20f4b53cSBarry Smith Note: 540*20f4b53cSBarry Smith If these functions are not provided but `DMShellSetGlobalToLocalVecScatter()` is called then 541*20f4b53cSBarry Smith `DMGlobalToLocalBeginDefaultShell()`/`DMGlobalToLocalEndDefaultShell()` are used to to perform the transfers 542*20f4b53cSBarry Smith 543*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetLocalToGlobal()`, `DMGlobalToLocalBeginDefaultShell()`, `DMGlobalToLocalEndDefaultShell()` 5448339e6d0SRichard Tran Mills @*/ 545d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetGlobalToLocal(DM dm, PetscErrorCode (*begin)(DM, Vec, InsertMode, Vec), PetscErrorCode (*end)(DM, Vec, InsertMode, Vec)) 546d71ae5a4SJacob Faibussowitsch { 5478339e6d0SRichard Tran Mills PetscFunctionBegin; 5482d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 5498339e6d0SRichard Tran Mills dm->ops->globaltolocalbegin = begin; 5508339e6d0SRichard Tran Mills dm->ops->globaltolocalend = end; 5513ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 5528339e6d0SRichard Tran Mills } 5538339e6d0SRichard Tran Mills 5548339e6d0SRichard Tran Mills /*@C 5558339e6d0SRichard Tran Mills DMShellSetLocalToGlobal - Sets the routines used to perform a local to global scatter 5568339e6d0SRichard Tran Mills 557d083f849SBarry Smith Logically Collective on dm 5588339e6d0SRichard Tran Mills 5594165533cSJose E. Roman Input Parameters 560*20f4b53cSBarry Smith + dm - the `DMSHELL` 5618339e6d0SRichard Tran Mills . begin - the routine that begins the local to global scatter 5628339e6d0SRichard Tran Mills - end - the routine that ends the local to global scatter 5638339e6d0SRichard Tran Mills 5648339e6d0SRichard Tran Mills Level: advanced 5658339e6d0SRichard Tran Mills 566*20f4b53cSBarry Smith Note: 567*20f4b53cSBarry Smith If these functions are not provided but `DMShellSetLocalToGlobalVecScatter()` is called then 568*20f4b53cSBarry Smith `DMLocalToGlobalBeginDefaultShell()`/`DMLocalToGlobalEndDefaultShell()` are used to to perform the transfers 569*20f4b53cSBarry Smith 570*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetGlobalToLocal()` 5718339e6d0SRichard Tran Mills @*/ 572d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetLocalToGlobal(DM dm, PetscErrorCode (*begin)(DM, Vec, InsertMode, Vec), PetscErrorCode (*end)(DM, Vec, InsertMode, Vec)) 573d71ae5a4SJacob Faibussowitsch { 5748339e6d0SRichard Tran Mills PetscFunctionBegin; 5752d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 5768339e6d0SRichard Tran Mills dm->ops->localtoglobalbegin = begin; 5778339e6d0SRichard Tran Mills dm->ops->localtoglobalend = end; 5783ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 5798339e6d0SRichard Tran Mills } 5808339e6d0SRichard Tran Mills 581f3db62a7SRichard Tran Mills /*@C 582f3db62a7SRichard Tran Mills DMShellSetLocalToLocal - Sets the routines used to perform a local to local scatter 583f3db62a7SRichard Tran Mills 584d083f849SBarry Smith Logically Collective on dm 585f3db62a7SRichard Tran Mills 5864165533cSJose E. Roman Input Parameters 587*20f4b53cSBarry Smith + dm - the `DMSHELL` 588f3db62a7SRichard Tran Mills . begin - the routine that begins the local to local scatter 589f3db62a7SRichard Tran Mills - end - the routine that ends the local to local scatter 590f3db62a7SRichard Tran Mills 591f3db62a7SRichard Tran Mills Level: advanced 592f3db62a7SRichard Tran Mills 593*20f4b53cSBarry Smith Note: 594*20f4b53cSBarry Smith If these functions are not provided but `DMShellSetLocalToLocalVecScatter()` is called then 595*20f4b53cSBarry Smith `DMLocalToLocalBeginDefaultShell()`/`DMLocalToLocalEndDefaultShell()` are used to to perform the transfers 596*20f4b53cSBarry Smith 597*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetGlobalToLocal()`, `DMLocalToLocalBeginDefaultShell()`, `DMLocalToLocalEndDefaultShell()` 598f3db62a7SRichard Tran Mills @*/ 599d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetLocalToLocal(DM dm, PetscErrorCode (*begin)(DM, Vec, InsertMode, Vec), PetscErrorCode (*end)(DM, Vec, InsertMode, Vec)) 600d71ae5a4SJacob Faibussowitsch { 601f3db62a7SRichard Tran Mills PetscFunctionBegin; 6022d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 603f3db62a7SRichard Tran Mills dm->ops->localtolocalbegin = begin; 604f3db62a7SRichard Tran Mills dm->ops->localtolocalend = end; 6053ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 606f3db62a7SRichard Tran Mills } 607f3db62a7SRichard Tran Mills 60881634712SRichard Tran Mills /*@ 609*20f4b53cSBarry Smith DMShellSetGlobalToLocalVecScatter - Sets a `VecScatter` context for global to local communication 61081634712SRichard Tran Mills 611d083f849SBarry Smith Logically Collective on dm 61281634712SRichard Tran Mills 6134165533cSJose E. Roman Input Parameters 614*20f4b53cSBarry Smith + dm - the `DMSHELL` 615*20f4b53cSBarry Smith - gtol - the global to local `VecScatter` context 61681634712SRichard Tran Mills 61781634712SRichard Tran Mills Level: advanced 61881634712SRichard Tran Mills 619*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetGlobalToLocal()`, `DMGlobalToLocalBeginDefaultShell()`, `DMGlobalToLocalEndDefaultShell()` 62081634712SRichard Tran Mills @*/ 621d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetGlobalToLocalVecScatter(DM dm, VecScatter gtol) 622d71ae5a4SJacob Faibussowitsch { 62381634712SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 62481634712SRichard Tran Mills 625b300e4a8SRichard Tran Mills PetscFunctionBegin; 6262d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 62797929ea7SJunchao Zhang PetscValidHeaderSpecific(gtol, PETSCSF_CLASSID, 2); 6289566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)gtol)); 6299566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->gtol)); 63081634712SRichard Tran Mills shell->gtol = gtol; 6313ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 63281634712SRichard Tran Mills } 63381634712SRichard Tran Mills 634988ea7d6SRichard Tran Mills /*@ 635*20f4b53cSBarry Smith DMShellSetLocalToGlobalVecScatter - Sets a` VecScatter` context for local to global communication 636988ea7d6SRichard Tran Mills 637d083f849SBarry Smith Logically Collective on dm 638988ea7d6SRichard Tran Mills 6394165533cSJose E. Roman Input Parameters 640*20f4b53cSBarry Smith + dm - the `DMSHELL` 641*20f4b53cSBarry Smith - ltog - the local to global `VecScatter` context 642988ea7d6SRichard Tran Mills 643988ea7d6SRichard Tran Mills Level: advanced 644988ea7d6SRichard Tran Mills 645*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetLocalToGlobal()`, `DMLocalToGlobalBeginDefaultShell()`, `DMLocalToGlobalEndDefaultShell()` 646988ea7d6SRichard Tran Mills @*/ 647d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetLocalToGlobalVecScatter(DM dm, VecScatter ltog) 648d71ae5a4SJacob Faibussowitsch { 649988ea7d6SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 650988ea7d6SRichard Tran Mills 651988ea7d6SRichard Tran Mills PetscFunctionBegin; 6522d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 65397929ea7SJunchao Zhang PetscValidHeaderSpecific(ltog, PETSCSF_CLASSID, 2); 6549566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)ltog)); 6559566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->ltog)); 656988ea7d6SRichard Tran Mills shell->ltog = ltog; 6573ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 658988ea7d6SRichard Tran Mills } 659988ea7d6SRichard Tran Mills 660f3db62a7SRichard Tran Mills /*@ 661*20f4b53cSBarry Smith DMShellSetLocalToLocalVecScatter - Sets a `VecScatter` context for local to local communication 662f3db62a7SRichard Tran Mills 663*20f4b53cSBarry Smith Logically Collective 664f3db62a7SRichard Tran Mills 6654165533cSJose E. Roman Input Parameters 666*20f4b53cSBarry Smith + dm - the `DMSHELL` 667*20f4b53cSBarry Smith - ltol - the local to local `VecScatter` context 668f3db62a7SRichard Tran Mills 669f3db62a7SRichard Tran Mills Level: advanced 670f3db62a7SRichard Tran Mills 671*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetLocalToLocal()`, `DMLocalToLocalBeginDefaultShell()`, `DMLocalToLocalEndDefaultShell()` 672f3db62a7SRichard Tran Mills @*/ 673d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetLocalToLocalVecScatter(DM dm, VecScatter ltol) 674d71ae5a4SJacob Faibussowitsch { 675f3db62a7SRichard Tran Mills DM_Shell *shell = (DM_Shell *)dm->data; 676f3db62a7SRichard Tran Mills 677f3db62a7SRichard Tran Mills PetscFunctionBegin; 6782d1bcd87SStefano Zampini PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 67997929ea7SJunchao Zhang PetscValidHeaderSpecific(ltol, PETSCSF_CLASSID, 2); 6809566063dSJacob Faibussowitsch PetscCall(PetscObjectReference((PetscObject)ltol)); 6819566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->ltol)); 682f3db62a7SRichard Tran Mills shell->ltol = ltol; 6833ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 684f3db62a7SRichard Tran Mills } 685f3db62a7SRichard Tran Mills 6869bf9660cSLawrence Mitchell /*@C 687*20f4b53cSBarry Smith DMShellSetCoarsen - Set the routine used to coarsen the `DMSHELL` 6889bf9660cSLawrence Mitchell 689*20f4b53cSBarry Smith Logically Collective 6909bf9660cSLawrence Mitchell 6914165533cSJose E. Roman Input Parameters 692*20f4b53cSBarry Smith + dm - the `DMSHELL` 693*20f4b53cSBarry Smith - coarsen - the routine that coarsens the `DM` 6949bf9660cSLawrence Mitchell 6959bf9660cSLawrence Mitchell Level: advanced 6969bf9660cSLawrence Mitchell 697*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetRefine()`, `DMCoarsen()`, `DMShellGetCoarsen()`, `DMShellSetContext()`, `DMShellGetContext()` 6989bf9660cSLawrence Mitchell @*/ 699d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCoarsen(DM dm, PetscErrorCode (*coarsen)(DM, MPI_Comm, DM *)) 700d71ae5a4SJacob Faibussowitsch { 701f572501eSLawrence Mitchell PetscBool isshell; 702f572501eSLawrence Mitchell 703f572501eSLawrence Mitchell PetscFunctionBegin; 704f572501eSLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 7059566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 7063ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 707f572501eSLawrence Mitchell dm->ops->coarsen = coarsen; 7083ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 709f572501eSLawrence Mitchell } 710f572501eSLawrence Mitchell 7119bf9660cSLawrence Mitchell /*@C 712*20f4b53cSBarry Smith DMShellGetCoarsen - Get the routine used to coarsen the `DMSHELL` 7134363ddcaSBoris Boutkov 714*20f4b53cSBarry Smith Logically Collective 7154363ddcaSBoris Boutkov 7164165533cSJose E. Roman Input Parameter: 717*20f4b53cSBarry Smith . dm - the `DMSHELL` 7184363ddcaSBoris Boutkov 7194165533cSJose E. Roman Output Parameter: 720*20f4b53cSBarry Smith . coarsen - the routine that coarsens the `DM` 7214363ddcaSBoris Boutkov 7224363ddcaSBoris Boutkov Level: advanced 7234363ddcaSBoris Boutkov 724*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCoarsen()`, `DMCoarsen()`, `DMShellSetRefine()`, `DMRefine()` 7254363ddcaSBoris Boutkov @*/ 726d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetCoarsen(DM dm, PetscErrorCode (**coarsen)(DM, MPI_Comm, DM *)) 727d71ae5a4SJacob Faibussowitsch { 7284363ddcaSBoris Boutkov PetscBool isshell; 7294363ddcaSBoris Boutkov 7304363ddcaSBoris Boutkov PetscFunctionBegin; 7314363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 7329566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 7337a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 7344363ddcaSBoris Boutkov *coarsen = dm->ops->coarsen; 7353ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 7364363ddcaSBoris Boutkov } 7374363ddcaSBoris Boutkov 7384363ddcaSBoris Boutkov /*@C 739*20f4b53cSBarry Smith DMShellSetRefine - Set the routine used to refine the `DMSHELL` 7409bf9660cSLawrence Mitchell 741*20f4b53cSBarry Smith Logically Collective 7429bf9660cSLawrence Mitchell 7434165533cSJose E. Roman Input Parameters 744*20f4b53cSBarry Smith + dm - the `DMSHELL` 745*20f4b53cSBarry Smith - refine - the routine that refines the `DM` 7469bf9660cSLawrence Mitchell 7479bf9660cSLawrence Mitchell Level: advanced 7489bf9660cSLawrence Mitchell 749*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCoarsen()`, `DMRefine()`, `DMShellGetRefine()`, `DMShellSetContext()`, `DMShellGetContext()` 7509bf9660cSLawrence Mitchell @*/ 751d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetRefine(DM dm, PetscErrorCode (*refine)(DM, MPI_Comm, DM *)) 752d71ae5a4SJacob Faibussowitsch { 753f572501eSLawrence Mitchell PetscBool isshell; 754f572501eSLawrence Mitchell 755f572501eSLawrence Mitchell PetscFunctionBegin; 756f572501eSLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 7579566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 7583ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 759f572501eSLawrence Mitchell dm->ops->refine = refine; 7603ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 761f572501eSLawrence Mitchell } 762f572501eSLawrence Mitchell 7639bf9660cSLawrence Mitchell /*@C 764*20f4b53cSBarry Smith DMShellGetRefine - Get the routine used to refine the `DMSHELL` 7654363ddcaSBoris Boutkov 766*20f4b53cSBarry Smith Logically Collective 7674363ddcaSBoris Boutkov 7684165533cSJose E. Roman Input Parameter: 769*20f4b53cSBarry Smith . dm - the `DMSHELL` 7704363ddcaSBoris Boutkov 7714165533cSJose E. Roman Output Parameter: 772*20f4b53cSBarry Smith . refine - the routine that refines the `DM` 7734363ddcaSBoris Boutkov 7744363ddcaSBoris Boutkov Level: advanced 7754363ddcaSBoris Boutkov 776*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCoarsen()`, `DMCoarsen()`, `DMShellSetRefine()`, `DMRefine()` 7774363ddcaSBoris Boutkov @*/ 778d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetRefine(DM dm, PetscErrorCode (**refine)(DM, MPI_Comm, DM *)) 779d71ae5a4SJacob Faibussowitsch { 7804363ddcaSBoris Boutkov PetscBool isshell; 7814363ddcaSBoris Boutkov 7824363ddcaSBoris Boutkov PetscFunctionBegin; 7834363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 7849566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 7857a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 7864363ddcaSBoris Boutkov *refine = dm->ops->refine; 7873ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 7884363ddcaSBoris Boutkov } 7894363ddcaSBoris Boutkov 7904363ddcaSBoris Boutkov /*@C 7919bf9660cSLawrence Mitchell DMShellSetCreateInterpolation - Set the routine used to create the interpolation operator 7929bf9660cSLawrence Mitchell 793*20f4b53cSBarry Smith Logically Collective 7949bf9660cSLawrence Mitchell 7954165533cSJose E. Roman Input Parameters 796*20f4b53cSBarry Smith + dm - the `DMSHELL` 7979bf9660cSLawrence Mitchell - interp - the routine to create the interpolation 7989bf9660cSLawrence Mitchell 7999bf9660cSLawrence Mitchell Level: advanced 8009bf9660cSLawrence Mitchell 801*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCreateInjection()`, `DMCreateInterpolation()`, `DMShellGetCreateInterpolation()`, `DMShellSetCreateRestriction()`, `DMShellSetContext()`, `DMShellGetContext()` 8029bf9660cSLawrence Mitchell @*/ 803d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateInterpolation(DM dm, PetscErrorCode (*interp)(DM, DM, Mat *, Vec *)) 804d71ae5a4SJacob Faibussowitsch { 805f572501eSLawrence Mitchell PetscBool isshell; 806f572501eSLawrence Mitchell 807f572501eSLawrence Mitchell PetscFunctionBegin; 808f572501eSLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 8099566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 8103ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 811f572501eSLawrence Mitchell dm->ops->createinterpolation = interp; 8123ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 813f572501eSLawrence Mitchell } 814f572501eSLawrence Mitchell 8153ad4599aSBarry Smith /*@C 8164363ddcaSBoris Boutkov DMShellGetCreateInterpolation - Get the routine used to create the interpolation operator 8174363ddcaSBoris Boutkov 818*20f4b53cSBarry Smith Logically Collective 8194363ddcaSBoris Boutkov 8204165533cSJose E. Roman Input Parameter: 821*20f4b53cSBarry Smith . dm - the `DMSHELL` 822a4a986ddSBoris Boutkov 8234165533cSJose E. Roman Output Parameter: 8244165533cSJose E. Roman . interp - the routine to create the interpolation 8254363ddcaSBoris Boutkov 8264363ddcaSBoris Boutkov Level: advanced 8274363ddcaSBoris Boutkov 828*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellGetCreateInjection()`, `DMCreateInterpolation()`, `DMShellGetCreateRestriction()`, `DMShellSetContext()`, `DMShellGetContext()` 8294363ddcaSBoris Boutkov @*/ 830d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetCreateInterpolation(DM dm, PetscErrorCode (**interp)(DM, DM, Mat *, Vec *)) 831d71ae5a4SJacob Faibussowitsch { 8324363ddcaSBoris Boutkov PetscBool isshell; 8334363ddcaSBoris Boutkov 8344363ddcaSBoris Boutkov PetscFunctionBegin; 8354363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 8369566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 8377a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 8384363ddcaSBoris Boutkov *interp = dm->ops->createinterpolation; 8393ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 8404363ddcaSBoris Boutkov } 8414363ddcaSBoris Boutkov 8424363ddcaSBoris Boutkov /*@C 8433ad4599aSBarry Smith DMShellSetCreateRestriction - Set the routine used to create the restriction operator 8443ad4599aSBarry Smith 845*20f4b53cSBarry Smith Logically Collective 8463ad4599aSBarry Smith 8474165533cSJose E. Roman Input Parameters 848*20f4b53cSBarry Smith + dm - the `DMSHELL` 8493ad4599aSBarry Smith - striction- the routine to create the restriction 8503ad4599aSBarry Smith 8513ad4599aSBarry Smith Level: advanced 8523ad4599aSBarry Smith 853*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCreateInjection()`, `DMCreateInterpolation()`, `DMShellGetCreateRestriction()`, `DMShellSetContext()`, `DMShellGetContext()` 8543ad4599aSBarry Smith @*/ 855d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateRestriction(DM dm, PetscErrorCode (*restriction)(DM, DM, Mat *)) 856d71ae5a4SJacob Faibussowitsch { 8573ad4599aSBarry Smith PetscBool isshell; 8583ad4599aSBarry Smith 8593ad4599aSBarry Smith PetscFunctionBegin; 8603ad4599aSBarry Smith PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 8619566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 8623ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 8633ad4599aSBarry Smith dm->ops->createrestriction = restriction; 8643ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 8653ad4599aSBarry Smith } 8663ad4599aSBarry Smith 8679bf9660cSLawrence Mitchell /*@C 8684363ddcaSBoris Boutkov DMShellGetCreateRestriction - Get the routine used to create the restriction operator 8694363ddcaSBoris Boutkov 870*20f4b53cSBarry Smith Logically Collective 8714363ddcaSBoris Boutkov 8724165533cSJose E. Roman Input Parameter: 873*20f4b53cSBarry Smith . dm - the `DMSHELL` 874a4a986ddSBoris Boutkov 8754165533cSJose E. Roman Output Parameter: 8764165533cSJose E. Roman . restriction - the routine to create the restriction 8774363ddcaSBoris Boutkov 8784363ddcaSBoris Boutkov Level: advanced 8794363ddcaSBoris Boutkov 880*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCreateInjection()`, `DMCreateInterpolation()`, `DMShellSetContext()`, `DMShellGetContext()` 8814363ddcaSBoris Boutkov @*/ 882d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetCreateRestriction(DM dm, PetscErrorCode (**restriction)(DM, DM, Mat *)) 883d71ae5a4SJacob Faibussowitsch { 8844363ddcaSBoris Boutkov PetscBool isshell; 8854363ddcaSBoris Boutkov 8864363ddcaSBoris Boutkov PetscFunctionBegin; 8874363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 8889566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 8897a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 8904363ddcaSBoris Boutkov *restriction = dm->ops->createrestriction; 8913ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 8924363ddcaSBoris Boutkov } 8934363ddcaSBoris Boutkov 8944363ddcaSBoris Boutkov /*@C 8959bf9660cSLawrence Mitchell DMShellSetCreateInjection - Set the routine used to create the injection operator 8969bf9660cSLawrence Mitchell 897*20f4b53cSBarry Smith Logically Collective 8989bf9660cSLawrence Mitchell 8994165533cSJose E. Roman Input Parameters: 900*20f4b53cSBarry Smith + dm - the `DMSHELL` 9019bf9660cSLawrence Mitchell - inject - the routine to create the injection 9029bf9660cSLawrence Mitchell 9039bf9660cSLawrence Mitchell Level: advanced 9049bf9660cSLawrence Mitchell 905*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellSetCreateInterpolation()`, `DMCreateInjection()`, `DMShellGetCreateInjection()`, `DMShellSetContext()`, `DMShellGetContext()` 9069bf9660cSLawrence Mitchell @*/ 907d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateInjection(DM dm, PetscErrorCode (*inject)(DM, DM, Mat *)) 908d71ae5a4SJacob Faibussowitsch { 909f572501eSLawrence Mitchell PetscBool isshell; 910f572501eSLawrence Mitchell 911f572501eSLawrence Mitchell PetscFunctionBegin; 912f572501eSLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 9139566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 9143ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 9155a84ad33SLisandro Dalcin dm->ops->createinjection = inject; 9163ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 917f572501eSLawrence Mitchell } 918f572501eSLawrence Mitchell 9194363ddcaSBoris Boutkov /*@C 9204363ddcaSBoris Boutkov DMShellGetCreateInjection - Get the routine used to create the injection operator 9214363ddcaSBoris Boutkov 922*20f4b53cSBarry Smith Logically Collective 9234363ddcaSBoris Boutkov 9244165533cSJose E. Roman Input Parameter: 925*20f4b53cSBarry Smith . dm - the `DMSHELL` 926a4a986ddSBoris Boutkov 9274165533cSJose E. Roman Output Parameter: 9284165533cSJose E. Roman . inject - the routine to create the injection 9294363ddcaSBoris Boutkov 9304363ddcaSBoris Boutkov Level: advanced 9314363ddcaSBoris Boutkov 932*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMShellGetCreateInterpolation()`, `DMCreateInjection()`, `DMShellSetContext()`, `DMShellGetContext()` 9334363ddcaSBoris Boutkov @*/ 934d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetCreateInjection(DM dm, PetscErrorCode (**inject)(DM, DM, Mat *)) 935d71ae5a4SJacob Faibussowitsch { 9364363ddcaSBoris Boutkov PetscBool isshell; 9374363ddcaSBoris Boutkov 9384363ddcaSBoris Boutkov PetscFunctionBegin; 9394363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 9409566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 9417a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 9425a84ad33SLisandro Dalcin *inject = dm->ops->createinjection; 9433ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 9444363ddcaSBoris Boutkov } 9454363ddcaSBoris Boutkov 9469bf9660cSLawrence Mitchell /*@C 947*20f4b53cSBarry Smith DMShellSetCreateFieldDecomposition - Set the routine used to create a decomposition of fields for the `DMSHELL` 9489bf9660cSLawrence Mitchell 949*20f4b53cSBarry Smith Logically Collective 9509bf9660cSLawrence Mitchell 9514165533cSJose E. Roman Input Parameters: 952*20f4b53cSBarry Smith + dm - the `DMSHELL` 9539bf9660cSLawrence Mitchell - decomp - the routine to create the decomposition 9549bf9660cSLawrence Mitchell 9559bf9660cSLawrence Mitchell Level: advanced 9569bf9660cSLawrence Mitchell 957*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateFieldDecomposition()`, `DMShellSetContext()`, `DMShellGetContext()` 9589bf9660cSLawrence Mitchell @*/ 959d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateFieldDecomposition(DM dm, PetscErrorCode (*decomp)(DM, PetscInt *, char ***, IS **, DM **)) 960d71ae5a4SJacob Faibussowitsch { 9615e2259d5SLawrence Mitchell PetscBool isshell; 9625e2259d5SLawrence Mitchell 9635e2259d5SLawrence Mitchell PetscFunctionBegin; 9645e2259d5SLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 9659566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 9663ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 9675e2259d5SLawrence Mitchell dm->ops->createfielddecomposition = decomp; 9683ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 9695e2259d5SLawrence Mitchell } 9705e2259d5SLawrence Mitchell 971c00061e5SLawrence Mitchell /*@C 972*20f4b53cSBarry Smith DMShellSetCreateDomainDecomposition - Set the routine used to create a domain decomposition for the `DMSHELL` 973e734121bSPatrick Farrell 974*20f4b53cSBarry Smith Logically Collective 975e734121bSPatrick Farrell 9764165533cSJose E. Roman Input Parameters: 977*20f4b53cSBarry Smith + dm - the `DMSHELL` 978e734121bSPatrick Farrell - decomp - the routine to create the decomposition 979e734121bSPatrick Farrell 980e734121bSPatrick Farrell Level: advanced 981e734121bSPatrick Farrell 982*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateDomainDecomposition()`, `DMShellSetContext()`, `DMShellGetContext()` 983e734121bSPatrick Farrell @*/ 984d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateDomainDecomposition(DM dm, PetscErrorCode (*decomp)(DM, PetscInt *, char ***, IS **, IS **, DM **)) 985d71ae5a4SJacob Faibussowitsch { 986e734121bSPatrick Farrell PetscBool isshell; 987e734121bSPatrick Farrell 988e734121bSPatrick Farrell PetscFunctionBegin; 989e734121bSPatrick Farrell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 9909566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 9913ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 992e734121bSPatrick Farrell dm->ops->createdomaindecomposition = decomp; 9933ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 994e734121bSPatrick Farrell } 995e734121bSPatrick Farrell 996e734121bSPatrick Farrell /*@C 997*20f4b53cSBarry Smith DMShellSetCreateDomainDecompositionScatters - Set the routine used to create the scatter contexts for domain decomposition with a `DMSHELL` 998eef9d6cdSPatrick Farrell 999*20f4b53cSBarry Smith Logically Collective 1000eef9d6cdSPatrick Farrell 10014165533cSJose E. Roman Input Parameters: 1002*20f4b53cSBarry Smith + dm - the `DMSHELL` 1003eef9d6cdSPatrick Farrell - scatter - the routine to create the scatters 1004eef9d6cdSPatrick Farrell 1005eef9d6cdSPatrick Farrell Level: advanced 1006eef9d6cdSPatrick Farrell 1007*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateDomainDecompositionScatters()`, `DMShellSetContext()`, `DMShellGetContext()` 1008eef9d6cdSPatrick Farrell @*/ 1009d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateDomainDecompositionScatters(DM dm, PetscErrorCode (*scatter)(DM, PetscInt, DM *, VecScatter **, VecScatter **, VecScatter **)) 1010d71ae5a4SJacob Faibussowitsch { 1011eef9d6cdSPatrick Farrell PetscBool isshell; 1012eef9d6cdSPatrick Farrell 1013eef9d6cdSPatrick Farrell PetscFunctionBegin; 1014eef9d6cdSPatrick Farrell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 10159566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 10163ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 1017eef9d6cdSPatrick Farrell dm->ops->createddscatters = scatter; 10183ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 1019eef9d6cdSPatrick Farrell } 1020eef9d6cdSPatrick Farrell 1021eef9d6cdSPatrick Farrell /*@C 1022*20f4b53cSBarry Smith DMShellSetCreateSubDM - Set the routine used to create a sub `DM` from the `DMSHELL` 1023c00061e5SLawrence Mitchell 1024*20f4b53cSBarry Smith Logically Collective 1025c00061e5SLawrence Mitchell 10264165533cSJose E. Roman Input Parameters: 1027*20f4b53cSBarry Smith + dm - the `DMSHELL` 1028c00061e5SLawrence Mitchell - subdm - the routine to create the decomposition 1029c00061e5SLawrence Mitchell 1030c00061e5SLawrence Mitchell Level: advanced 1031c00061e5SLawrence Mitchell 1032*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateSubDM()`, `DMShellGetCreateSubDM()`, `DMShellSetContext()`, `DMShellGetContext()` 1033c00061e5SLawrence Mitchell @*/ 1034d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellSetCreateSubDM(DM dm, PetscErrorCode (*subdm)(DM, PetscInt, const PetscInt[], IS *, DM *)) 1035d71ae5a4SJacob Faibussowitsch { 1036c00061e5SLawrence Mitchell PetscBool isshell; 1037c00061e5SLawrence Mitchell 1038c00061e5SLawrence Mitchell PetscFunctionBegin; 1039c00061e5SLawrence Mitchell PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 10409566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 10413ba16761SJacob Faibussowitsch if (!isshell) PetscFunctionReturn(PETSC_SUCCESS); 1042c00061e5SLawrence Mitchell dm->ops->createsubdm = subdm; 10433ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 1044c00061e5SLawrence Mitchell } 1045c00061e5SLawrence Mitchell 10464363ddcaSBoris Boutkov /*@C 1047*20f4b53cSBarry Smith DMShellGetCreateSubDM - Get the routine used to create a sub DM from the `DMSHELL` 10484363ddcaSBoris Boutkov 1049*20f4b53cSBarry Smith Logically Collective 10504363ddcaSBoris Boutkov 10514165533cSJose E. Roman Input Parameter: 1052*20f4b53cSBarry Smith . dm - the `DMSHELL` 1053a4a986ddSBoris Boutkov 10544165533cSJose E. Roman Output Parameter: 10554165533cSJose E. Roman . subdm - the routine to create the decomposition 10564363ddcaSBoris Boutkov 10574363ddcaSBoris Boutkov Level: advanced 10584363ddcaSBoris Boutkov 1059*20f4b53cSBarry Smith .seealso: `DM`, `DMSHELL`, `DMCreateSubDM()`, `DMShellSetCreateSubDM()`, `DMShellSetContext()`, `DMShellGetContext()` 10604363ddcaSBoris Boutkov @*/ 1061d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellGetCreateSubDM(DM dm, PetscErrorCode (**subdm)(DM, PetscInt, const PetscInt[], IS *, DM *)) 1062d71ae5a4SJacob Faibussowitsch { 10634363ddcaSBoris Boutkov PetscBool isshell; 10644363ddcaSBoris Boutkov 10654363ddcaSBoris Boutkov PetscFunctionBegin; 10664363ddcaSBoris Boutkov PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 10679566063dSJacob Faibussowitsch PetscCall(PetscObjectTypeCompare((PetscObject)dm, DMSHELL, &isshell)); 10687a8be351SBarry Smith PetscCheck(isshell, PetscObjectComm((PetscObject)dm), PETSC_ERR_SUP, "Can only use with DMSHELL type DMs"); 10694363ddcaSBoris Boutkov *subdm = dm->ops->createsubdm; 10703ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 10714363ddcaSBoris Boutkov } 10724363ddcaSBoris Boutkov 1073d71ae5a4SJacob Faibussowitsch static PetscErrorCode DMDestroy_Shell(DM dm) 1074d71ae5a4SJacob Faibussowitsch { 1075fe1899a2SJed Brown DM_Shell *shell = (DM_Shell *)dm->data; 1076fe1899a2SJed Brown 1077fe1899a2SJed Brown PetscFunctionBegin; 107809904cd0SBarry Smith if (shell->destroyctx) PetscCallBack("Destroy Context", (*shell->destroyctx)(shell->ctx)); 10799566063dSJacob Faibussowitsch PetscCall(MatDestroy(&shell->A)); 10809566063dSJacob Faibussowitsch PetscCall(VecDestroy(&shell->Xglobal)); 10819566063dSJacob Faibussowitsch PetscCall(VecDestroy(&shell->Xlocal)); 10829566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->gtol)); 10839566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->ltog)); 10849566063dSJacob Faibussowitsch PetscCall(VecScatterDestroy(&shell->ltol)); 10857b6ad80cSMatthew G Knepley /* This was originally freed in DMDestroy(), but that prevents reference counting of backend objects */ 10869566063dSJacob Faibussowitsch PetscCall(PetscFree(shell)); 10873ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 1088fe1899a2SJed Brown } 1089fe1899a2SJed Brown 1090d71ae5a4SJacob Faibussowitsch static PetscErrorCode DMView_Shell(DM dm, PetscViewer v) 1091d71ae5a4SJacob Faibussowitsch { 10922d53ad75SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 10932d53ad75SBarry Smith 10942d53ad75SBarry Smith PetscFunctionBegin; 109501f8681bSStefano Zampini if (shell->Xglobal) PetscCall(VecView(shell->Xglobal, v)); 10963ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 10972d53ad75SBarry Smith } 10982d53ad75SBarry Smith 1099d71ae5a4SJacob Faibussowitsch static PetscErrorCode DMLoad_Shell(DM dm, PetscViewer v) 1100d71ae5a4SJacob Faibussowitsch { 11012d53ad75SBarry Smith DM_Shell *shell = (DM_Shell *)dm->data; 11022d53ad75SBarry Smith 11032d53ad75SBarry Smith PetscFunctionBegin; 11049566063dSJacob Faibussowitsch PetscCall(VecCreate(PetscObjectComm((PetscObject)dm), &shell->Xglobal)); 11059566063dSJacob Faibussowitsch PetscCall(VecLoad(shell->Xglobal, v)); 11063ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 11072d53ad75SBarry Smith } 1108fe1899a2SJed Brown 1109d71ae5a4SJacob Faibussowitsch PetscErrorCode DMCreateSubDM_Shell(DM dm, PetscInt numFields, const PetscInt fields[], IS *is, DM *subdm) 1110d71ae5a4SJacob Faibussowitsch { 11116e44b4cfSMatthew G. Knepley PetscFunctionBegin; 11129566063dSJacob Faibussowitsch if (subdm) PetscCall(DMShellCreate(PetscObjectComm((PetscObject)dm), subdm)); 11139566063dSJacob Faibussowitsch PetscCall(DMCreateSectionSubDM(dm, numFields, fields, is, subdm)); 11143ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 11156e44b4cfSMatthew G. Knepley } 11166e44b4cfSMatthew G. Knepley 1117d71ae5a4SJacob Faibussowitsch PETSC_EXTERN PetscErrorCode DMCreate_Shell(DM dm) 1118d71ae5a4SJacob Faibussowitsch { 1119fe1899a2SJed Brown DM_Shell *shell; 1120fe1899a2SJed Brown 1121fe1899a2SJed Brown PetscFunctionBegin; 11224dfa11a4SJacob Faibussowitsch PetscCall(PetscNew(&shell)); 11238c87107bSJed Brown dm->data = shell; 1124fe1899a2SJed Brown 11258c87107bSJed Brown dm->ops->destroy = DMDestroy_Shell; 11268c87107bSJed Brown dm->ops->createglobalvector = DMCreateGlobalVector_Shell; 1127dc43b69eSJed Brown dm->ops->createlocalvector = DMCreateLocalVector_Shell; 11288c87107bSJed Brown dm->ops->creatematrix = DMCreateMatrix_Shell; 11292d53ad75SBarry Smith dm->ops->view = DMView_Shell; 11302d53ad75SBarry Smith dm->ops->load = DMLoad_Shell; 11317a108d1dSBarry Smith dm->ops->globaltolocalbegin = DMGlobalToLocalBeginDefaultShell; 11327a108d1dSBarry Smith dm->ops->globaltolocalend = DMGlobalToLocalEndDefaultShell; 113355daaa54SRichard Tran Mills dm->ops->localtoglobalbegin = DMLocalToGlobalBeginDefaultShell; 113455daaa54SRichard Tran Mills dm->ops->localtoglobalend = DMLocalToGlobalEndDefaultShell; 113563731094SRichard Tran Mills dm->ops->localtolocalbegin = DMLocalToLocalBeginDefaultShell; 113663731094SRichard Tran Mills dm->ops->localtolocalend = DMLocalToLocalEndDefaultShell; 11376e44b4cfSMatthew G. Knepley dm->ops->createsubdm = DMCreateSubDM_Shell; 11389566063dSJacob Faibussowitsch PetscCall(DMSetMatType(dm, MATDENSE)); 11393ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 1140fe1899a2SJed Brown } 1141fe1899a2SJed Brown 1142fe1899a2SJed Brown /*@ 1143*20f4b53cSBarry Smith DMShellCreate - Creates a `DMSHELL` object, used to manage user-defined problem data 1144fe1899a2SJed Brown 1145d083f849SBarry Smith Collective 1146fe1899a2SJed Brown 1147fe1899a2SJed Brown Input Parameter: 1148fe1899a2SJed Brown . comm - the processors that will share the global vector 1149fe1899a2SJed Brown 1150fe1899a2SJed Brown Output Parameters: 1151*20f4b53cSBarry Smith . shell - the `DMSHELL` 1152fe1899a2SJed Brown 1153fe1899a2SJed Brown Level: advanced 1154fe1899a2SJed Brown 1155db781477SPatrick Sanan .seealso `DMDestroy()`, `DMCreateGlobalVector()`, `DMCreateLocalVector()`, `DMShellSetContext()`, `DMShellGetContext()` 1156fe1899a2SJed Brown @*/ 1157d71ae5a4SJacob Faibussowitsch PetscErrorCode DMShellCreate(MPI_Comm comm, DM *dm) 1158d71ae5a4SJacob Faibussowitsch { 1159fe1899a2SJed Brown PetscFunctionBegin; 1160fe1899a2SJed Brown PetscValidPointer(dm, 2); 11619566063dSJacob Faibussowitsch PetscCall(DMCreate(comm, dm)); 11629566063dSJacob Faibussowitsch PetscCall(DMSetType(*dm, DMSHELL)); 11639566063dSJacob Faibussowitsch PetscCall(DMSetUp(*dm)); 11643ba16761SJacob Faibussowitsch PetscFunctionReturn(PETSC_SUCCESS); 1165fe1899a2SJed Brown } 1166