xref: /petsc/src/dm/impls/moab/dmmbvec.cxx (revision 1baa6e3354bfe224b33a0c158f482508792a8a6e)
1af0996ceSBarry Smith #include <petsc/private/dmmbimpl.h> /*I  "petscdmmoab.h"   I*/
2af0996ceSBarry Smith #include <petsc/private/vecimpl.h>
3032b8ab6SVijay Mahadevan 
4032b8ab6SVijay Mahadevan #include <petscdmmoab.h>
5032b8ab6SVijay Mahadevan #include <MBTagConventions.hpp>
6032b8ab6SVijay Mahadevan 
79c368985SVijay Mahadevan #define USE_NATIVE_PETSCVEC
89c368985SVijay Mahadevan 
9f6829af0SVijay Mahadevan /* declare some private DMMoab specific overrides */
10f6829af0SVijay Mahadevan static PetscErrorCode DMCreateVector_Moab_Private(DM dm,moab::Tag tag,const moab::Range* userrange,PetscBool is_global_vec,PetscBool destroy_tag,Vec *vec);
11f6829af0SVijay Mahadevan static PetscErrorCode DMVecUserDestroy_Moab(void *user);
12f6829af0SVijay Mahadevan static PetscErrorCode DMVecDuplicate_Moab(Vec x,Vec *y);
139daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
149daf19fdSVijay Mahadevan static PetscErrorCode DMVecCreateTagName_Moab_Private(moab::Interface *mbiface,moab::ParallelComm *pcomm,char** tag_name);
159daf19fdSVijay Mahadevan #else
169daf19fdSVijay Mahadevan static PetscErrorCode DMVecCreateTagName_Moab_Private(moab::Interface *mbiface,char** tag_name);
179daf19fdSVijay Mahadevan #endif
18032b8ab6SVijay Mahadevan 
19b8ecf6d3SVijay Mahadevan /*@C
20f6829af0SVijay Mahadevan   DMMoabCreateVector - Create a Vec from either an existing tag, or a specified tag size, and a range of entities
21f6829af0SVijay Mahadevan 
22d083f849SBarry Smith   Collective
23f6829af0SVijay Mahadevan 
24d8d19677SJose E. Roman   Input Parameters:
25b8ecf6d3SVijay Mahadevan + dm              - The DMMoab object being set
26f6829af0SVijay Mahadevan . tag             - If non-zero, block size will be taken from the tag size
27f6829af0SVijay Mahadevan . range           - If non-empty, Vec corresponds to these entities, otherwise to the entities set on the DMMoab
28f6829af0SVijay Mahadevan . is_global_vec   - If true, this is a local representation of the Vec (including ghosts in parallel), otherwise a truly parallel one
29a2b725a8SWilliam Gropp - destroy_tag     - If true, MOAB tag is destroyed with Vec, otherwise it is left on MOAB
30f6829af0SVijay Mahadevan 
31f6829af0SVijay Mahadevan   Output Parameter:
32f6829af0SVijay Mahadevan . vec             - The created vector
33f6829af0SVijay Mahadevan 
34f6829af0SVijay Mahadevan   Level: beginner
35f6829af0SVijay Mahadevan 
36db781477SPatrick Sanan .seealso: `VecCreate()`
37f6829af0SVijay Mahadevan @*/
38f6829af0SVijay Mahadevan PetscErrorCode DMMoabCreateVector(DM dm, moab::Tag tag, const moab::Range* range, PetscBool is_global_vec, PetscBool destroy_tag, Vec *vec)
39f6829af0SVijay Mahadevan {
40f6829af0SVijay Mahadevan   PetscFunctionBegin;
417a8be351SBarry Smith   PetscCheck(tag || (range && !range->empty()),PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Both tag and range cannot be null.");
42f6829af0SVijay Mahadevan 
439566063dSJacob Faibussowitsch   PetscCall(DMCreateVector_Moab_Private(dm, tag, range, is_global_vec, destroy_tag, vec));
44f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
45f6829af0SVijay Mahadevan }
46f6829af0SVijay Mahadevan 
47b8ecf6d3SVijay Mahadevan /*@C
48f6829af0SVijay Mahadevan   DMMoabGetVecTag - Get the MOAB tag associated with this Vec
49f6829af0SVijay Mahadevan 
50f6829af0SVijay Mahadevan   Input Parameter:
51f6829af0SVijay Mahadevan . vec - Vec being queried
52f6829af0SVijay Mahadevan 
53f6829af0SVijay Mahadevan   Output Parameter:
54f6829af0SVijay Mahadevan . tag - Tag associated with this Vec. NULL if vec is a native PETSc Vec.
55f6829af0SVijay Mahadevan 
56f6829af0SVijay Mahadevan   Level: beginner
57f6829af0SVijay Mahadevan 
58db781477SPatrick Sanan .seealso: `DMMoabCreateVector()`, `DMMoabGetVecRange()`
59f6829af0SVijay Mahadevan @*/
60f6829af0SVijay Mahadevan PetscErrorCode DMMoabGetVecTag(Vec vec, moab::Tag *tag)
61f6829af0SVijay Mahadevan {
62f6829af0SVijay Mahadevan   PetscContainer  moabdata;
63f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab;
64f6829af0SVijay Mahadevan 
65f6829af0SVijay Mahadevan   PetscFunctionBegin;
66f6829af0SVijay Mahadevan   PetscValidPointer(tag, 2);
67f6829af0SVijay Mahadevan 
68f6829af0SVijay Mahadevan   /* Get the MOAB private data */
699566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
709566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**) &vmoab));
71f6829af0SVijay Mahadevan 
72f6829af0SVijay Mahadevan   *tag = vmoab->tag;
73f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
74f6829af0SVijay Mahadevan }
75f6829af0SVijay Mahadevan 
76b8ecf6d3SVijay Mahadevan /*@C
77f6829af0SVijay Mahadevan   DMMoabGetVecRange - Get the MOAB entities associated with this Vec
78f6829af0SVijay Mahadevan 
79f6829af0SVijay Mahadevan   Input Parameter:
80f6829af0SVijay Mahadevan . vec   - Vec being queried
81f6829af0SVijay Mahadevan 
82f6829af0SVijay Mahadevan   Output Parameter:
83f6829af0SVijay Mahadevan . range - Entities associated with this Vec. NULL if vec is a native PETSc Vec.
84f6829af0SVijay Mahadevan 
85f6829af0SVijay Mahadevan   Level: beginner
86f6829af0SVijay Mahadevan 
87db781477SPatrick Sanan .seealso: `DMMoabCreateVector()`, `DMMoabGetVecTag()`
88f6829af0SVijay Mahadevan @*/
89f6829af0SVijay Mahadevan PetscErrorCode DMMoabGetVecRange(Vec vec, moab::Range *range)
90f6829af0SVijay Mahadevan {
91f6829af0SVijay Mahadevan   PetscContainer  moabdata;
92f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab;
93f6829af0SVijay Mahadevan 
94f6829af0SVijay Mahadevan   PetscFunctionBegin;
95f6829af0SVijay Mahadevan   PetscValidPointer(range, 2);
96f6829af0SVijay Mahadevan 
97f6829af0SVijay Mahadevan   /* Get the MOAB private data handle */
989566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
999566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**) &vmoab));
100f6829af0SVijay Mahadevan 
101f6829af0SVijay Mahadevan   *range = *vmoab->tag_range;
102f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
103f6829af0SVijay Mahadevan }
104f6829af0SVijay Mahadevan 
105b8ecf6d3SVijay Mahadevan /*@C
106f6829af0SVijay Mahadevan   DMMoabVecGetArray - Returns the writable direct access array to the local representation of MOAB tag data for the underlying vector using locally owned+ghosted range of entities
107f6829af0SVijay Mahadevan 
108d083f849SBarry Smith   Collective
109f6829af0SVijay Mahadevan 
110d8d19677SJose E. Roman   Input Parameters:
111a2b725a8SWilliam Gropp + dm              - The DMMoab object being set
112a2b725a8SWilliam Gropp - vec             - The Vector whose underlying data is requested
113f6829af0SVijay Mahadevan 
114f6829af0SVijay Mahadevan   Output Parameter:
115f6829af0SVijay Mahadevan . array           - The local data array
116f6829af0SVijay Mahadevan 
117f6829af0SVijay Mahadevan   Level: intermediate
118f6829af0SVijay Mahadevan 
119db781477SPatrick Sanan .seealso: `DMMoabVecRestoreArray()`, `DMMoabVecGetArrayRead()`, `DMMoabVecRestoreArrayRead()`
120f6829af0SVijay Mahadevan @*/
121f6829af0SVijay Mahadevan PetscErrorCode  DMMoabVecGetArray(DM dm, Vec vec, void* array)
122f6829af0SVijay Mahadevan {
123f6829af0SVijay Mahadevan   DM_Moab        *dmmoab;
124f6829af0SVijay Mahadevan   moab::ErrorCode merr;
125f6829af0SVijay Mahadevan   PetscInt        count, i, f;
126f6829af0SVijay Mahadevan   moab::Tag       vtag;
127f6829af0SVijay Mahadevan   PetscScalar     **varray;
128f6829af0SVijay Mahadevan   PetscScalar     *marray;
129f6829af0SVijay Mahadevan   PetscContainer  moabdata;
130f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab, *xmoab;
131f6829af0SVijay Mahadevan 
132f6829af0SVijay Mahadevan   PetscFunctionBegin;
133f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
134f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(vec, VEC_CLASSID, 2);
135f6829af0SVijay Mahadevan   PetscValidPointer(array, 3);
136f6829af0SVijay Mahadevan   dmmoab = (DM_Moab*)dm->data;
137f6829af0SVijay Mahadevan 
138f6829af0SVijay Mahadevan   /* Get the Vec_MOAB struct for the original vector */
1399566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
1409566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**)&vmoab));
141f6829af0SVijay Mahadevan 
142f6829af0SVijay Mahadevan   /* Get the real scalar array handle */
143f6829af0SVijay Mahadevan   varray = reinterpret_cast<PetscScalar**>(array);
144f6829af0SVijay Mahadevan 
145f6829af0SVijay Mahadevan   if (vmoab->is_native_vec) {
146f6829af0SVijay Mahadevan 
147f6829af0SVijay Mahadevan     /* get the local representation of the arrays from Vectors */
1489566063dSJacob Faibussowitsch     PetscCall(DMGetLocalVector(dm, &vmoab->local));
1499566063dSJacob Faibussowitsch     PetscCall(DMGlobalToLocalBegin(dm, vec, INSERT_VALUES, vmoab->local));
1509566063dSJacob Faibussowitsch     PetscCall(DMGlobalToLocalEnd(dm, vec, INSERT_VALUES, vmoab->local));
151f6829af0SVijay Mahadevan 
152f6829af0SVijay Mahadevan     /* Get the Vec_MOAB struct for the original vector */
1539566063dSJacob Faibussowitsch     PetscCall(PetscObjectQuery((PetscObject)vmoab->local, "MOABData", (PetscObject*) &moabdata));
1549566063dSJacob Faibussowitsch     PetscCall(PetscContainerGetPointer(moabdata, (void**)&xmoab));
155f6829af0SVijay Mahadevan 
156f6829af0SVijay Mahadevan     /* get the local representation of the arrays from Vectors */
1579566063dSJacob Faibussowitsch     PetscCall(VecGhostGetLocalForm(vmoab->local, &xmoab->local));
1589566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateBegin(vmoab->local, INSERT_VALUES, SCATTER_FORWARD));
1599566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateEnd(vmoab->local, INSERT_VALUES, SCATTER_FORWARD));
160f6829af0SVijay Mahadevan 
1619566063dSJacob Faibussowitsch     PetscCall(VecGetArray(xmoab->local, varray));
162*1baa6e33SBarry Smith   } else {
163f6829af0SVijay Mahadevan 
164f6829af0SVijay Mahadevan     /* Get the MOAB private data */
1659566063dSJacob Faibussowitsch     PetscCall(DMMoabGetVecTag(vec, &vtag));
166f6829af0SVijay Mahadevan 
1679daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
168f6829af0SVijay Mahadevan     /* exchange the data into ghost cells first */
169f6829af0SVijay Mahadevan     merr = dmmoab->pcomm->exchange_tags(vtag, *dmmoab->vlocal); MBERRNM(merr);
1709daf19fdSVijay Mahadevan #endif
171f6829af0SVijay Mahadevan 
1729566063dSJacob Faibussowitsch     PetscCall(PetscMalloc1((dmmoab->nloc + dmmoab->nghost) * dmmoab->numFields, varray));
173f6829af0SVijay Mahadevan 
174f6829af0SVijay Mahadevan     /* Get the array data for local entities */
175f6829af0SVijay Mahadevan     merr = dmmoab->mbiface->tag_iterate(vtag, dmmoab->vlocal->begin(), dmmoab->vlocal->end(), count, reinterpret_cast<void*&>(marray), false); MBERRNM(merr);
1761dca8a05SBarry Smith     PetscCheck(count == dmmoab->nloc + dmmoab->nghost,PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Mismatch between local vertices and tag partition for Vec. %" PetscInt_FMT " != %" PetscInt_FMT ".", count, dmmoab->nloc + dmmoab->nghost);
177f6829af0SVijay Mahadevan 
178f6829af0SVijay Mahadevan     i = 0;
179f6829af0SVijay Mahadevan     for (moab::Range::iterator iter = dmmoab->vlocal->begin(); iter != dmmoab->vlocal->end(); iter++) {
180f6829af0SVijay Mahadevan       for (f = 0; f < dmmoab->numFields; f++, i++)
1813f1c6e43SVijay Mahadevan         (*varray)[dmmoab->lidmap[(PetscInt)*iter - dmmoab->seqstart]*dmmoab->numFields + f] = marray[i];
1823f1c6e43SVijay Mahadevan       //(*varray)[dmmoab->llmap[dmmoab->lidmap[((PetscInt)*iter-dmmoab->seqstart)]*dmmoab->numFields+f]]=marray[i];
183f6829af0SVijay Mahadevan     }
184f6829af0SVijay Mahadevan   }
185f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
186f6829af0SVijay Mahadevan }
187f6829af0SVijay Mahadevan 
188b8ecf6d3SVijay Mahadevan /*@C
189f6829af0SVijay Mahadevan   DMMoabVecRestoreArray - Restores the writable direct access array obtained via DMMoabVecGetArray
190f6829af0SVijay Mahadevan 
191d083f849SBarry Smith   Collective
192f6829af0SVijay Mahadevan 
193d8d19677SJose E. Roman   Input Parameters:
194f6829af0SVijay Mahadevan + dm              - The DMMoab object being set
195f6829af0SVijay Mahadevan . vec             - The Vector whose underlying data is requested
196a2b725a8SWilliam Gropp - array           - The local data array
197f6829af0SVijay Mahadevan 
198f6829af0SVijay Mahadevan   Level: intermediate
199f6829af0SVijay Mahadevan 
200db781477SPatrick Sanan .seealso: `DMMoabVecGetArray()`, `DMMoabVecGetArrayRead()`, `DMMoabVecRestoreArrayRead()`
201f6829af0SVijay Mahadevan @*/
202f6829af0SVijay Mahadevan PetscErrorCode  DMMoabVecRestoreArray(DM dm, Vec vec, void* array)
203f6829af0SVijay Mahadevan {
204f6829af0SVijay Mahadevan   DM_Moab        *dmmoab;
205f6829af0SVijay Mahadevan   moab::ErrorCode merr;
206f6829af0SVijay Mahadevan   moab::Tag       vtag;
207f6829af0SVijay Mahadevan   PetscInt        count, i, f;
208f6829af0SVijay Mahadevan   PetscScalar     **varray;
209f6829af0SVijay Mahadevan   PetscScalar     *marray;
210f6829af0SVijay Mahadevan   PetscContainer  moabdata;
211f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab, *xmoab;
212f6829af0SVijay Mahadevan 
213f6829af0SVijay Mahadevan   PetscFunctionBegin;
214f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
215f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(vec, VEC_CLASSID, 2);
216f6829af0SVijay Mahadevan   PetscValidPointer(array, 3);
217f6829af0SVijay Mahadevan   dmmoab = (DM_Moab*)dm->data;
218f6829af0SVijay Mahadevan 
219f6829af0SVijay Mahadevan   /* Get the Vec_MOAB struct for the original vector */
2209566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
2219566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**)&vmoab));
222f6829af0SVijay Mahadevan 
223f6829af0SVijay Mahadevan   /* Get the real scalar array handle */
224f6829af0SVijay Mahadevan   varray = reinterpret_cast<PetscScalar**>(array);
225f6829af0SVijay Mahadevan 
226f6829af0SVijay Mahadevan   if (vmoab->is_native_vec) {
227f6829af0SVijay Mahadevan 
228f6829af0SVijay Mahadevan     /* Get the Vec_MOAB struct for the original vector */
2299566063dSJacob Faibussowitsch     PetscCall(PetscObjectQuery((PetscObject)vmoab->local, "MOABData", (PetscObject*) &moabdata));
2309566063dSJacob Faibussowitsch     PetscCall(PetscContainerGetPointer(moabdata, (void**)&xmoab));
231f6829af0SVijay Mahadevan 
232f6829af0SVijay Mahadevan     /* get the local representation of the arrays from Vectors */
2339566063dSJacob Faibussowitsch     PetscCall(VecRestoreArray(xmoab->local, varray));
2349566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateBegin(vmoab->local, ADD_VALUES, SCATTER_REVERSE));
2359566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateEnd(vmoab->local, ADD_VALUES, SCATTER_REVERSE));
2369566063dSJacob Faibussowitsch     PetscCall(VecGhostRestoreLocalForm(vmoab->local, &xmoab->local));
237f6829af0SVijay Mahadevan 
238f6829af0SVijay Mahadevan     /* restore local pieces */
2399566063dSJacob Faibussowitsch     PetscCall(DMLocalToGlobalBegin(dm, vmoab->local, INSERT_VALUES, vec));
2409566063dSJacob Faibussowitsch     PetscCall(DMLocalToGlobalEnd(dm, vmoab->local, INSERT_VALUES, vec));
2419566063dSJacob Faibussowitsch     PetscCall(DMRestoreLocalVector(dm, &vmoab->local));
242f6829af0SVijay Mahadevan   }
243f6829af0SVijay Mahadevan   else {
244f6829af0SVijay Mahadevan 
245f6829af0SVijay Mahadevan     /* Get the MOAB private data */
2469566063dSJacob Faibussowitsch     PetscCall(DMMoabGetVecTag(vec, &vtag));
247f6829af0SVijay Mahadevan 
248f6829af0SVijay Mahadevan     /* Get the array data for local entities */
249f6829af0SVijay Mahadevan     merr = dmmoab->mbiface->tag_iterate(vtag, dmmoab->vlocal->begin(), dmmoab->vlocal->end(), count, reinterpret_cast<void*&>(marray), false); MBERRNM(merr);
2501dca8a05SBarry Smith     PetscCheck(count == dmmoab->nloc + dmmoab->nghost,PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Mismatch between local vertices and tag partition for Vec. %" PetscInt_FMT " != %" PetscInt_FMT ".", count, dmmoab->nloc + dmmoab->nghost);
251f6829af0SVijay Mahadevan 
252f6829af0SVijay Mahadevan     i = 0;
253f6829af0SVijay Mahadevan     for (moab::Range::iterator iter = dmmoab->vlocal->begin(); iter != dmmoab->vlocal->end(); iter++) {
254f6829af0SVijay Mahadevan       for (f = 0; f < dmmoab->numFields; f++, i++)
2553f1c6e43SVijay Mahadevan         marray[i] = (*varray)[dmmoab->lidmap[(PetscInt) * iter - dmmoab->seqstart] * dmmoab->numFields + f];
2563f1c6e43SVijay Mahadevan       //marray[i] = (*varray)[dmmoab->llmap[dmmoab->lidmap[((PetscInt)*iter-dmmoab->seqstart)]*dmmoab->numFields+f]];
257f6829af0SVijay Mahadevan     }
258f6829af0SVijay Mahadevan 
2599daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
260f6829af0SVijay Mahadevan     /* reduce the tags correctly -> should probably let the user choose how to reduce in the future
261f6829af0SVijay Mahadevan       For all FEM residual based assembly calculations, MPI_SUM should serve well */
262f6829af0SVijay Mahadevan     merr = dmmoab->pcomm->reduce_tags(vtag, MPI_SUM, *dmmoab->vlocal); MBERRV(dmmoab->mbiface, merr);
2639daf19fdSVijay Mahadevan #endif
2649566063dSJacob Faibussowitsch     PetscCall(PetscFree(*varray));
265f6829af0SVijay Mahadevan   }
266f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
267f6829af0SVijay Mahadevan }
268f6829af0SVijay Mahadevan 
269b8ecf6d3SVijay Mahadevan /*@C
270f6829af0SVijay Mahadevan   DMMoabVecGetArrayRead - Returns the read-only direct access array to the local representation of MOAB tag data for the underlying vector using locally owned+ghosted range of entities
271f6829af0SVijay Mahadevan 
272d083f849SBarry Smith   Collective
273f6829af0SVijay Mahadevan 
274d8d19677SJose E. Roman   Input Parameters:
275f6829af0SVijay Mahadevan + dm              - The DMMoab object being set
276a2b725a8SWilliam Gropp - vec             - The Vector whose underlying data is requested
277f6829af0SVijay Mahadevan 
278f6829af0SVijay Mahadevan   Output Parameter:
279f6829af0SVijay Mahadevan . array           - The local data array
280f6829af0SVijay Mahadevan 
281f6829af0SVijay Mahadevan   Level: intermediate
282f6829af0SVijay Mahadevan 
283db781477SPatrick Sanan .seealso: `DMMoabVecRestoreArrayRead()`, `DMMoabVecGetArray()`, `DMMoabVecRestoreArray()`
284f6829af0SVijay Mahadevan @*/
285f6829af0SVijay Mahadevan PetscErrorCode  DMMoabVecGetArrayRead(DM dm, Vec vec, void* array)
286f6829af0SVijay Mahadevan {
287f6829af0SVijay Mahadevan   DM_Moab        *dmmoab;
288f6829af0SVijay Mahadevan   moab::ErrorCode merr;
289f6829af0SVijay Mahadevan   PetscInt        count, i, f;
290f6829af0SVijay Mahadevan   moab::Tag       vtag;
291f6829af0SVijay Mahadevan   PetscScalar     **varray;
292f6829af0SVijay Mahadevan   PetscScalar     *marray;
293f6829af0SVijay Mahadevan   PetscContainer  moabdata;
294f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab, *xmoab;
295f6829af0SVijay Mahadevan 
296f6829af0SVijay Mahadevan   PetscFunctionBegin;
297f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
298f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(vec, VEC_CLASSID, 2);
299f6829af0SVijay Mahadevan   PetscValidPointer(array, 3);
300f6829af0SVijay Mahadevan   dmmoab = (DM_Moab*)dm->data;
301f6829af0SVijay Mahadevan 
302f6829af0SVijay Mahadevan   /* Get the Vec_MOAB struct for the original vector */
3039566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
3049566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**)&vmoab));
305f6829af0SVijay Mahadevan 
306f6829af0SVijay Mahadevan   /* Get the real scalar array handle */
307f6829af0SVijay Mahadevan   varray = reinterpret_cast<PetscScalar**>(array);
308f6829af0SVijay Mahadevan 
309f6829af0SVijay Mahadevan   if (vmoab->is_native_vec) {
310f6829af0SVijay Mahadevan     /* get the local representation of the arrays from Vectors */
3119566063dSJacob Faibussowitsch     PetscCall(DMGetLocalVector(dm, &vmoab->local));
3129566063dSJacob Faibussowitsch     PetscCall(DMGlobalToLocalBegin(dm, vec, INSERT_VALUES, vmoab->local));
3139566063dSJacob Faibussowitsch     PetscCall(DMGlobalToLocalEnd(dm, vec, INSERT_VALUES, vmoab->local));
314f6829af0SVijay Mahadevan 
315f6829af0SVijay Mahadevan     /* Get the Vec_MOAB struct for the original vector */
3169566063dSJacob Faibussowitsch     PetscCall(PetscObjectQuery((PetscObject)vmoab->local, "MOABData", (PetscObject*) &moabdata));
3179566063dSJacob Faibussowitsch     PetscCall(PetscContainerGetPointer(moabdata, (void**)&xmoab));
318f6829af0SVijay Mahadevan 
319f6829af0SVijay Mahadevan     /* get the local representation of the arrays from Vectors */
3209566063dSJacob Faibussowitsch     PetscCall(VecGhostGetLocalForm(vmoab->local, &xmoab->local));
3219566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateBegin(vmoab->local, INSERT_VALUES, SCATTER_FORWARD));
3229566063dSJacob Faibussowitsch     PetscCall(VecGhostUpdateEnd(vmoab->local, INSERT_VALUES, SCATTER_FORWARD));
3239566063dSJacob Faibussowitsch     PetscCall(VecGetArray(xmoab->local, varray));
324f6829af0SVijay Mahadevan   }
325f6829af0SVijay Mahadevan   else {
326f6829af0SVijay Mahadevan     /* Get the MOAB private data */
3279566063dSJacob Faibussowitsch     PetscCall(DMMoabGetVecTag(vec, &vtag));
328f6829af0SVijay Mahadevan 
3299daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
330f6829af0SVijay Mahadevan     /* exchange the data into ghost cells first */
331f6829af0SVijay Mahadevan     merr = dmmoab->pcomm->exchange_tags(vtag, *dmmoab->vlocal); MBERRNM(merr);
3329daf19fdSVijay Mahadevan #endif
3339566063dSJacob Faibussowitsch     PetscCall(PetscMalloc1((dmmoab->nloc + dmmoab->nghost) * dmmoab->numFields, varray));
334f6829af0SVijay Mahadevan 
335f6829af0SVijay Mahadevan     /* Get the array data for local entities */
336f6829af0SVijay Mahadevan     merr = dmmoab->mbiface->tag_iterate(vtag, dmmoab->vlocal->begin(), dmmoab->vlocal->end(), count, reinterpret_cast<void*&>(marray), false); MBERRNM(merr);
3371dca8a05SBarry Smith     PetscCheck(count == dmmoab->nloc + dmmoab->nghost,PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Mismatch between local vertices and tag partition for Vec. %" PetscInt_FMT " != %" PetscInt_FMT ".", count, dmmoab->nloc + dmmoab->nghost);
338f6829af0SVijay Mahadevan 
339f6829af0SVijay Mahadevan     i = 0;
340f6829af0SVijay Mahadevan     for (moab::Range::iterator iter = dmmoab->vlocal->begin(); iter != dmmoab->vlocal->end(); iter++) {
341f6829af0SVijay Mahadevan       for (f = 0; f < dmmoab->numFields; f++, i++)
3423f1c6e43SVijay Mahadevan         (*varray)[dmmoab->lidmap[(PetscInt)*iter - dmmoab->seqstart]*dmmoab->numFields + f] = marray[i];
3433f1c6e43SVijay Mahadevan       //(*varray)[dmmoab->llmap[dmmoab->lidmap[((PetscInt)*iter-dmmoab->seqstart)]*dmmoab->numFields+f]]=marray[i];
344f6829af0SVijay Mahadevan     }
345f6829af0SVijay Mahadevan   }
346f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
347f6829af0SVijay Mahadevan }
348f6829af0SVijay Mahadevan 
349b8ecf6d3SVijay Mahadevan /*@C
3504597dd3dSJose E. Roman   DMMoabVecRestoreArrayRead - Restores the read-only direct access array obtained via DMMoabVecGetArray
351f6829af0SVijay Mahadevan 
352d083f849SBarry Smith   Collective
353f6829af0SVijay Mahadevan 
35497bb3fdcSJose E. Roman   Input Parameters:
355f6829af0SVijay Mahadevan + dm              - The DMMoab object being set
356f6829af0SVijay Mahadevan . vec             - The Vector whose underlying data is requested
357a2b725a8SWilliam Gropp - array           - The local data array
358f6829af0SVijay Mahadevan 
359f6829af0SVijay Mahadevan   Level: intermediate
360f6829af0SVijay Mahadevan 
361db781477SPatrick Sanan .seealso: `DMMoabVecGetArrayRead()`, `DMMoabVecGetArray()`, `DMMoabVecRestoreArray()`
362f6829af0SVijay Mahadevan @*/
363f6829af0SVijay Mahadevan PetscErrorCode  DMMoabVecRestoreArrayRead(DM dm, Vec vec, void* array)
364f6829af0SVijay Mahadevan {
365f6829af0SVijay Mahadevan   PetscScalar     **varray;
366f6829af0SVijay Mahadevan   PetscContainer  moabdata;
367f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab, *xmoab;
368f6829af0SVijay Mahadevan 
369f6829af0SVijay Mahadevan   PetscFunctionBegin;
370f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
371f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(vec, VEC_CLASSID, 2);
372f6829af0SVijay Mahadevan   PetscValidPointer(array, 3);
373f6829af0SVijay Mahadevan 
374f6829af0SVijay Mahadevan   /* Get the Vec_MOAB struct for the original vector */
3759566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)vec, "MOABData", (PetscObject*) &moabdata));
3769566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**)&vmoab));
377f6829af0SVijay Mahadevan 
378f6829af0SVijay Mahadevan   /* Get the real scalar array handle */
379f6829af0SVijay Mahadevan   varray = reinterpret_cast<PetscScalar**>(array);
380f6829af0SVijay Mahadevan 
381f6829af0SVijay Mahadevan   if (vmoab->is_native_vec) {
382f6829af0SVijay Mahadevan     /* Get the Vec_MOAB struct for the original vector */
3839566063dSJacob Faibussowitsch     PetscCall(PetscObjectQuery((PetscObject)vmoab->local, "MOABData", (PetscObject*) &moabdata));
3849566063dSJacob Faibussowitsch     PetscCall(PetscContainerGetPointer(moabdata, (void**)&xmoab));
385f6829af0SVijay Mahadevan 
386f6829af0SVijay Mahadevan     /* restore the local representation of the arrays from Vectors */
3879566063dSJacob Faibussowitsch     PetscCall(VecRestoreArray(xmoab->local, varray));
3889566063dSJacob Faibussowitsch     PetscCall(VecGhostRestoreLocalForm(vmoab->local, &xmoab->local));
389f6829af0SVijay Mahadevan 
390f6829af0SVijay Mahadevan     /* restore local pieces */
3919566063dSJacob Faibussowitsch     PetscCall(DMRestoreLocalVector(dm, &vmoab->local));
392f6829af0SVijay Mahadevan   }
393f6829af0SVijay Mahadevan   else {
394f6829af0SVijay Mahadevan     /* Nothing to do but just free the memory allocated before */
3959566063dSJacob Faibussowitsch     PetscCall(PetscFree(*varray));
396f6829af0SVijay Mahadevan 
397f6829af0SVijay Mahadevan   }
398f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
399f6829af0SVijay Mahadevan }
400f6829af0SVijay Mahadevan 
401f6829af0SVijay Mahadevan PetscErrorCode DMCreateVector_Moab_Private(DM dm, moab::Tag tag, const moab::Range* userrange, PetscBool is_global_vec, PetscBool destroy_tag, Vec *vec)
402032b8ab6SVijay Mahadevan {
403032b8ab6SVijay Mahadevan   moab::ErrorCode   merr;
404032b8ab6SVijay Mahadevan   PetscBool         is_newtag;
405351b8a77SVijay Mahadevan   const moab::Range *range;
406bb8f3634SVijay Mahadevan   PetscInt          count, lnative_vec, gnative_vec;
4079088682fSVijay Mahadevan   std::string       ttname;
408c4427235SVijay Mahadevan   PetscScalar       *data_ptr, *defaultvals;
409032b8ab6SVijay Mahadevan 
410db66d124SVijay Mahadevan   Vec_MOAB *vmoab;
411032b8ab6SVijay Mahadevan   DM_Moab *dmmoab = (DM_Moab*)dm->data;
4129daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
413032b8ab6SVijay Mahadevan   moab::ParallelComm *pcomm = dmmoab->pcomm;
4149daf19fdSVijay Mahadevan #endif
415032b8ab6SVijay Mahadevan   moab::Interface *mbiface = dmmoab->mbiface;
416032b8ab6SVijay Mahadevan 
417032b8ab6SVijay Mahadevan   PetscFunctionBegin;
41808401ef6SPierre Jolivet   PetscCheck(sizeof(PetscReal) == sizeof(PetscScalar),PETSC_COMM_SELF, PETSC_ERR_ARG_SIZ, "MOAB tags only support Real types (Complex-type unsupported)");
419032b8ab6SVijay Mahadevan   if (!userrange) range = dmmoab->vowned;
420032b8ab6SVijay Mahadevan   else range = userrange;
4217a8be351SBarry Smith   PetscCheck(range,PETSC_COMM_WORLD, PETSC_ERR_ARG_WRONG, "Input range cannot be empty or call DMSetUp first.");
422032b8ab6SVijay Mahadevan 
4233ac71f70SVijay Mahadevan #ifndef USE_NATIVE_PETSCVEC
424bb8f3634SVijay Mahadevan   /* If the tag data is in a single sequence, use PETSc native vector since tag_iterate isn't useful anymore */
425bb8f3634SVijay Mahadevan   lnative_vec = (range->psize() - 1);
4263ac71f70SVijay Mahadevan #else
4273ac71f70SVijay Mahadevan   lnative_vec = 1; /* NOTE: Testing PETSc vector: will force to create native vector all the time */
4286465f021SVijay Mahadevan //  lnative_vec=0; /* NOTE: Testing MOAB vector: will force to create MOAB tag_iterate based vector all the time */
429f6829af0SVijay Mahadevan #endif
4303ac71f70SVijay Mahadevan 
4319daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
4321c2dc1cbSBarry Smith   PetscCall(MPIU_Allreduce(&lnative_vec, &gnative_vec, 1, MPI_INT, MPI_MAX, (((PetscObject)dm)->comm)));
4339daf19fdSVijay Mahadevan #else
4349daf19fdSVijay Mahadevan   gnative_vec = lnative_vec;
4359daf19fdSVijay Mahadevan #endif
436bb8f3634SVijay Mahadevan 
437bb8f3634SVijay Mahadevan   /* Create the MOAB internal data object */
4389566063dSJacob Faibussowitsch   PetscCall(PetscNew(&vmoab));
439bb8f3634SVijay Mahadevan   vmoab->is_native_vec = (gnative_vec > 0 ? PETSC_TRUE : PETSC_FALSE);
440bb8f3634SVijay Mahadevan 
441bb8f3634SVijay Mahadevan   if (!vmoab->is_native_vec) {
4423ac71f70SVijay Mahadevan     merr = moab::MB_SUCCESS;
44364e1c140SVijay Mahadevan     if (tag != 0) merr = mbiface->tag_get_name(tag, ttname);
44464e1c140SVijay Mahadevan     if (!ttname.length() || merr != moab::MB_SUCCESS) {
445db66d124SVijay Mahadevan       /* get the new name for the anonymous MOABVec -> the tag_name will be destroyed along with Tag */
446c528d872SBarry Smith       char *tag_name = NULL;
4479daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
4489566063dSJacob Faibussowitsch       PetscCall(DMVecCreateTagName_Moab_Private(mbiface,pcomm,&tag_name));
4499daf19fdSVijay Mahadevan #else
4509566063dSJacob Faibussowitsch       PetscCall(DMVecCreateTagName_Moab_Private(mbiface,&tag_name));
4519daf19fdSVijay Mahadevan #endif
452032b8ab6SVijay Mahadevan       is_newtag = PETSC_TRUE;
453032b8ab6SVijay Mahadevan 
454db66d124SVijay Mahadevan       /* Create the default value for the tag (all zeros) */
4559566063dSJacob Faibussowitsch       PetscCall(PetscCalloc1(dmmoab->numFields, &defaultvals));
456032b8ab6SVijay Mahadevan 
457db66d124SVijay Mahadevan       /* Create the tag */
458d1839e75SVijay Mahadevan       merr = mbiface->tag_get_handle(tag_name, dmmoab->numFields, moab::MB_TYPE_DOUBLE, tag,
459c4427235SVijay Mahadevan                                      moab::MB_TAG_DENSE | moab::MB_TAG_CREAT, defaultvals); MBERRNM(merr);
4609566063dSJacob Faibussowitsch       PetscCall(PetscFree(tag_name));
4619566063dSJacob Faibussowitsch       PetscCall(PetscFree(defaultvals));
462032b8ab6SVijay Mahadevan     }
463032b8ab6SVijay Mahadevan     else {
464db66d124SVijay Mahadevan       /* Make sure the tag data is of type "double" */
465032b8ab6SVijay Mahadevan       moab::DataType tag_type;
466032b8ab6SVijay Mahadevan       merr = mbiface->tag_get_data_type(tag, tag_type); MBERRNM(merr);
4671dca8a05SBarry Smith       PetscCheck(tag_type == moab::MB_TYPE_DOUBLE,PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Tag data type must be MB_TYPE_DOUBLE");
468032b8ab6SVijay Mahadevan       is_newtag = destroy_tag;
469032b8ab6SVijay Mahadevan     }
470032b8ab6SVijay Mahadevan 
471032b8ab6SVijay Mahadevan     vmoab->tag = tag;
472bb8f3634SVijay Mahadevan     vmoab->new_tag = is_newtag;
473bb8f3634SVijay Mahadevan   }
474032b8ab6SVijay Mahadevan   vmoab->mbiface = mbiface;
4759daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
476032b8ab6SVijay Mahadevan   vmoab->pcomm = pcomm;
4779daf19fdSVijay Mahadevan #endif
478032b8ab6SVijay Mahadevan   vmoab->is_global_vec = is_global_vec;
479bb8f3634SVijay Mahadevan   vmoab->tag_size = dmmoab->bs;
480032b8ab6SVijay Mahadevan 
481bb8f3634SVijay Mahadevan   if (vmoab->is_native_vec) {
482fc418013SVijay Mahadevan 
483bb8f3634SVijay Mahadevan     /* Create the PETSc Vector directly and attach our functions accordingly */
484bb8f3634SVijay Mahadevan     if (!is_global_vec) {
485bb8f3634SVijay Mahadevan       /* This is an MPI Vector with ghosted padding */
4869566063dSJacob Faibussowitsch       PetscCall(VecCreateGhostBlock((((PetscObject)dm)->comm), dmmoab->bs, dmmoab->numFields * dmmoab->nloc,dmmoab->numFields * dmmoab->n, dmmoab->nghost, &dmmoab->gsindices[dmmoab->nloc], vec));
4875f80ce2aSJacob Faibussowitsch     } else {
488bb8f3634SVijay Mahadevan       /* This is an MPI/SEQ Vector */
4899566063dSJacob Faibussowitsch       PetscCall(VecCreate((((PetscObject)dm)->comm), vec));
4909566063dSJacob Faibussowitsch       PetscCall(VecSetSizes(*vec, dmmoab->numFields * dmmoab->nloc, PETSC_DECIDE));
4919566063dSJacob Faibussowitsch       PetscCall(VecSetBlockSize(*vec, dmmoab->bs));
4929566063dSJacob Faibussowitsch       PetscCall(VecSetType(*vec, VECMPI));
493bb8f3634SVijay Mahadevan     }
4945f80ce2aSJacob Faibussowitsch   } else {
495db66d124SVijay Mahadevan     /* Call tag_iterate. This will cause MOAB to allocate memory for the
496db66d124SVijay Mahadevan        tag data if it hasn't already happened */
497032b8ab6SVijay Mahadevan     merr = mbiface->tag_iterate(tag, range->begin(), range->end(), count, (void*&)data_ptr); MBERRNM(merr);
498032b8ab6SVijay Mahadevan 
499bb8f3634SVijay Mahadevan     /* set the reference for vector range */
500bb8f3634SVijay Mahadevan     vmoab->tag_range = new moab::Range(*range);
501addae81cSVijay Mahadevan     merr = mbiface->tag_get_length(tag, dmmoab->numFields); MBERRNM(merr);
502032b8ab6SVijay Mahadevan 
503db66d124SVijay Mahadevan     /* Create the PETSc Vector
504db66d124SVijay Mahadevan       Query MOAB mesh to check if there are any ghosted entities
505032b8ab6SVijay Mahadevan         -> if we do, create a ghosted vector to map correctly to the same layout
506032b8ab6SVijay Mahadevan         -> else, create a non-ghosted parallel vector */
507bb8f3634SVijay Mahadevan     if (!is_global_vec) {
508db66d124SVijay Mahadevan       /* This is an MPI Vector with ghosted padding */
5099566063dSJacob Faibussowitsch       PetscCall(VecCreateGhostBlockWithArray((((PetscObject)dm)->comm), dmmoab->bs, dmmoab->numFields * dmmoab->nloc,dmmoab->numFields * dmmoab->n, dmmoab->nghost, &dmmoab->gsindices[dmmoab->nloc], data_ptr, vec));
5105f80ce2aSJacob Faibussowitsch     } else {
511bb8f3634SVijay Mahadevan       /* This is an MPI Vector without ghosted padding */
5129566063dSJacob Faibussowitsch       PetscCall(VecCreateMPIWithArray((((PetscObject)dm)->comm), dmmoab->bs, dmmoab->numFields * range->size(),PETSC_DECIDE, data_ptr, vec));
513032b8ab6SVijay Mahadevan     }
514bb8f3634SVijay Mahadevan   }
5159566063dSJacob Faibussowitsch   PetscCall(VecSetFromOptions(*vec));
516032b8ab6SVijay Mahadevan 
517f6829af0SVijay Mahadevan   /* create a container and store the internal MOAB data for faster access based on Entities etc */
518032b8ab6SVijay Mahadevan   PetscContainer moabdata;
5199566063dSJacob Faibussowitsch   PetscCall(PetscContainerCreate(PETSC_COMM_WORLD, &moabdata));
5209566063dSJacob Faibussowitsch   PetscCall(PetscContainerSetPointer(moabdata, vmoab));
5219566063dSJacob Faibussowitsch   PetscCall(PetscContainerSetUserDestroy(moabdata, DMVecUserDestroy_Moab));
5229566063dSJacob Faibussowitsch   PetscCall(PetscObjectCompose((PetscObject) * vec, "MOABData", (PetscObject)moabdata));
523f6829af0SVijay Mahadevan   (*vec)->ops->duplicate = DMVecDuplicate_Moab;
5249566063dSJacob Faibussowitsch   PetscCall(PetscContainerDestroy(&moabdata));
525032b8ab6SVijay Mahadevan 
526db66d124SVijay Mahadevan   /* Vector created, manually set local to global mapping */
5276d9eb265SVijay Mahadevan   if (dmmoab->ltog_map) {
5289566063dSJacob Faibussowitsch     PetscCall(VecSetLocalToGlobalMapping(*vec, dmmoab->ltog_map));
5296d9eb265SVijay Mahadevan   }
530032b8ab6SVijay Mahadevan 
531032b8ab6SVijay Mahadevan   /* set the DM reference to the vector */
5329566063dSJacob Faibussowitsch   PetscCall(VecSetDM(*vec, dm));
533032b8ab6SVijay Mahadevan   PetscFunctionReturn(0);
534032b8ab6SVijay Mahadevan }
535032b8ab6SVijay Mahadevan 
536f6829af0SVijay Mahadevan /*  DMVecCreateTagName_Moab_Private
537032b8ab6SVijay Mahadevan  *
538032b8ab6SVijay Mahadevan  *  Creates a unique tag name that will be shared across processes. If
539032b8ab6SVijay Mahadevan  *  pcomm is NULL, then this is a serial vector. A unique tag name
540032b8ab6SVijay Mahadevan  *  will be returned in tag_name in either case.
541032b8ab6SVijay Mahadevan  *
542032b8ab6SVijay Mahadevan  *  The tag names have the format _PETSC_VEC_N where N is some integer.
543032b8ab6SVijay Mahadevan  *
544032b8ab6SVijay Mahadevan  *  NOTE: The tag_name is allocated in this routine; The user needs to free
545032b8ab6SVijay Mahadevan  *        the character array.
546032b8ab6SVijay Mahadevan  */
5479daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
5489daf19fdSVijay Mahadevan PetscErrorCode DMVecCreateTagName_Moab_Private(moab::Interface *mbiface, moab::ParallelComm *pcomm, char** tag_name)
5499daf19fdSVijay Mahadevan #else
5509daf19fdSVijay Mahadevan PetscErrorCode DMVecCreateTagName_Moab_Private(moab::Interface *mbiface, char** tag_name)
5519daf19fdSVijay Mahadevan #endif
552032b8ab6SVijay Mahadevan {
553032b8ab6SVijay Mahadevan   moab::ErrorCode mberr;
554032b8ab6SVijay Mahadevan   PetscInt        n, global_n;
555032b8ab6SVijay Mahadevan   moab::Tag indexTag;
556032b8ab6SVijay Mahadevan 
557032b8ab6SVijay Mahadevan   PetscFunctionBegin;
558032b8ab6SVijay Mahadevan   const char*       PVEC_PREFIX      = "__PETSC_VEC_";
5599566063dSJacob Faibussowitsch   PetscCall(PetscMalloc1(PETSC_MAX_PATH_LEN, tag_name));
560032b8ab6SVijay Mahadevan 
561032b8ab6SVijay Mahadevan   moab::EntityHandle rootset = mbiface->get_root_set();
562032b8ab6SVijay Mahadevan 
5639daf19fdSVijay Mahadevan   /* Check to see if there are any PETSc vectors defined */
564efd17f3eSVijay Mahadevan   /* Create a tag in MOAB mesh to index and keep track of number of Petsc vec tags */
565032b8ab6SVijay Mahadevan   mberr = mbiface->tag_get_handle("__PETSC_VECS__", 1, moab::MB_TYPE_INTEGER, indexTag,
566032b8ab6SVijay Mahadevan                                   moab::MB_TAG_SPARSE | moab::MB_TAG_CREAT, 0); MBERRNM(mberr);
567032b8ab6SVijay Mahadevan   mberr = mbiface->tag_get_data(indexTag, &rootset, 1, &n);
568032b8ab6SVijay Mahadevan   if (mberr == moab::MB_TAG_NOT_FOUND) n = 0; /* this is the first temporary vector */
569032b8ab6SVijay Mahadevan   else MBERRNM(mberr);
570032b8ab6SVijay Mahadevan 
571032b8ab6SVijay Mahadevan   /* increment the new value of n */
572032b8ab6SVijay Mahadevan   ++n;
573032b8ab6SVijay Mahadevan 
5749daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
575efd17f3eSVijay Mahadevan   /* Make sure that n is consistent across all processes */
5761c2dc1cbSBarry Smith   PetscCall(MPIU_Allreduce(&n, &global_n, 1, MPI_INT, MPI_MAX, pcomm->comm()));
5779daf19fdSVijay Mahadevan #else
5789daf19fdSVijay Mahadevan   global_n = n;
5799daf19fdSVijay Mahadevan #endif
580032b8ab6SVijay Mahadevan 
581efd17f3eSVijay Mahadevan   /* Set the new name accordingly and return */
58263a3b9bcSJacob Faibussowitsch   PetscCall(PetscSNPrintf(*tag_name, PETSC_MAX_PATH_LEN - 1, "%s_%" PetscInt_FMT, PVEC_PREFIX, global_n));
583032b8ab6SVijay Mahadevan   mberr = mbiface->tag_set_data(indexTag, &rootset, 1, (const void*)&global_n); MBERRNM(mberr);
584032b8ab6SVijay Mahadevan   PetscFunctionReturn(0);
585032b8ab6SVijay Mahadevan }
586032b8ab6SVijay Mahadevan 
587304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode DMCreateGlobalVector_Moab(DM dm, Vec *gvec)
588f6829af0SVijay Mahadevan {
589f6829af0SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
590f6829af0SVijay Mahadevan 
591f6829af0SVijay Mahadevan   PetscFunctionBegin;
592f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
593f6829af0SVijay Mahadevan   PetscValidPointer(gvec,2);
5949566063dSJacob Faibussowitsch   PetscCall(DMCreateVector_Moab_Private(dm,NULL,dmmoab->vowned,PETSC_TRUE,PETSC_TRUE,gvec));
595f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
596f6829af0SVijay Mahadevan }
597f6829af0SVijay Mahadevan 
598304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode DMCreateLocalVector_Moab(DM dm, Vec *lvec)
599f6829af0SVijay Mahadevan {
600f6829af0SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
601f6829af0SVijay Mahadevan 
602f6829af0SVijay Mahadevan   PetscFunctionBegin;
603f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
604f6829af0SVijay Mahadevan   PetscValidPointer(lvec,2);
6059566063dSJacob Faibussowitsch   PetscCall(DMCreateVector_Moab_Private(dm,NULL,dmmoab->vlocal,PETSC_FALSE,PETSC_TRUE,lvec));
606f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
607f6829af0SVijay Mahadevan }
608f6829af0SVijay Mahadevan 
609f6829af0SVijay Mahadevan PetscErrorCode DMVecDuplicate_Moab(Vec x, Vec *y)
610f6829af0SVijay Mahadevan {
611f6829af0SVijay Mahadevan   DM             dm;
612f6829af0SVijay Mahadevan   PetscContainer  moabdata;
613f6829af0SVijay Mahadevan   Vec_MOAB        *vmoab;
614f6829af0SVijay Mahadevan 
615f6829af0SVijay Mahadevan   PetscFunctionBegin;
616f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(x, VEC_CLASSID, 1);
617f6829af0SVijay Mahadevan   PetscValidPointer(y, 2);
618f6829af0SVijay Mahadevan 
619f6829af0SVijay Mahadevan   /* Get the Vec_MOAB struct for the original vector */
6209566063dSJacob Faibussowitsch   PetscCall(PetscObjectQuery((PetscObject)x, "MOABData", (PetscObject*) &moabdata));
6219566063dSJacob Faibussowitsch   PetscCall(PetscContainerGetPointer(moabdata, (void**)&vmoab));
622f6829af0SVijay Mahadevan 
6239566063dSJacob Faibussowitsch   PetscCall(VecGetDM(x, &dm));
624f6829af0SVijay Mahadevan   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
625f6829af0SVijay Mahadevan 
6269566063dSJacob Faibussowitsch   PetscCall(DMCreateVector_Moab_Private(dm,NULL,vmoab->tag_range,vmoab->is_global_vec,PETSC_TRUE,y));
6279566063dSJacob Faibussowitsch   PetscCall(VecSetDM(*y, dm));
628f6829af0SVijay Mahadevan   PetscFunctionReturn(0);
629f6829af0SVijay Mahadevan }
630f6829af0SVijay Mahadevan 
631f6829af0SVijay Mahadevan PetscErrorCode DMVecUserDestroy_Moab(void *user)
632032b8ab6SVijay Mahadevan {
633efd17f3eSVijay Mahadevan   Vec_MOAB        *vmoab = (Vec_MOAB*)user;
634032b8ab6SVijay Mahadevan   moab::ErrorCode merr;
635032b8ab6SVijay Mahadevan 
636032b8ab6SVijay Mahadevan   PetscFunctionBegin;
637032b8ab6SVijay Mahadevan   if (vmoab->new_tag && vmoab->tag) {
638efd17f3eSVijay Mahadevan     /* Tag was created via a call to VecDuplicate, delete the underlying tag in MOAB */
639032b8ab6SVijay Mahadevan     merr = vmoab->mbiface->tag_delete(vmoab->tag); MBERRNM(merr);
640032b8ab6SVijay Mahadevan   }
641032b8ab6SVijay Mahadevan   delete vmoab->tag_range;
642c528d872SBarry Smith   vmoab->tag = NULL;
643c528d872SBarry Smith   vmoab->mbiface = NULL;
6449daf19fdSVijay Mahadevan #ifdef MOAB_HAVE_MPI
645c528d872SBarry Smith   vmoab->pcomm = NULL;
6469daf19fdSVijay Mahadevan #endif
6479566063dSJacob Faibussowitsch   PetscCall(PetscFree(vmoab));
648032b8ab6SVijay Mahadevan   PetscFunctionReturn(0);
649032b8ab6SVijay Mahadevan }
650032b8ab6SVijay Mahadevan 
651304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode  DMGlobalToLocalBegin_Moab(DM dm, Vec g, InsertMode mode, Vec l)
652db66d124SVijay Mahadevan {
653db66d124SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
654db66d124SVijay Mahadevan 
655db66d124SVijay Mahadevan   PetscFunctionBegin;
6569566063dSJacob Faibussowitsch   PetscCall(VecScatterBegin(dmmoab->ltog_sendrecv, g, l, mode, SCATTER_REVERSE));
657db66d124SVijay Mahadevan   PetscFunctionReturn(0);
658db66d124SVijay Mahadevan }
659db66d124SVijay Mahadevan 
660304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode  DMGlobalToLocalEnd_Moab(DM dm, Vec g, InsertMode mode, Vec l)
661db66d124SVijay Mahadevan {
662db66d124SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
663db66d124SVijay Mahadevan 
664db66d124SVijay Mahadevan   PetscFunctionBegin;
6659566063dSJacob Faibussowitsch   PetscCall(VecScatterEnd(dmmoab->ltog_sendrecv, g, l, mode, SCATTER_REVERSE));
666db66d124SVijay Mahadevan   PetscFunctionReturn(0);
667db66d124SVijay Mahadevan }
668db66d124SVijay Mahadevan 
669304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode  DMLocalToGlobalBegin_Moab(DM dm, Vec l, InsertMode mode, Vec g)
670db66d124SVijay Mahadevan {
671db66d124SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
672db66d124SVijay Mahadevan 
673db66d124SVijay Mahadevan   PetscFunctionBegin;
6749566063dSJacob Faibussowitsch   PetscCall(VecScatterBegin(dmmoab->ltog_sendrecv, l, g, mode, SCATTER_FORWARD));
675db66d124SVijay Mahadevan   PetscFunctionReturn(0);
676db66d124SVijay Mahadevan }
677db66d124SVijay Mahadevan 
678304006b3SVijay Mahadevan PETSC_EXTERN PetscErrorCode  DMLocalToGlobalEnd_Moab(DM dm, Vec l, InsertMode mode, Vec g)
679db66d124SVijay Mahadevan {
680db66d124SVijay Mahadevan   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
681db66d124SVijay Mahadevan 
682db66d124SVijay Mahadevan   PetscFunctionBegin;
6839566063dSJacob Faibussowitsch   PetscCall(VecScatterEnd(dmmoab->ltog_sendrecv, l, g, mode, SCATTER_FORWARD));
684db66d124SVijay Mahadevan   PetscFunctionReturn(0);
685db66d124SVijay Mahadevan }
686