Actual source code: dmmbfield.cxx

      1: #include <petsc/private/dmmbimpl.h>

      3: #include <petscdmmoab.h>

      5: /*@C
      6:   DMMoabSetFieldVector - Sets the vector reference that represents the solution associated
      7:   with a particular field component.

      9:   Not Collective

     11:   Input Parameters:
     12: + dm     - the discretization manager object
     13: . ifield - the index of the field as set before via DMMoabSetFieldName.
     14: - fvec   - the Vector solution corresponding to the field (component)

     16:   Level: intermediate

     18: .seealso: `DMMoabGetFieldName()`, `DMMoabSetGlobalFieldVector()`
     19: @*/
     20: PetscErrorCode DMMoabSetFieldVector(DM dm, PetscInt ifield, Vec fvec)
     21: {
     22:   DM_Moab           *dmmoab;
     23:   moab::Tag          vtag, ntag;
     24:   const PetscScalar *varray;
     25:   PetscScalar       *farray;
     26:   moab::ErrorCode    merr;
     27:   std::string        tag_name;

     29:   PetscFunctionBegin;
     31:   dmmoab = (DM_Moab *)dm->data;

     33:   PetscCheck(!(ifield < 0) && !(ifield >= dmmoab->numFields), PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "The field %d should be positive and less than %d.", ifield, dmmoab->numFields);

     35:   /* Create a tag in MOAB mesh to index and keep track of number of PETSc vec tags */
     36:   merr = dmmoab->mbiface->tag_get_handle(dmmoab->fieldNames[ifield], 1, moab::MB_TYPE_DOUBLE, ntag, moab::MB_TAG_DENSE | moab::MB_TAG_CREAT);
     37:   MBERRNM(merr);

     39:   PetscCall(DMMoabGetVecTag(fvec, &vtag));

     41:   merr = dmmoab->mbiface->tag_get_name(vtag, tag_name);
     42:   if (!tag_name.length() && merr != moab::MB_SUCCESS) {
     43:     PetscCall(VecGetArrayRead(fvec, &varray));
     44:     /* use the entity handle and the Dof index to set the right value */
     45:     merr = dmmoab->mbiface->tag_set_data(ntag, *dmmoab->vowned, (const void *)varray);
     46:     MBERRNM(merr);
     47:     PetscCall(VecRestoreArrayRead(fvec, &varray));
     48:   } else {
     49:     PetscCall(PetscMalloc1(dmmoab->nloc, &farray));
     50:     /* we are using a MOAB Vec - directly copy the tag data to new one */
     51:     merr = dmmoab->mbiface->tag_get_data(vtag, *dmmoab->vowned, (void *)farray);
     52:     MBERRNM(merr);
     53:     merr = dmmoab->mbiface->tag_set_data(ntag, *dmmoab->vowned, (const void *)farray);
     54:     MBERRNM(merr);
     55:     /* make sure the parallel exchange for ghosts are done appropriately */
     56:     PetscCall(PetscFree(farray));
     57:   }
     58: #ifdef MOAB_HAVE_MPI
     59:   merr = dmmoab->pcomm->exchange_tags(ntag, *dmmoab->vowned);
     60:   MBERRNM(merr);
     61: #endif
     62:   PetscFunctionReturn(PETSC_SUCCESS);
     63: }

     65: /*@C
     66:   DMMoabSetGlobalFieldVector - Sets the vector reference that represents the global solution associated
     67:   with all fields (components) managed by DM.
     68:   A useful utility when updating the DM solution after a solve, to be serialized with the mesh for
     69:   checkpointing purposes.

     71:   Not Collective

     73:   Input Parameters:
     74: + dm   - the discretization manager object
     75: - fvec - the global Vector solution corresponding to all the fields managed by DM

     77:   Level: intermediate

     79: .seealso: `DMMoabGetFieldName()`, `DMMoabSetFieldVector()`
     80: @*/
     81: PetscErrorCode DMMoabSetGlobalFieldVector(DM dm, Vec fvec)
     82: {
     83:   DM_Moab              *dmmoab;
     84:   moab::Tag             vtag, ntag;
     85:   const PetscScalar    *rarray;
     86:   PetscScalar          *varray, *farray;
     87:   moab::ErrorCode       merr;
     88:   PetscInt              i, ifield;
     89:   std::string           tag_name;
     90:   moab::Range::iterator iter;

     92:   PetscFunctionBegin;
     94:   dmmoab = (DM_Moab *)dm->data;

     96:   /* get the Tag corresponding to the global vector - possible that there is no tag associated.. */
     97:   PetscCall(DMMoabGetVecTag(fvec, &vtag));
     98:   merr = dmmoab->mbiface->tag_get_name(vtag, tag_name);
     99:   PetscCall(PetscMalloc1(dmmoab->nloc, &farray));
    100:   if (!tag_name.length() && merr != moab::MB_SUCCESS) {
    101:     /* not a MOAB vector - use VecGetSubVector to get the parts as needed */
    102:     PetscCall(VecGetArrayRead(fvec, &rarray));
    103:     for (ifield = 0; ifield < dmmoab->numFields; ++ifield) {
    104:       /* Create a tag in MOAB mesh to index and keep track of number of PETSc vec tags */
    105:       merr = dmmoab->mbiface->tag_get_handle(dmmoab->fieldNames[ifield], 1, moab::MB_TYPE_DOUBLE, ntag, moab::MB_TAG_DENSE | moab::MB_TAG_CREAT);
    106:       MBERRNM(merr);

    108:       for (i = 0; i < dmmoab->nloc; i++) farray[i] = (dmmoab->bs == 1 ? rarray[ifield * dmmoab->nloc + i] : rarray[i * dmmoab->numFields + ifield]);

    110:       /* use the entity handle and the Dof index to set the right value */
    111:       merr = dmmoab->mbiface->tag_set_data(ntag, *dmmoab->vowned, (const void *)farray);
    112:       MBERRNM(merr);
    113:     }
    114:     PetscCall(VecRestoreArrayRead(fvec, &rarray));
    115:   } else {
    116:     PetscCall(PetscMalloc1(dmmoab->nloc * dmmoab->numFields, &varray));

    118:     /* we are using a MOAB Vec - directly copy the tag data to new one */
    119:     merr = dmmoab->mbiface->tag_get_data(vtag, *dmmoab->vowned, (void *)varray);
    120:     MBERRNM(merr);
    121:     for (ifield = 0; ifield < dmmoab->numFields; ++ifield) {
    122:       /* Create a tag in MOAB mesh to index and keep track of number of PETSc vec tags */
    123:       merr = dmmoab->mbiface->tag_get_handle(dmmoab->fieldNames[ifield], 1, moab::MB_TYPE_DOUBLE, ntag, moab::MB_TAG_DENSE | moab::MB_TAG_CREAT);
    124:       MBERRNM(merr);

    126:       /* we are using a MOAB Vec - directly copy the tag data to new one */
    127:       for (i = 0; i < dmmoab->nloc; i++) farray[i] = (dmmoab->bs == 1 ? varray[ifield * dmmoab->nloc + i] : varray[i * dmmoab->numFields + ifield]);

    129:       merr = dmmoab->mbiface->tag_set_data(ntag, *dmmoab->vowned, (const void *)farray);
    130:       MBERRNM(merr);

    132: #ifdef MOAB_HAVE_MPI
    133:       /* make sure the parallel exchange for ghosts are done appropriately */
    134:       merr = dmmoab->pcomm->exchange_tags(ntag, *dmmoab->vlocal);
    135:       MBERRNM(merr);
    136: #endif
    137:     }
    138:     PetscCall(PetscFree(varray));
    139:   }
    140:   PetscCall(PetscFree(farray));
    141:   PetscFunctionReturn(PETSC_SUCCESS);
    142: }

    144: /*@C
    145:   DMMoabSetFieldNames - Sets the number of fields and their names to be managed by the DM

    147:   Not Collective

    149:   Input Parameters:
    150: + dm        - the discretization manager object
    151: . numFields - the total number of fields
    152: - fields    - the array containing the names of each field (component); Can be `NULL`.

    154:   Level: intermediate

    156: .seealso: `DMMoabGetFieldName()`, `DMMoabSetFieldName()`
    157: @*/
    158: PetscErrorCode DMMoabSetFieldNames(DM dm, PetscInt numFields, const char *fields[])
    159: {
    160:   PetscInt i;
    161:   DM_Moab *dmmoab;

    163:   PetscFunctionBegin;
    165:   dmmoab = (DM_Moab *)dm->data;

    167:   /* first deallocate the existing field structure */
    168:   if (dmmoab->fieldNames) {
    169:     for (i = 0; i < dmmoab->numFields; i++) PetscCall(PetscFree(dmmoab->fieldNames[i]));
    170:     PetscCall(PetscFree(dmmoab->fieldNames));
    171:   }

    173:   /* now re-allocate and assign field names  */
    174:   dmmoab->numFields = numFields;
    175:   PetscCall(PetscMalloc1(numFields, &dmmoab->fieldNames));
    176:   if (fields) {
    177:     for (i = 0; i < dmmoab->numFields; i++) PetscCall(PetscStrallocpy(fields[i], (char **)&dmmoab->fieldNames[i]));
    178:   }
    179:   PetscCall(DMSetNumFields(dm, numFields));
    180:   PetscFunctionReturn(PETSC_SUCCESS);
    181: }

    183: /*@C
    184:   DMMoabGetFieldName - Gets the names of individual field components in multicomponent
    185:   vectors associated with a DMDA.

    187:   Not Collective

    189:   Input Parameters:
    190: + dm    - the discretization manager object
    191: - field - field number for the DMMoab (0, 1, ... dof-1), where dof indicates the
    192:         number of degrees of freedom per node within the DMMoab

    194:   Output Parameter:
    195: . fieldName - the name of the field (component)

    197:   Level: intermediate

    199: .seealso: `DMMoabSetFieldName()`, `DMMoabSetFields()`
    200: @*/
    201: PetscErrorCode DMMoabGetFieldName(DM dm, PetscInt field, const char *fieldName[])
    202: {
    203:   DM_Moab *dmmoab;

    205:   PetscFunctionBegin;
    207:   dmmoab = (DM_Moab *)dm->data;
    208:   PetscCheck(!(field < 0) && !(field >= dmmoab->numFields), PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "DM field %d should be in [%d, %d)", field, 0, dmmoab->numFields);

    210:   *fieldName = dmmoab->fieldNames[field];
    211:   PetscFunctionReturn(PETSC_SUCCESS);
    212: }

    214: /*@C
    215:   DMMoabSetFieldName - Sets the name of a field (component) managed by the DM

    217:   Not Collective

    219:   Input Parameters:
    220: + dm        - the discretization manager object
    221: . field     - the field number
    222: - fieldName - the field (component) name

    224:   Level: intermediate

    226:   Notes:
    227:   Can only be called after DMMoabSetFields supplied with correct numFields

    229: .seealso: `DMMoabGetFieldName()`, `DMMoabSetFields()`
    230: @*/
    231: PetscErrorCode DMMoabSetFieldName(DM dm, PetscInt field, const char *fieldName)
    232: {
    233:   DM_Moab *dmmoab;

    235:   PetscFunctionBegin;
    237:   PetscAssertPointer(fieldName, 3);

    239:   dmmoab = (DM_Moab *)dm->data;
    240:   PetscCheck(!(field < 0) && !(field >= dmmoab->numFields), PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "DM field %d should be in [%d, %d)", field, 0, dmmoab->numFields);

    242:   if (dmmoab->fieldNames[field]) PetscCall(PetscFree(dmmoab->fieldNames[field]));
    243:   PetscCall(PetscStrallocpy(fieldName, (char **)&dmmoab->fieldNames[field]));
    244:   PetscFunctionReturn(PETSC_SUCCESS);
    245: }

    247: /*@C
    248:   DMMoabGetFieldDof - Gets the global degree-of-freedom of a field (component) defined on a
    249:   particular MOAB EntityHandle.

    251:   Not Collective

    253:   Input Parameters:
    254: + dm    - the discretization manager object
    255: . point - the MOAB EntityHandle container which holds the field degree-of-freedom values
    256: - field - the field (component) index

    258:   Output Parameter:
    259: . dof - the global degree-of-freedom index corresponding to the field in the discrete representation (Vec, Mat)

    261:   Level: beginner

    263: .seealso: `DMMoabGetFieldDofs()`, `DMMoabGetFieldDofsLocal()`
    264: @*/
    265: PetscErrorCode DMMoabGetFieldDof(DM dm, moab::EntityHandle point, PetscInt field, PetscInt *dof)
    266: {
    267:   DM_Moab *dmmoab;

    269:   PetscFunctionBegin;
    271:   dmmoab = (DM_Moab *)dm->data;

    273:   *dof = (dmmoab->bs == 1 ? dmmoab->gidmap[dmmoab->mbiface->id_from_handle(point) - dmmoab->seqstart] + field * dmmoab->n : dmmoab->gidmap[dmmoab->mbiface->id_from_handle(point) - dmmoab->seqstart] * dmmoab->numFields + field);
    274:   PetscFunctionReturn(PETSC_SUCCESS);
    275: }

    277: /*@C
    278:   DMMoabGetFieldDofs - Gets the global degree-of-freedom of a field (component) defined on an
    279:   array of MOAB EntityHandles.

    281:   Not Collective

    283:   Input Parameters:
    284: + dm      - the discretization manager object
    285: . npoints - the total number of Entities in the points array
    286: . points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values
    287: - field   - the field (component) index

    289:   Output Parameter:
    290: . dof - the global degree-of-freedom index array corresponding to the field in the discrete representation (Vec, Mat)

    292:   Level: intermediate

    294: .seealso: `DMMoabGetFieldDof()`, `DMMoabGetFieldDofsLocal()`
    295: @*/
    296: PetscErrorCode DMMoabGetFieldDofs(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt field, PetscInt *dof)
    297: {
    298:   PetscInt i;
    299:   DM_Moab *dmmoab;

    301:   PetscFunctionBegin;
    303:   PetscAssertPointer(points, 3);
    304:   dmmoab = (DM_Moab *)dm->data;

    306:   if (!dof) PetscCall(PetscMalloc1(npoints, &dof));

    308:   /* compute the DOF based on local blocking in the fields */
    309:   /* We also assume all fields have equal distribution; i.e., all fields are either defined on vertices or elements and not on a mixture */
    310:   /* TODO: eliminate the limitation using PetscSection to manage DOFs */
    311:   for (i = 0; i < npoints; ++i)
    312:     dof[i] = (dmmoab->bs == 1 ? dmmoab->gidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] + field * dmmoab->n : dmmoab->gidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] * dmmoab->numFields + field);
    313:   PetscFunctionReturn(PETSC_SUCCESS);
    314: }

    316: /*@C
    317:   DMMoabGetFieldDofsLocal - Gets the local degrees-of-freedom of a field (component) defined on an
    318:   array of MOAB EntityHandles.

    320:   Not Collective

    322:   Input Parameters:
    323: + dm      - the discretization manager object
    324: . npoints - the total number of Entities in the points array
    325: . points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values
    326: - field   - the field (component) index

    328:   Output Parameter:
    329: . dof - the local degree-of-freedom index array corresponding to the field in the discrete representation (Vec, Mat)

    331:   Level: intermediate

    333: .seealso: `DMMoabGetFieldDof()`, `DMMoabGetFieldDofs()`
    334: @*/
    335: PetscErrorCode DMMoabGetFieldDofsLocal(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt field, PetscInt *dof)
    336: {
    337:   PetscInt i;
    338:   DM_Moab *dmmoab;

    340:   PetscFunctionBegin;
    342:   PetscAssertPointer(points, 3);
    343:   dmmoab = (DM_Moab *)dm->data;

    345:   if (!dof) PetscCall(PetscMalloc1(npoints, &dof));

    347:   /* compute the DOF based on local blocking in the fields */
    348:   /* assume all fields have equal distribution; i.e., all fields are either defined on vertices or elements and not on a mixture */
    349:   /* TODO: eliminate the limitation using PetscSection to manage DOFs */
    350:   for (i = 0; i < npoints; ++i) {
    351:     dof[i] = (dmmoab->bs > 1 ? dmmoab->lidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] * dmmoab->numFields + field : dmmoab->lidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] + field * dmmoab->n);
    352:   }
    353:   PetscFunctionReturn(PETSC_SUCCESS);
    354: }

    356: /*@C
    357:   DMMoabGetDofs - Gets the global degree-of-freedom for all fields (components) defined on an
    358:   array of MOAB EntityHandles.

    360:   Not Collective

    362:   Input Parameters:
    363: + dm      - the discretization manager object
    364: . npoints - the total number of Entities in the points array
    365: - points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values

    367:   Output Parameter:
    368: . dof - the global degree-of-freedom index array corresponding to the field in the discrete representation (Vec, Mat)

    370:   Level: intermediate

    372: .seealso: `DMMoabGetFieldDofs()`, `DMMoabGetDofsLocal()`, `DMMoabGetDofsBlocked()`
    373: @*/
    374: PetscErrorCode DMMoabGetDofs(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt *dof)
    375: {
    376:   PetscInt i, field, offset;
    377:   DM_Moab *dmmoab;

    379:   PetscFunctionBegin;
    381:   PetscAssertPointer(points, 3);
    382:   dmmoab = (DM_Moab *)dm->data;

    384:   if (!dof) PetscCall(PetscMalloc1(dmmoab->numFields * npoints, &dof));

    386:   /* compute the DOF based on local blocking in the fields */
    387:   /* assume all fields have equal distribution; i.e., all fields are either defined on vertices or elements and not on a mixture */
    388:   /* TODO: eliminate the limitation using PetscSection to manage DOFs */
    389:   for (field = 0; field < dmmoab->numFields; ++field) {
    390:     offset = field * dmmoab->n;
    391:     for (i = 0; i < npoints; ++i)
    392:       dof[i * dmmoab->numFields + field] = (dmmoab->bs > 1 ? dmmoab->gidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] * dmmoab->numFields + field : dmmoab->gidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] + offset);
    393:   }
    394:   PetscFunctionReturn(PETSC_SUCCESS);
    395: }

    397: /*@C
    398:   DMMoabGetDofsLocal - Gets the local degree-of-freedom for all fields (components) defined on an
    399:   array of MOAB EntityHandles.

    401:   Not Collective

    403:   Input Parameters:
    404: + dm      - the discretization manager object
    405: . npoints - the total number of Entities in the points array
    406: - points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values

    408:   Output Parameter:
    409: . dof - the local degree-of-freedom index array corresponding to the field in the discrete representation (Vec, Mat)

    411:   Level: intermediate

    413: .seealso: `DMMoabGetFieldDofs()`, `DMMoabGetDofs()`, `DMMoabGetDofsBlocked()`
    414: @*/
    415: PetscErrorCode DMMoabGetDofsLocal(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt *dof)
    416: {
    417:   PetscInt i, field, offset;
    418:   DM_Moab *dmmoab;

    420:   PetscFunctionBegin;
    422:   PetscAssertPointer(points, 3);
    423:   dmmoab = (DM_Moab *)dm->data;

    425:   if (!dof) PetscCall(PetscMalloc1(dmmoab->numFields * npoints, &dof));

    427:   /* compute the DOF based on local blocking in the fields */
    428:   /* assume all fields have equal distribution; i.e., all fields are either defined on vertices or elements and not on a mixture */
    429:   /* TODO: eliminate the limitation using PetscSection to manage DOFs */
    430:   for (field = 0; field < dmmoab->numFields; ++field) {
    431:     offset = field * dmmoab->n;
    432:     for (i = 0; i < npoints; ++i)
    433:       dof[i * dmmoab->numFields + field] = (dmmoab->bs > 1 ? dmmoab->lidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] * dmmoab->numFields + field : dmmoab->lidmap[dmmoab->mbiface->id_from_handle(points[i]) - dmmoab->seqstart] + offset);
    434:   }
    435:   PetscFunctionReturn(PETSC_SUCCESS);
    436: }

    438: /*@C
    439:   DMMoabGetDofsBlocked - Gets the global degree-of-freedom for the first field (component) defined on an
    440:   array of MOAB EntityHandles. It is useful when performing Blocked(Get/Set) methods in computation
    441:   of element residuals and assembly of the discrete systems when all fields are co-located.

    443:   Not Collective

    445:   Input Parameters:
    446: + dm      - the discretization manager object
    447: . npoints - the total number of Entities in the points array
    448: - points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values

    450:   Output Parameter:
    451: . dof - the blocked global degree-of-freedom index array in the discrete representation (Vec, Mat)

    453:   Level: intermediate

    455: .seealso: `DMMoabGetDofsLocal()`, `DMMoabGetDofs()`, `DMMoabGetDofsBlockedLocal()`
    456: @*/
    457: PetscErrorCode DMMoabGetDofsBlocked(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt *dof)
    458: {
    459:   PetscInt i;
    460:   DM_Moab *dmmoab;

    462:   PetscFunctionBegin;
    464:   PetscAssertPointer(points, 3);
    465:   dmmoab = (DM_Moab *)dm->data;

    467:   if (!dof) PetscCall(PetscMalloc1(npoints, &dof));

    469:   for (i = 0; i < npoints; ++i) dof[i] = dmmoab->gidmap[(PetscInt)points[i] - dmmoab->seqstart];
    470:   PetscFunctionReturn(PETSC_SUCCESS);
    471: }

    473: /*@C
    474:   DMMoabGetDofsBlockedLocal - Gets the local degree-of-freedom for the first field (component) defined on an
    475:   array of MOAB EntityHandles. It is useful when performing local Blocked(Get/Set) methods in computation
    476:   of element residuals and assembly of the discrete systems when all fields are co-located.

    478:   Not Collective

    480:   Input Parameters:
    481: + dm      - the discretization manager object
    482: . npoints - the total number of Entities in the points array
    483: - points  - the MOAB EntityHandle container array which holds the field degree-of-freedom values

    485:   Output Parameter:
    486: . dof - the blocked local degree-of-freedom index array in the discrete representation (Vec, Mat)

    488:   Level: intermediate

    490: .seealso: `DMMoabGetDofsLocal()`, `DMMoabGetDofs()`
    491: @*/
    492: PetscErrorCode DMMoabGetDofsBlockedLocal(DM dm, PetscInt npoints, const moab::EntityHandle *points, PetscInt *dof)
    493: {
    494:   PetscInt i;
    495:   DM_Moab *dmmoab;

    497:   PetscFunctionBegin;
    499:   PetscAssertPointer(points, 3);
    500:   dmmoab = (DM_Moab *)dm->data;

    502:   if (!dof) PetscCall(PetscMalloc1(npoints, &dof));

    504:   for (i = 0; i < npoints; ++i) dof[i] = dmmoab->lidmap[(PetscInt)points[i] - dmmoab->seqstart];
    505:   PetscFunctionReturn(PETSC_SUCCESS);
    506: }

    508: /*@C
    509:   DMMoabGetVertexDofsBlocked - Gets the global degree-of-freedom for the first field (component) defined on an
    510:   array of locally owned MOAB mesh vertices.

    512:   Not Collective

    514:   Input Parameters:
    515: . dm - the discretization manager object

    517:   Output Parameter:
    518: . dof - the blocked global degree-of-freedom index array in the discrete representation (Vec, Mat) that is vertex-based based on local numbering

    520:   Level: intermediate

    522:   Note:
    523:   It's utility is when performing Finite-Difference type calculations where vertex traversal is
    524:   faster than element-wise assembly that is typically done in FEM calculations.

    526: .seealso: `DMMoabGetVertexDofsBlockedLocal()`, `DMMoabGetDofsBlocked()`, `DMMoabGetDofsBlockedLocal()`
    527: @*/
    528: PetscErrorCode DMMoabGetVertexDofsBlocked(DM dm, PetscInt **dof)
    529: {
    530:   DM_Moab *dmmoab;

    532:   PetscFunctionBegin;
    534:   dmmoab = (DM_Moab *)dm->data;

    536:   *dof = dmmoab->gidmap;
    537:   PetscFunctionReturn(PETSC_SUCCESS);
    538: }

    540: /*@C
    541:   DMMoabGetVertexDofsBlockedLocal - Gets the local degree-of-freedom for the first field (component) defined on an
    542:   array of locally owned MOAB mesh vertices.

    544:   Not Collective

    546:   Input Parameters:
    547: . dm - the discretization manager object

    549:   Output Parameter:
    550: . dof - the blocked local degree-of-freedom index array in the discrete representation (Vec, Mat) that is vertex-based based on local numbering

    552:   Level: intermediate

    554:   Note:
    555:   It's utility is when performing Finite-Difference type calculations where vertex traversal is
    556:   faster than element-wise assembly that is typically done in FEM calculations.

    558: .seealso: `DMMoabGetVertexDofsBlocked()`, `DMMoabGetDofsBlocked()`, `DMMoabGetDofsBlockedLocal()`
    559: @*/
    560: PetscErrorCode DMMoabGetVertexDofsBlockedLocal(DM dm, PetscInt **dof)
    561: {
    562:   DM_Moab *dmmoab;

    564:   PetscFunctionBegin;
    566:   PetscAssertPointer(dof, 2);
    567:   dmmoab = (DM_Moab *)dm->data;

    569:   *dof = dmmoab->lidmap;
    570:   PetscFunctionReturn(PETSC_SUCCESS);
    571: }