xref: /petsc/src/dm/impls/moab/dmmoab.cxx (revision 7d89fc02abab604d15ad492b6847af8e660b0065)
11d72bce8STim Tautges #include <petsc-private/dmimpl.h> /*I  "petscdm.h"   I*/
2aa768e4cSTim Tautges #include <petsc-private/vecimpl.h> /*I  "petscdm.h"   I*/
31d72bce8STim Tautges 
41d72bce8STim Tautges #include <petscdmmoab.h>
51d72bce8STim Tautges #include "MBTagConventions.hpp"
61d72bce8STim Tautges 
71d72bce8STim Tautges typedef struct {
81d72bce8STim Tautges   PetscInt bs; /* Number of degrees of freedom on each entity, aka tag size in moab */
91d72bce8STim Tautges   PetscBool icreatedinstance; /* true if DM created moab instance internally, will destroy instance in DMDestroy */
101d72bce8STim Tautges   moab::ParallelComm *pcomm;
11a4d2169cSTim Tautges   moab::Interface *mbiface;
121d72bce8STim Tautges   moab::Tag ltog_tag; /* moab supports "global id" tags, which are usually local to global numbering */
131d72bce8STim Tautges   moab::Range range;
141d72bce8STim Tautges } DM_Moab;
151d72bce8STim Tautges 
16a4d2169cSTim Tautges typedef struct {
17a4d2169cSTim Tautges   moab::Interface    *mbiface;
18a4d2169cSTim Tautges   moab::ParallelComm *pcomm;
19a4d2169cSTim Tautges   moab::Range         tag_range; /* entities to which this tag applies */
20a4d2169cSTim Tautges   moab::Tag           tag;
21a4d2169cSTim Tautges   moab::Tag           ltog_tag;
22a4d2169cSTim Tautges   PetscInt            tag_size;
23a4d2169cSTim Tautges   PetscBool           new_tag;
24a4d2169cSTim Tautges   PetscBool           serial;
25a4d2169cSTim Tautges 
26a4d2169cSTim Tautges } Vec_MOAB;
27a4d2169cSTim Tautges 
281d72bce8STim Tautges #undef __FUNCT__
29fd349b41STim Tautges #define __FUNCT__ "DMCreateGlobalVector_Moab"
30fd349b41STim Tautges PetscErrorCode DMCreateGlobalVector_Moab(DM dm,Vec *gvec)
31fd349b41STim Tautges {
32fd349b41STim Tautges   PetscErrorCode  ierr;
33fd349b41STim Tautges   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
34fd349b41STim Tautges 
35fd349b41STim Tautges   PetscFunctionBegin;
36fd349b41STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
37fd349b41STim Tautges   PetscValidPointer(gvec,2);
38fd349b41STim Tautges   PetscInt block_size = ((DM_Moab*)dm->data)->bs;
39a4d2169cSTim Tautges   moab::Tag tag = 0;
40a4d2169cSTim Tautges   ierr = DMMoabCreateVector(dm,tag,block_size,dmmoab->range,PETSC_FALSE,PETSC_TRUE,gvec);CHKERRQ(ierr);
41fd349b41STim Tautges   PetscFunctionReturn(0);
42fd349b41STim Tautges }
43fd349b41STim Tautges 
44fd349b41STim Tautges 
45fd349b41STim Tautges #undef __FUNCT__
46fd349b41STim Tautges #define __FUNCT__ "DMCreateLocalVector_Moab"
47fd349b41STim Tautges PetscErrorCode DMCreateLocalVector_Moab(DM dm,Vec *gvec)
48fd349b41STim Tautges {
49fd349b41STim Tautges   PetscErrorCode  ierr;
50fd349b41STim Tautges   DM_Moab         *dmmoab = (DM_Moab*)dm->data;
51fd349b41STim Tautges 
52fd349b41STim Tautges   PetscFunctionBegin;
53fd349b41STim Tautges   PetscInt bs = 1;
54fd349b41STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
55fd349b41STim Tautges   PetscValidPointer(gvec,2);
56a4d2169cSTim Tautges   moab::Tag tag = 0;
57a4d2169cSTim Tautges   ierr = DMMoabCreateVector(dm,tag,bs,dmmoab->range,PETSC_TRUE,PETSC_TRUE,gvec);CHKERRQ(ierr);
58fd349b41STim Tautges   PetscFunctionReturn(0);
59fd349b41STim Tautges }
60fd349b41STim Tautges 
61aa768e4cSTim Tautges EXTERN_C_BEGIN
62aa768e4cSTim Tautges #undef __FUNCT__
63aa768e4cSTim Tautges #define __FUNCT__ "DMCreate_Moab"
64aa768e4cSTim Tautges PetscErrorCode DMCreate_Moab(DM dm)
65aa768e4cSTim Tautges {
66aa768e4cSTim Tautges   DM_Moab        *moab;
67aa768e4cSTim Tautges   PetscErrorCode ierr;
68aa768e4cSTim Tautges 
69aa768e4cSTim Tautges   PetscFunctionBegin;
70aa768e4cSTim Tautges   PetscValidHeaderSpecific(dm, DM_CLASSID, 1);
71aa768e4cSTim Tautges   ierr     = PetscNewLog(dm, DM_Moab, &moab);CHKERRQ(ierr);
72aa768e4cSTim Tautges   dm->data = moab;
73aa768e4cSTim Tautges 
74aa768e4cSTim Tautges   PetscFunctionReturn(0);
75aa768e4cSTim Tautges }
76aa768e4cSTim Tautges EXTERN_C_END
77aa768e4cSTim Tautges 
78fd349b41STim Tautges #undef __FUNCT__
79fd349b41STim Tautges #define __FUNCT__ "DMDestroy_Moab"
80fd349b41STim Tautges PetscErrorCode DMDestroy_Moab(DM dm)
81fd349b41STim Tautges {
82fd349b41STim Tautges   PetscFunctionBegin;
83fd349b41STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
84fd349b41STim Tautges 
85fd349b41STim Tautges   // Delete the DM_Moab:
86fd349b41STim Tautges   if(dm->data) {
87fd349b41STim Tautges     if (((DM_Moab*)dm->data)->icreatedinstance) {
88a4d2169cSTim Tautges       delete ((DM_Moab*)dm->data)->mbiface;
89a4d2169cSTim Tautges       ((DM_Moab*)dm->data)->mbiface = NULL;
90fd349b41STim Tautges       ((DM_Moab*)dm->data)->pcomm = NULL;
91fd349b41STim Tautges     }
92fd349b41STim Tautges     delete (DM_Moab*)dm->data;
93fd349b41STim Tautges     dm->data = NULL;
94fd349b41STim Tautges   }
95fd349b41STim Tautges   PetscFunctionReturn(0);
96fd349b41STim Tautges }
97fd349b41STim Tautges 
98fd349b41STim Tautges 
99fd349b41STim Tautges #undef __FUNCT__
1001d72bce8STim Tautges #define __FUNCT__ "DMMoabCreate"
1011d72bce8STim Tautges /*@
1021d72bce8STim Tautges   DMMoabCreate - Creates a DMMoab object, which encapsulates a moab instance
1031d72bce8STim Tautges 
1041d72bce8STim Tautges   Collective on MPI_Comm
1051d72bce8STim Tautges 
1061d72bce8STim Tautges   Input Parameter:
1071d72bce8STim Tautges . comm - The communicator for the DMMoab object
1081d72bce8STim Tautges 
1091d72bce8STim Tautges   Output Parameter:
1101d72bce8STim Tautges . moab  - The DMMoab object
1111d72bce8STim Tautges 
1121d72bce8STim Tautges   Level: beginner
1131d72bce8STim Tautges 
1141d72bce8STim Tautges .keywords: DMMoab, create
1151d72bce8STim Tautges @*/
1161d72bce8STim Tautges PetscErrorCode DMMoabCreate(MPI_Comm comm, DM *moab)
1171d72bce8STim Tautges {
1181d72bce8STim Tautges   PetscErrorCode ierr;
1191d72bce8STim Tautges 
1201d72bce8STim Tautges   PetscFunctionBegin;
1211d72bce8STim Tautges   PetscValidPointer(moab,2);
1221d72bce8STim Tautges   ierr = DMCreate(comm, moab);CHKERRQ(ierr);
1231d72bce8STim Tautges   ierr = DMSetType(*moab, DMMOAB);CHKERRQ(ierr);
1241d72bce8STim Tautges   PetscFunctionReturn(0);
1251d72bce8STim Tautges }
1261d72bce8STim Tautges 
1271d72bce8STim Tautges #undef __FUNCT__
128aa768e4cSTim Tautges #define __FUNCT__ "DMMoabCreateMoab"
1291d72bce8STim Tautges /*@
130a4d2169cSTim Tautges   DMMoabCreate - Creates a DMMoab object, optionally from an instance and other data
1311d72bce8STim Tautges 
1321d72bce8STim Tautges   Collective on MPI_Comm
1331d72bce8STim Tautges 
1341d72bce8STim Tautges   Input Parameter:
1351d72bce8STim Tautges . comm - The communicator for the DMMoab object
136a4d2169cSTim Tautges . moab - (ptr to) the MOAB Instance; if passed in NULL, MOAB instance is created inside PETSc, and destroyed
137a4d2169cSTim Tautges          along with the DMMoab
138a4d2169cSTim Tautges . pcomm - (ptr to) a ParallelComm; if NULL, creates one internally for the whole communicator
1391d72bce8STim Tautges . ltog_tag - A tag to use to retrieve global id for an entity; if 0, will use GLOBAL_ID_TAG_NAME/tag
1401d72bce8STim Tautges . range - If non-NULL, contains range of entities to which DOFs will be assigned
1411d72bce8STim Tautges 
1421d72bce8STim Tautges   Output Parameter:
1431d72bce8STim Tautges . moab  - The DMMoab object
1441d72bce8STim Tautges 
1451d72bce8STim Tautges   Level: beginner
1461d72bce8STim Tautges 
1471d72bce8STim Tautges .keywords: DMMoab, create
1481d72bce8STim Tautges @*/
149a4d2169cSTim Tautges PetscErrorCode DMMoabCreateMoab(MPI_Comm comm, moab::Interface *mbiface, moab::ParallelComm *pcomm, moab::Tag ltog_tag, moab::Range *range, DM *moab)
1501d72bce8STim Tautges {
1511d72bce8STim Tautges   PetscErrorCode ierr;
1521d72bce8STim Tautges 
1531d72bce8STim Tautges   PetscFunctionBegin;
1541d72bce8STim Tautges   PetscValidPointer(moab,2);
1551d72bce8STim Tautges   ierr = DMCreate(comm, moab);CHKERRQ(ierr);
1561d72bce8STim Tautges   ierr = DMSetType(*moab, DMMOAB);CHKERRQ(ierr);
157*7d89fc02STim Tautges   DM_Moab *dmmoab = new DM_Moab;
158*7d89fc02STim Tautges   (*moab)->data      = dmmoab;
159a4d2169cSTim Tautges 
160a4d2169cSTim Tautges   if (!mbiface) {
161a4d2169cSTim Tautges     mbiface = new moab::Core();
162*7d89fc02STim Tautges     dmmoab->icreatedinstance = PETSC_TRUE;
1631d72bce8STim Tautges   }
164*7d89fc02STim Tautges   else
165*7d89fc02STim Tautges     dmmoab->icreatedinstance = PETSC_FALSE;
166*7d89fc02STim Tautges 
167a4d2169cSTim Tautges   if (!pcomm) {
1681d72bce8STim Tautges     PetscInt rank, nprocs;
1691d72bce8STim Tautges     MPI_Comm_rank(comm, &rank);
1701d72bce8STim Tautges     MPI_Comm_size(comm, &nprocs);
171a4d2169cSTim Tautges     pcomm = new moab::ParallelComm(mbiface, comm);
172a4d2169cSTim Tautges   }
173a4d2169cSTim Tautges 
174a4d2169cSTim Tautges     // do the initialization of the DM
175a4d2169cSTim Tautges   dmmoab->bs       = 0;
176a4d2169cSTim Tautges   dmmoab->pcomm    = pcomm;
177a4d2169cSTim Tautges   dmmoab->mbiface    = mbiface;
178a4d2169cSTim Tautges   dmmoab->ltog_tag = ltog_tag;
179a4d2169cSTim Tautges 
180a4d2169cSTim Tautges     // initialize various functions
181a4d2169cSTim Tautges   (*moab)->ops->createglobalvector              = DMCreateGlobalVector_Moab;
182a4d2169cSTim Tautges   (*moab)->ops->createlocalvector               = DMCreateLocalVector_Moab;
183a4d2169cSTim Tautges   (*moab)->ops->destroy                         = DMDestroy_Moab;
184a4d2169cSTim Tautges 
185a4d2169cSTim Tautges   ierr = DMMoabSetInterface(*moab, mbiface);CHKERRQ(ierr);
186a4d2169cSTim Tautges   if (!pcomm) pcomm = new moab::ParallelComm(mbiface, comm);
187a4d2169cSTim Tautges   ierr = DMMoabSetParallelComm(*moab, pcomm);CHKERRQ(ierr);
188a4d2169cSTim Tautges   if (!ltog_tag) {
189a4d2169cSTim Tautges     moab::ErrorCode merr = mbiface->tag_get_handle(GLOBAL_ID_TAG_NAME, ltog_tag);MBERRNM(merr);
190a4d2169cSTim Tautges   }
191a4d2169cSTim Tautges   if (ltog_tag) {
192a4d2169cSTim Tautges     ierr = DMMoabSetLocalToGlobalTag(*moab, ltog_tag);CHKERRQ(ierr);
193a4d2169cSTim Tautges   }
194a4d2169cSTim Tautges   if (range) {
195a4d2169cSTim Tautges     ierr = DMMoabSetRange(*moab, *range);CHKERRQ(ierr);
196a4d2169cSTim Tautges   }
1971d72bce8STim Tautges   PetscFunctionReturn(0);
1981d72bce8STim Tautges }
1991d72bce8STim Tautges 
2001d72bce8STim Tautges #undef __FUNCT__
2011d72bce8STim Tautges #define __FUNCT__ "DMMoabSetParallelComm"
202aa768e4cSTim Tautges /*@
203aa768e4cSTim Tautges   DMMoabSetParallelComm - Set the ParallelComm used with this DMMoab
204aa768e4cSTim Tautges 
205aa768e4cSTim Tautges   Collective on MPI_Comm
206aa768e4cSTim Tautges 
207aa768e4cSTim Tautges   Input Parameter:
208aa768e4cSTim Tautges . dm    - The DMMoab object being set
209aa768e4cSTim Tautges . pcomm - The ParallelComm being set on the DMMoab
210aa768e4cSTim Tautges 
211aa768e4cSTim Tautges   Level: beginner
212aa768e4cSTim Tautges 
213aa768e4cSTim Tautges .keywords: DMMoab, create
214aa768e4cSTim Tautges @*/
2151d72bce8STim Tautges PetscErrorCode DMMoabSetParallelComm(DM dm,moab::ParallelComm *pcomm)
2161d72bce8STim Tautges {
2171d72bce8STim Tautges   PetscFunctionBegin;
2181d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
2191d72bce8STim Tautges   ((DM_Moab*)dm->data)->pcomm = pcomm;
220a4d2169cSTim Tautges   ((DM_Moab*)dm->data)->mbiface = pcomm->get_moab();
2211d72bce8STim Tautges   PetscFunctionReturn(0);
2221d72bce8STim Tautges }
2231d72bce8STim Tautges 
2241d72bce8STim Tautges 
2251d72bce8STim Tautges #undef __FUNCT__
2261d72bce8STim Tautges #define __FUNCT__ "DMMoabGetParallelComm"
227aa768e4cSTim Tautges /*@
228aa768e4cSTim Tautges   DMMoabGetParallelComm - Get the ParallelComm used with this DMMoab
229aa768e4cSTim Tautges 
230aa768e4cSTim Tautges   Collective on MPI_Comm
231aa768e4cSTim Tautges 
232aa768e4cSTim Tautges   Input Parameter:
233aa768e4cSTim Tautges . dm    - The DMMoab object being set
234aa768e4cSTim Tautges 
235aa768e4cSTim Tautges   Output Parameter:
236aa768e4cSTim Tautges . pcomm - The ParallelComm for the DMMoab
237aa768e4cSTim Tautges 
238aa768e4cSTim Tautges   Level: beginner
239aa768e4cSTim Tautges 
240aa768e4cSTim Tautges .keywords: DMMoab, create
241aa768e4cSTim Tautges @*/
2421d72bce8STim Tautges PetscErrorCode DMMoabGetParallelComm(DM dm,moab::ParallelComm **pcomm)
2431d72bce8STim Tautges {
2441d72bce8STim Tautges   PetscFunctionBegin;
2451d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
2461d72bce8STim Tautges   *pcomm = ((DM_Moab*)dm->data)->pcomm;
2471d72bce8STim Tautges   PetscFunctionReturn(0);
2481d72bce8STim Tautges }
2491d72bce8STim Tautges 
2501d72bce8STim Tautges 
2511d72bce8STim Tautges #undef __FUNCT__
2521d72bce8STim Tautges #define __FUNCT__ "DMMoabSetInterface"
253aa768e4cSTim Tautges /*@
254aa768e4cSTim Tautges   DMMoabSetInterface - Set the MOAB instance used with this DMMoab
255aa768e4cSTim Tautges 
256aa768e4cSTim Tautges   Collective on MPI_Comm
257aa768e4cSTim Tautges 
258aa768e4cSTim Tautges   Input Parameter:
259aa768e4cSTim Tautges . dm      - The DMMoab object being set
260aa768e4cSTim Tautges . mbiface - The MOAB instance being set on this DMMoab
261aa768e4cSTim Tautges 
262aa768e4cSTim Tautges   Level: beginner
263aa768e4cSTim Tautges 
264aa768e4cSTim Tautges .keywords: DMMoab, create
265aa768e4cSTim Tautges @*/
266a4d2169cSTim Tautges PetscErrorCode DMMoabSetInterface(DM dm,moab::Interface *mbiface)
2671d72bce8STim Tautges {
2681d72bce8STim Tautges   PetscFunctionBegin;
2691d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
2701d72bce8STim Tautges   ((DM_Moab*)dm->data)->pcomm = NULL;
271a4d2169cSTim Tautges   ((DM_Moab*)dm->data)->mbiface = mbiface;
2721d72bce8STim Tautges   PetscFunctionReturn(0);
2731d72bce8STim Tautges }
2741d72bce8STim Tautges 
2751d72bce8STim Tautges 
2761d72bce8STim Tautges #undef __FUNCT__
2771d72bce8STim Tautges #define __FUNCT__ "DMMoabGetInterface"
278aa768e4cSTim Tautges /*@
279aa768e4cSTim Tautges   DMMoabGetInterface - Get the MOAB instance used with this DMMoab
280aa768e4cSTim Tautges 
281aa768e4cSTim Tautges   Collective on MPI_Comm
282aa768e4cSTim Tautges 
283aa768e4cSTim Tautges   Input Parameter:
284aa768e4cSTim Tautges . dm      - The DMMoab object being set
285aa768e4cSTim Tautges 
286aa768e4cSTim Tautges   Output Parameter:
287aa768e4cSTim Tautges . mbiface - The MOAB instance set on this DMMoab
288aa768e4cSTim Tautges 
289aa768e4cSTim Tautges   Level: beginner
290aa768e4cSTim Tautges 
291aa768e4cSTim Tautges .keywords: DMMoab, create
292aa768e4cSTim Tautges @*/
293a4d2169cSTim Tautges PetscErrorCode DMMoabGetInterface(DM dm,moab::Interface **mbiface)
2941d72bce8STim Tautges {
2951d72bce8STim Tautges   PetscFunctionBegin;
2961d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
297a4d2169cSTim Tautges   *mbiface = ((DM_Moab*)dm->data)->mbiface;
2981d72bce8STim Tautges   PetscFunctionReturn(0);
2991d72bce8STim Tautges }
3001d72bce8STim Tautges 
3011d72bce8STim Tautges 
3021d72bce8STim Tautges #undef __FUNCT__
3031d72bce8STim Tautges #define __FUNCT__ "DMMoabSetRange"
304aa768e4cSTim Tautges /*@
305aa768e4cSTim Tautges   DMMoabSetRange - Set the entities having DOFs on this DMMoab
306aa768e4cSTim Tautges 
307aa768e4cSTim Tautges   Collective on MPI_Comm
308aa768e4cSTim Tautges 
309aa768e4cSTim Tautges   Input Parameter:
310aa768e4cSTim Tautges . dm    - The DMMoab object being set
311aa768e4cSTim Tautges . range - The entities treated by this DMMoab
312aa768e4cSTim Tautges 
313aa768e4cSTim Tautges   Level: beginner
314aa768e4cSTim Tautges 
315aa768e4cSTim Tautges .keywords: DMMoab, create
316aa768e4cSTim Tautges @*/
3171d72bce8STim Tautges PetscErrorCode DMMoabSetRange(DM dm,moab::Range range)
3181d72bce8STim Tautges {
3191d72bce8STim Tautges   PetscFunctionBegin;
3201d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
3211d72bce8STim Tautges   ((DM_Moab*)dm->data)->range = range;
3221d72bce8STim Tautges   PetscFunctionReturn(0);
3231d72bce8STim Tautges }
3241d72bce8STim Tautges 
3251d72bce8STim Tautges 
3261d72bce8STim Tautges #undef __FUNCT__
3271d72bce8STim Tautges #define __FUNCT__ "DMMoabGetRange"
328aa768e4cSTim Tautges /*@
329aa768e4cSTim Tautges   DMMoabGetRange - Get the entities having DOFs on this DMMoab
330aa768e4cSTim Tautges 
331aa768e4cSTim Tautges   Collective on MPI_Comm
332aa768e4cSTim Tautges 
333aa768e4cSTim Tautges   Input Parameter:
334aa768e4cSTim Tautges . dm    - The DMMoab object being set
335aa768e4cSTim Tautges 
336aa768e4cSTim Tautges   Output Parameter:
337aa768e4cSTim Tautges . range - The entities treated by this DMMoab
338aa768e4cSTim Tautges 
339aa768e4cSTim Tautges   Level: beginner
340aa768e4cSTim Tautges 
341aa768e4cSTim Tautges .keywords: DMMoab, create
342aa768e4cSTim Tautges @*/
3431d72bce8STim Tautges PetscErrorCode DMMoabGetRange(DM dm,moab::Range *range)
3441d72bce8STim Tautges {
3451d72bce8STim Tautges   PetscFunctionBegin;
3461d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
3471d72bce8STim Tautges   *range = ((DM_Moab*)dm->data)->range;
3481d72bce8STim Tautges   PetscFunctionReturn(0);
3491d72bce8STim Tautges }
3501d72bce8STim Tautges 
3511d72bce8STim Tautges #undef __FUNCT__
3521d72bce8STim Tautges #define __FUNCT__ "DMMoabSetLocalToGlobalTag"
353aa768e4cSTim Tautges /*@
354aa768e4cSTim Tautges   DMMoabSetLocalToGlobalTag - Set the tag used for local to global numbering
355aa768e4cSTim Tautges 
356aa768e4cSTim Tautges   Collective on MPI_Comm
357aa768e4cSTim Tautges 
358aa768e4cSTim Tautges   Input Parameter:
359aa768e4cSTim Tautges . dm      - The DMMoab object being set
360aa768e4cSTim Tautges . ltogtag - The MOAB tag used for local to global ids
361aa768e4cSTim Tautges 
362aa768e4cSTim Tautges   Level: beginner
363aa768e4cSTim Tautges 
364aa768e4cSTim Tautges .keywords: DMMoab, create
365aa768e4cSTim Tautges @*/
3661d72bce8STim Tautges PetscErrorCode DMMoabSetLocalToGlobalTag(DM dm,moab::Tag ltogtag)
3671d72bce8STim Tautges {
3681d72bce8STim Tautges   PetscFunctionBegin;
3691d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
3701d72bce8STim Tautges   ((DM_Moab*)dm->data)->ltog_tag = ltogtag;
3711d72bce8STim Tautges   PetscFunctionReturn(0);
3721d72bce8STim Tautges }
3731d72bce8STim Tautges 
3741d72bce8STim Tautges 
3751d72bce8STim Tautges #undef __FUNCT__
3761d72bce8STim Tautges #define __FUNCT__ "DMMoabGetLocalToGlobalTag"
377aa768e4cSTim Tautges /*@
378aa768e4cSTim Tautges   DMMoabGetLocalToGlobalTag - Get the tag used for local to global numbering
379aa768e4cSTim Tautges 
380aa768e4cSTim Tautges   Collective on MPI_Comm
381aa768e4cSTim Tautges 
382aa768e4cSTim Tautges   Input Parameter:
383aa768e4cSTim Tautges . dm      - The DMMoab object being set
384aa768e4cSTim Tautges 
385aa768e4cSTim Tautges   Output Parameter:
386aa768e4cSTim Tautges . ltogtag - The MOAB tag used for local to global ids
387aa768e4cSTim Tautges 
388aa768e4cSTim Tautges   Level: beginner
389aa768e4cSTim Tautges 
390aa768e4cSTim Tautges .keywords: DMMoab, create
391aa768e4cSTim Tautges @*/
3921d72bce8STim Tautges PetscErrorCode DMMoabGetLocalToGlobalTag(DM dm,moab::Tag *ltog_tag)
3931d72bce8STim Tautges {
3941d72bce8STim Tautges   PetscFunctionBegin;
3951d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
3961d72bce8STim Tautges   *ltog_tag = ((DM_Moab*)dm->data)->ltog_tag;
3971d72bce8STim Tautges   PetscFunctionReturn(0);
3981d72bce8STim Tautges }
3991d72bce8STim Tautges 
4001d72bce8STim Tautges 
4011d72bce8STim Tautges #undef __FUNCT__
4021d72bce8STim Tautges #define __FUNCT__ "DMMoabSetBlockSize"
403aa768e4cSTim Tautges /*@
404aa768e4cSTim Tautges   DMMoabSetBlockSize - Set the block size used with this DMMoab
405aa768e4cSTim Tautges 
406aa768e4cSTim Tautges   Collective on MPI_Comm
407aa768e4cSTim Tautges 
408aa768e4cSTim Tautges   Input Parameter:
409aa768e4cSTim Tautges . dm - The DMMoab object being set
410aa768e4cSTim Tautges . bs - The block size used with this DMMoab
411aa768e4cSTim Tautges 
412aa768e4cSTim Tautges   Level: beginner
413aa768e4cSTim Tautges 
414aa768e4cSTim Tautges .keywords: DMMoab, create
415aa768e4cSTim Tautges @*/
4161d72bce8STim Tautges PetscErrorCode DMMoabSetBlockSize(DM dm,PetscInt bs)
4171d72bce8STim Tautges {
4181d72bce8STim Tautges   PetscFunctionBegin;
4191d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
4201d72bce8STim Tautges   ((DM_Moab*)dm->data)->bs = bs;
4211d72bce8STim Tautges   PetscFunctionReturn(0);
4221d72bce8STim Tautges }
4231d72bce8STim Tautges 
4241d72bce8STim Tautges 
4251d72bce8STim Tautges #undef __FUNCT__
4261d72bce8STim Tautges #define __FUNCT__ "DMMoabGetBlockSize"
427aa768e4cSTim Tautges /*@
428aa768e4cSTim Tautges   DMMoabGetBlockSize - Get the block size used with this DMMoab
429aa768e4cSTim Tautges 
430aa768e4cSTim Tautges   Collective on MPI_Comm
431aa768e4cSTim Tautges 
432aa768e4cSTim Tautges   Input Parameter:
433aa768e4cSTim Tautges . dm - The DMMoab object being set
434aa768e4cSTim Tautges 
435aa768e4cSTim Tautges   Output Parameter:
436aa768e4cSTim Tautges . bs - The block size used with this DMMoab
437aa768e4cSTim Tautges 
438aa768e4cSTim Tautges   Level: beginner
439aa768e4cSTim Tautges 
440aa768e4cSTim Tautges .keywords: DMMoab, create
441aa768e4cSTim Tautges @*/
4421d72bce8STim Tautges PetscErrorCode DMMoabGetBlockSize(DM dm,PetscInt *bs)
4431d72bce8STim Tautges {
4441d72bce8STim Tautges   PetscFunctionBegin;
4451d72bce8STim Tautges   PetscValidHeaderSpecific(dm,DM_CLASSID,1);
4461d72bce8STim Tautges   *bs = ((DM_Moab*)dm->data)->bs;
4471d72bce8STim Tautges   PetscFunctionReturn(0);
4481d72bce8STim Tautges }
4491d72bce8STim Tautges 
4501d72bce8STim Tautges 
451a4d2169cSTim Tautges // declare for use later but before they're defined
452a4d2169cSTim Tautges PetscErrorCode DMMoab_VecUserDestroy(void *user);
453a4d2169cSTim Tautges PetscErrorCode DMMoab_VecDuplicate(Vec x,Vec *y);
454a4d2169cSTim Tautges PetscErrorCode DMMoab_CreateTagName(const moab::ParallelComm *pcomm,std::string& tag_name);
455a4d2169cSTim Tautges PetscErrorCode DMMoab_CreateVector(moab::Interface *iface,moab::ParallelComm *pcomm,moab::Tag tag,PetscInt tag_size,moab::Tag ltog_tag,moab::Range range,PetscBool serial, PetscBool destroy_tag,Vec *vec);
4561d72bce8STim Tautges 
4571d72bce8STim Tautges #undef __FUNCT__
4581d72bce8STim Tautges #define __FUNCT__ "DMMoabCreateVector"
459aa768e4cSTim Tautges /*@
460aa768e4cSTim Tautges   DMMoabCreateVector - Create a Vec from either an existing tag, or a specified tag size, and a range of entities
461aa768e4cSTim Tautges 
462aa768e4cSTim Tautges   Collective on MPI_Comm
463aa768e4cSTim Tautges 
464aa768e4cSTim Tautges   Input Parameter:
465aa768e4cSTim Tautges . dm          - The DMMoab object being set
466aa768e4cSTim Tautges . tag         - If non-zero, block size will be taken from the tag size
467aa768e4cSTim Tautges . tag_size    - If tag was zero, this parameter specifies the block size; unique tag name will be generated automatically
468aa768e4cSTim Tautges . range       - If non-empty, Vec corresponds to these entities, otherwise to the entities set on the DMMoab
469aa768e4cSTim Tautges . serial      - If true, this is a serial Vec, otherwise a parallel one
470aa768e4cSTim Tautges . destroy_tag - If true, MOAB tag is destroyed with Vec, otherwise it is left on MOAB
471aa768e4cSTim Tautges 
472aa768e4cSTim Tautges   Output Parameter:
473aa768e4cSTim Tautges . vec         - The created vector
474aa768e4cSTim Tautges 
475aa768e4cSTim Tautges   Level: beginner
476aa768e4cSTim Tautges 
477aa768e4cSTim Tautges .keywords: DMMoab, create
478aa768e4cSTim Tautges @*/
479a4d2169cSTim Tautges PetscErrorCode DMMoabCreateVector(DM dm,moab::Tag tag,PetscInt tag_size,moab::Range range,PetscBool serial, PetscBool destroy_tag,Vec *vec)
4801d72bce8STim Tautges {
4811d72bce8STim Tautges   PetscErrorCode     ierr;
482a4d2169cSTim Tautges 
4831d72bce8STim Tautges   PetscFunctionBegin;
484a4d2169cSTim Tautges 
4851d72bce8STim Tautges   DM_Moab *dmmoab = (DM_Moab*)dm->data;
486a4d2169cSTim Tautges   moab::ParallelComm *pcomm = dmmoab->pcomm;
487a4d2169cSTim Tautges   moab::Interface *mbiface = dmmoab->mbiface;
488a4d2169cSTim Tautges   moab::Tag ltog_tag = dmmoab->ltog_tag;
489a4d2169cSTim Tautges 
490a4d2169cSTim Tautges   if (!tag && !tag_size) {
491a4d2169cSTim Tautges     PetscFunctionReturn(PETSC_ERR_ARG_WRONG);
492a4d2169cSTim Tautges   }
493*7d89fc02STim Tautges   else {
494a4d2169cSTim Tautges     ierr = DMMoab_CreateVector(mbiface,pcomm,tag,tag_size,ltog_tag,range,serial,destroy_tag,vec);CHKERRQ(ierr);
495a4d2169cSTim Tautges   }
4961d72bce8STim Tautges   PetscFunctionReturn(0);
4971d72bce8STim Tautges }
4981d72bce8STim Tautges 
4991d72bce8STim Tautges 
5001d72bce8STim Tautges #undef __FUNCT__
501a4d2169cSTim Tautges #define __FUNCT__ "DMMoab_CreateVector"
502a4d2169cSTim Tautges PetscErrorCode DMMoab_CreateVector(moab::Interface *mbiface,moab::ParallelComm *pcomm,moab::Tag tag,PetscInt tag_size,moab::Tag ltog_tag,moab::Range range,PetscBool serial, PetscBool destroy_tag,Vec *vec)
503a4d2169cSTim Tautges {
504a4d2169cSTim Tautges   PetscErrorCode     ierr;
505a4d2169cSTim Tautges   moab::ErrorCode    merr;
506a4d2169cSTim Tautges 
507a4d2169cSTim Tautges   PetscFunctionBegin;
508a4d2169cSTim Tautges 
509a4d2169cSTim Tautges   if (!tag) {
510a4d2169cSTim Tautges     std::string tag_name;
511a4d2169cSTim Tautges     ierr = DMMoab_CreateTagName(pcomm,tag_name);CHKERRQ(ierr);
512a4d2169cSTim Tautges 
513a4d2169cSTim Tautges       // Create the default value for the tag (all zeros):
514a4d2169cSTim Tautges     std::vector<PetscScalar> default_value(tag_size, 0.0);
515a4d2169cSTim Tautges 
516a4d2169cSTim Tautges       // Create the tag:
517a4d2169cSTim Tautges     merr = mbiface->tag_get_handle(tag_name.c_str(),tag_size,moab::MB_TYPE_DOUBLE,tag,
518a4d2169cSTim Tautges                                    moab::MB_TAG_DENSE | moab::MB_TAG_CREAT,default_value.data());MBERRNM(merr);
519a4d2169cSTim Tautges   }
520a4d2169cSTim Tautges   else {
521a4d2169cSTim Tautges 
522a4d2169cSTim Tautges       // Make sure the tag data is of type "double":
523a4d2169cSTim Tautges     moab::DataType tag_type;
524a4d2169cSTim Tautges     merr = mbiface->tag_get_data_type(tag, tag_type);MBERRNM(merr);
525a4d2169cSTim Tautges     if(tag_type != moab::MB_TYPE_DOUBLE) SETERRQ(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Tag data type must be MB_TYPE_DOUBLE");
526a4d2169cSTim Tautges   }
527a4d2169cSTim Tautges 
528a4d2169cSTim Tautges     // Create the MOAB internal data object
529a4d2169cSTim Tautges   Vec_MOAB *vmoab;
530a4d2169cSTim Tautges   ierr = PetscMalloc(sizeof(Vec_MOAB),&vmoab);CHKERRQ(ierr);
531a4d2169cSTim Tautges   new (vmoab) Vec_MOAB();
532a4d2169cSTim Tautges   vmoab->tag = tag;
533a4d2169cSTim Tautges   vmoab->ltog_tag = ltog_tag;
534a4d2169cSTim Tautges   vmoab->mbiface = mbiface;
535a4d2169cSTim Tautges   vmoab->pcomm = pcomm;
536a4d2169cSTim Tautges   vmoab->tag_range = range;
537a4d2169cSTim Tautges   vmoab->new_tag = destroy_tag;
538a4d2169cSTim Tautges   vmoab->serial = serial;
539a4d2169cSTim Tautges   merr = mbiface->tag_get_length(tag,vmoab->tag_size);MBERR("tag_get_size", merr);
540a4d2169cSTim Tautges 
541a4d2169cSTim Tautges     // Call tag_iterate. This will cause MOAB to allocate memory for the
542a4d2169cSTim Tautges     // tag data if it hasn't already happened:
543a4d2169cSTim Tautges   int  count;
544a4d2169cSTim Tautges   void *void_ptr;
545a4d2169cSTim Tautges   merr = mbiface->tag_iterate(tag,range.begin(),range.end(),count,void_ptr);MBERRNM(merr);
546a4d2169cSTim Tautges 
547a4d2169cSTim Tautges     // Check to make sure the tag data is in a single sequence:
548a4d2169cSTim Tautges   if ((unsigned)count != range.size()) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Can only create MOAB Vector for single sequence");
549a4d2169cSTim Tautges   PetscScalar *data_ptr = (PetscScalar*)void_ptr;
550a4d2169cSTim Tautges 
551a4d2169cSTim Tautges     // Create the PETSc Vector:
552a4d2169cSTim Tautges   if(!serial) {
553a4d2169cSTim Tautges       // This is an MPI Vector:
554a4d2169cSTim Tautges     ierr = VecCreateMPIWithArray(vmoab->pcomm->comm(),vmoab->tag_size,vmoab->tag_size*range.size(),
555a4d2169cSTim Tautges                                  PETSC_DECIDE,data_ptr,vec);CHKERRXX(ierr);
556a4d2169cSTim Tautges 
557a4d2169cSTim Tautges       // Vector created, manually set local to global mapping:
558a4d2169cSTim Tautges     ISLocalToGlobalMapping ltog;
559a4d2169cSTim Tautges     PetscInt               *gindices = new PetscInt[range.size()];
560a4d2169cSTim Tautges     PetscInt               count = 0;
561a4d2169cSTim Tautges     moab::Range::iterator  iter;
562a4d2169cSTim Tautges     for(iter = range.begin(); iter != range.end(); iter++) {
563a4d2169cSTim Tautges       int dof;
564a4d2169cSTim Tautges       merr = mbiface->tag_get_data(ltog_tag,&(*iter),1,&dof);MBERRNM(merr);
565a4d2169cSTim Tautges       gindices[count] = dof;
566a4d2169cSTim Tautges       count++;
567a4d2169cSTim Tautges     }
568a4d2169cSTim Tautges 
569a4d2169cSTim Tautges     ierr = ISLocalToGlobalMappingCreate(PETSC_COMM_SELF,range.size(),gindices,
570a4d2169cSTim Tautges                                         PETSC_COPY_VALUES,&ltog);CHKERRQ(ierr);
571a4d2169cSTim Tautges     ierr = VecSetLocalToGlobalMappingBlock(*vec,ltog);CHKERRQ(ierr);
572a4d2169cSTim Tautges 
573a4d2169cSTim Tautges       // Clean up:
574a4d2169cSTim Tautges     ierr = ISLocalToGlobalMappingDestroy(&ltog);CHKERRQ(ierr);
575a4d2169cSTim Tautges     delete [] gindices;
576a4d2169cSTim Tautges   } else {
577a4d2169cSTim Tautges       // This is a serial vector:
578a4d2169cSTim Tautges     ierr = VecCreateSeqWithArray(PETSC_COMM_SELF,vmoab->tag_size,vmoab->tag_size*range.size(),data_ptr,vec);CHKERRXX(ierr);
579a4d2169cSTim Tautges   }
580a4d2169cSTim Tautges 
581a4d2169cSTim Tautges 
582a4d2169cSTim Tautges   PetscContainer moabdata;
583a4d2169cSTim Tautges   ierr = PetscContainerCreate(PETSC_COMM_SELF,&moabdata);CHKERRQ(ierr);
584a4d2169cSTim Tautges   ierr = PetscContainerSetPointer(moabdata,vmoab);CHKERRQ(ierr);
585a4d2169cSTim Tautges   ierr = PetscContainerSetUserDestroy(moabdata,DMMoab_VecUserDestroy);CHKERRQ(ierr);
586a4d2169cSTim Tautges   ierr = PetscObjectCompose((PetscObject)*vec,"MOABData",(PetscObject)moabdata);CHKERRQ(ierr);
587a4d2169cSTim Tautges   (*vec)->ops->duplicate = DMMoab_VecDuplicate;
588a4d2169cSTim Tautges 
589a4d2169cSTim Tautges   ierr = PetscContainerDestroy(&moabdata);CHKERRQ(ierr);
590a4d2169cSTim Tautges   PetscFunctionReturn(0);
591a4d2169cSTim Tautges }
592a4d2169cSTim Tautges 
593a4d2169cSTim Tautges #undef __FUNCT__
5941d72bce8STim Tautges #define __FUNCT__ "DMMoabGetVecTag"
595aa768e4cSTim Tautges /*@
596aa768e4cSTim Tautges   DMMoabGetVecTag - Get the MOAB tag associated with this Vec
597aa768e4cSTim Tautges 
598aa768e4cSTim Tautges   Collective on MPI_Comm
599aa768e4cSTim Tautges 
600aa768e4cSTim Tautges   Input Parameter:
601aa768e4cSTim Tautges . vec - Vec being queried
602aa768e4cSTim Tautges 
603aa768e4cSTim Tautges   Output Parameter:
604aa768e4cSTim Tautges . tag - Tag associated with this Vec
605aa768e4cSTim Tautges 
606aa768e4cSTim Tautges   Level: beginner
607aa768e4cSTim Tautges 
608aa768e4cSTim Tautges .keywords: DMMoab, create
609aa768e4cSTim Tautges @*/
6101d72bce8STim Tautges PetscErrorCode DMMoabGetVecTag(Vec vec,moab::Tag *tag)
6111d72bce8STim Tautges {
612a4d2169cSTim Tautges   PetscContainer  moabdata;
613a4d2169cSTim Tautges   Vec_MOAB        *vmoab;
6141d72bce8STim Tautges   PetscErrorCode  ierr;
615a4d2169cSTim Tautges 
6161d72bce8STim Tautges   PetscFunctionBegin;
617a4d2169cSTim Tautges 
618a4d2169cSTim Tautges   // Get the MOAB private data:
619a4d2169cSTim Tautges   ierr = PetscObjectQuery((PetscObject)vec,"MOABData", (PetscObject*) &moabdata);CHKERRQ(ierr);
620a4d2169cSTim Tautges   ierr = PetscContainerGetPointer(moabdata, (void**) &vmoab);CHKERRQ(ierr);
621a4d2169cSTim Tautges 
622a4d2169cSTim Tautges   *tag = vmoab->tag;
623a4d2169cSTim Tautges 
6241d72bce8STim Tautges   PetscFunctionReturn(0);
6251d72bce8STim Tautges }
6261d72bce8STim Tautges 
6271d72bce8STim Tautges 
6281d72bce8STim Tautges #undef __FUNCT__
6291d72bce8STim Tautges #define __FUNCT__ "DMMoabGetVecRange"
630aa768e4cSTim Tautges /*@
631aa768e4cSTim Tautges   DMMoabGetVecRange - Get the MOAB entities associated with this Vec
632aa768e4cSTim Tautges 
633aa768e4cSTim Tautges   Collective on MPI_Comm
634aa768e4cSTim Tautges 
635aa768e4cSTim Tautges   Input Parameter:
636aa768e4cSTim Tautges . vec   - Vec being queried
637aa768e4cSTim Tautges 
638aa768e4cSTim Tautges   Output Parameter:
639aa768e4cSTim Tautges . range - Entities associated with this Vec
640aa768e4cSTim Tautges 
641aa768e4cSTim Tautges   Level: beginner
642aa768e4cSTim Tautges 
643aa768e4cSTim Tautges .keywords: DMMoab, create
644aa768e4cSTim Tautges @*/
6451d72bce8STim Tautges PetscErrorCode DMMoabGetVecRange(Vec vec,moab::Range *range)
6461d72bce8STim Tautges {
647a4d2169cSTim Tautges   PetscContainer  moabdata;
648a4d2169cSTim Tautges   Vec_MOAB        *vmoab;
6491d72bce8STim Tautges   PetscErrorCode  ierr;
650a4d2169cSTim Tautges 
6511d72bce8STim Tautges   PetscFunctionBegin;
652a4d2169cSTim Tautges 
653a4d2169cSTim Tautges   // Get the MOAB private data:
654a4d2169cSTim Tautges   ierr = PetscObjectQuery((PetscObject)vec,"MOABData", (PetscObject*) &moabdata);CHKERRQ(ierr);
655a4d2169cSTim Tautges   ierr = PetscContainerGetPointer(moabdata, (void**) &vmoab);CHKERRQ(ierr);
656a4d2169cSTim Tautges 
657a4d2169cSTim Tautges   *range = vmoab->tag_range;
658a4d2169cSTim Tautges 
6591d72bce8STim Tautges   PetscFunctionReturn(0);
6601d72bce8STim Tautges }
6611d72bce8STim Tautges 
6621d72bce8STim Tautges 
663a4d2169cSTim Tautges #undef __FUNCT__
664a4d2169cSTim Tautges #define __FUNCT__ "DMMoab_VecDuplicate"
665a4d2169cSTim Tautges PetscErrorCode DMMoab_VecDuplicate(Vec x,Vec *y)
666a4d2169cSTim Tautges {
667a4d2169cSTim Tautges   PetscErrorCode ierr;
668a4d2169cSTim Tautges   PetscFunctionBegin;
669a4d2169cSTim Tautges   PetscValidHeaderSpecific(x,VEC_CLASSID,1);
670a4d2169cSTim Tautges   PetscValidPointer(y,2);
671a4d2169cSTim Tautges 
672a4d2169cSTim Tautges   // Get the Vec_MOAB struct for the original vector:
673a4d2169cSTim Tautges   PetscContainer  moabdata;
674a4d2169cSTim Tautges   Vec_MOAB        *vmoab;
675a4d2169cSTim Tautges   ierr = PetscObjectQuery((PetscObject)x,"MOABData", (PetscObject*) &moabdata);CHKERRQ(ierr);
676a4d2169cSTim Tautges   ierr = PetscContainerGetPointer(moabdata, (void**)&vmoab);CHKERRQ(ierr);
677a4d2169cSTim Tautges 
678*7d89fc02STim Tautges   ierr = DMMoab_CreateVector(vmoab->mbiface,vmoab->pcomm,0,vmoab->tag_size,vmoab->ltog_tag,vmoab->tag_range,vmoab->serial,PETSC_TRUE,y);CHKERRQ(ierr);
679a4d2169cSTim Tautges   PetscFunctionReturn(0);
680a4d2169cSTim Tautges }
681a4d2169cSTim Tautges 
682a4d2169cSTim Tautges 
683a4d2169cSTim Tautges #undef __FUNCT__
684a4d2169cSTim Tautges #define __FUNCT__ "DMMoab_CreateTagName"
685a4d2169cSTim Tautges /*  DMMoab_CreateTagName
686a4d2169cSTim Tautges  *
687a4d2169cSTim Tautges  *  Creates a unique tag name that will be shared across processes. If
688a4d2169cSTim Tautges  *  pcomm is NULL, then this is a serial vector. A unique tag name
689a4d2169cSTim Tautges  *  will be returned in tag_name in either case.
690a4d2169cSTim Tautges  *
691a4d2169cSTim Tautges  *  The tag names have the format _PETSC_VEC_N where N is some integer.
692a4d2169cSTim Tautges  */
693a4d2169cSTim Tautges PetscErrorCode DMMoab_CreateTagName(const moab::ParallelComm *pcomm,std::string& tag_name)
694a4d2169cSTim Tautges {
695a4d2169cSTim Tautges   moab::ErrorCode mberr;
696a4d2169cSTim Tautges   PetscErrorCode  ierr;
697a4d2169cSTim Tautges 
698a4d2169cSTim Tautges   PetscFunctionBegin;
699a4d2169cSTim Tautges   const std::string PVEC_PREFIX      = "_PETSC_VEC_";
700a4d2169cSTim Tautges   const PetscInt    PVEC_PREFIX_SIZE = PVEC_PREFIX.size();
701a4d2169cSTim Tautges 
702a4d2169cSTim Tautges   // Check to see if there are any PETSc vectors defined:
703a4d2169cSTim Tautges   const moab::Interface  *mbiface = pcomm->get_moab();
704a4d2169cSTim Tautges   std::vector<moab::Tag> tags;
705a4d2169cSTim Tautges   PetscInt               n = 0;
706a4d2169cSTim Tautges   mberr = mbiface->tag_get_tags(tags);MBERRNM(mberr);
707a4d2169cSTim Tautges   for(unsigned i = 0; i < tags.size(); i++) {
708a4d2169cSTim Tautges     std::string s;
709a4d2169cSTim Tautges     mberr = mbiface->tag_get_name(tags[i],s);MBERRNM(mberr);
710a4d2169cSTim Tautges     if(s.find(PVEC_PREFIX) != std::string::npos){
711a4d2169cSTim Tautges       // This tag represents a PETSc vector. Find the vector number:
712a4d2169cSTim Tautges       PetscInt m;
713a4d2169cSTim Tautges       std::istringstream(s.substr(PVEC_PREFIX_SIZE)) >> m;
714a4d2169cSTim Tautges       if(m >= n) n = m+1;
715a4d2169cSTim Tautges     }
716a4d2169cSTim Tautges   }
717a4d2169cSTim Tautges 
718a4d2169cSTim Tautges   // Make sure that n is consistent across all processes:
719a4d2169cSTim Tautges   PetscInt global_n;
720a4d2169cSTim Tautges   MPI_Comm comm = PETSC_COMM_SELF;
721a4d2169cSTim Tautges   if(pcomm) comm = pcomm->comm();
722a4d2169cSTim Tautges   ierr = MPI_Allreduce(&n,&global_n,1,MPI_INT,MPI_MAX,comm);CHKERRQ(ierr);
723a4d2169cSTim Tautges 
724a4d2169cSTim Tautges   // Set the answer and return:
725a4d2169cSTim Tautges   std::stringstream ss;
726a4d2169cSTim Tautges   ss << PVEC_PREFIX << global_n;
727a4d2169cSTim Tautges   tag_name = ss.str();
728a4d2169cSTim Tautges   PetscFunctionReturn(0);
729a4d2169cSTim Tautges }
730a4d2169cSTim Tautges 
731a4d2169cSTim Tautges 
732a4d2169cSTim Tautges #undef __FUNCT__
733a4d2169cSTim Tautges #define __FUNCT__ "DMMoab_VecUserDestroy"
734a4d2169cSTim Tautges PetscErrorCode DMMoab_VecUserDestroy(void *user)
735a4d2169cSTim Tautges {
736a4d2169cSTim Tautges   Vec_MOAB        *vmoab;
737a4d2169cSTim Tautges   PetscErrorCode  ierr;
738a4d2169cSTim Tautges   moab::ErrorCode merr;
739a4d2169cSTim Tautges 
740a4d2169cSTim Tautges   PetscFunctionBegin;
741a4d2169cSTim Tautges   vmoab = (Vec_MOAB*)user;
742a4d2169cSTim Tautges   if(vmoab->new_tag == PETSC_TRUE) {
743a4d2169cSTim Tautges     // Tag created via a call to VecDuplicate, delete the underlying tag in MOAB...
744a4d2169cSTim Tautges     merr = vmoab->mbiface->tag_delete(vmoab->tag);MBERRNM(merr);
745a4d2169cSTim Tautges   }
746a4d2169cSTim Tautges 
747a4d2169cSTim Tautges   ierr = PetscFree(vmoab);CHKERRQ(ierr);
748a4d2169cSTim Tautges   PetscFunctionReturn(0);
749a4d2169cSTim Tautges }
750a4d2169cSTim Tautges 
751