1 #include <petsc/private/dmmbimpl.h> /*I "petscdmmoab.h" I*/ 2 3 #include <petscdmmoab.h> 4 #include <MBTagConventions.hpp> 5 #include <moab/NestedRefine.hpp> 6 #include <moab/Skinner.hpp> 7 8 /*MC 9 DMMOAB = "moab" - A DM object that encapsulates an unstructured mesh described by the MOAB mesh database. 10 Direct access to the MOAB Interface and other mesh manipulation related objects are available 11 through public API. Ability to create global and local representation of Vecs containing all 12 unknowns in the interior and shared boundary via a transparent tag-data wrapper is provided 13 along with utility functions to traverse the mesh and assemble a discrete system via 14 field-based/blocked Vec(Get/Set) methods. Input from and output to different formats are 15 available. 16 17 Reference: http://www.mcs.anl.gov/~fathom/moab-docs/html/contents.html 18 19 Level: intermediate 20 21 .seealso: DMType, DMMoabCreate(), DMCreate(), DMSetType(), DMMoabCreateMoab() 22 M*/ 23 24 /* External function declarations here */ 25 PETSC_EXTERN PetscErrorCode DMCreateInterpolation_Moab(DM dmCoarse, DM dmFine, Mat *interpolation, Vec *scaling); 26 PETSC_EXTERN PetscErrorCode DMCreateDefaultConstraints_Moab(DM dm); 27 PETSC_EXTERN PetscErrorCode DMCreateMatrix_Moab(DM dm, Mat *J); 28 PETSC_EXTERN PetscErrorCode DMCreateCoordinateDM_Moab(DM dm, DM *cdm); 29 PETSC_EXTERN PetscErrorCode DMRefine_Moab(DM dm, MPI_Comm comm, DM *dmRefined); 30 PETSC_EXTERN PetscErrorCode DMCoarsen_Moab(DM dm, MPI_Comm comm, DM *dmCoarsened); 31 PETSC_EXTERN PetscErrorCode DMRefineHierarchy_Moab(DM dm, PetscInt nlevels, DM dmRefined[]); 32 PETSC_EXTERN PetscErrorCode DMCoarsenHierarchy_Moab(DM dm, PetscInt nlevels, DM dmCoarsened[]); 33 PETSC_EXTERN PetscErrorCode DMClone_Moab(DM dm, DM *newdm); 34 PETSC_EXTERN PetscErrorCode DMCreateGlobalVector_Moab(DM, Vec *); 35 PETSC_EXTERN PetscErrorCode DMCreateLocalVector_Moab(DM, Vec *); 36 PETSC_EXTERN PetscErrorCode DMCreateMatrix_Moab(DM dm, Mat *J); 37 PETSC_EXTERN PetscErrorCode DMGlobalToLocalBegin_Moab(DM, Vec, InsertMode, Vec); 38 PETSC_EXTERN PetscErrorCode DMGlobalToLocalEnd_Moab(DM, Vec, InsertMode, Vec); 39 PETSC_EXTERN PetscErrorCode DMLocalToGlobalBegin_Moab(DM, Vec, InsertMode, Vec); 40 PETSC_EXTERN PetscErrorCode DMLocalToGlobalEnd_Moab(DM, Vec, InsertMode, Vec); 41 42 43 /* Un-implemented routines */ 44 /* 45 PETSC_EXTERN PetscErrorCode DMCreateDefaultSection_Moab(DM dm); 46 PETSC_EXTERN PetscErrorCode DMCreateInjection_Moab(DM dmCoarse, DM dmFine, Mat *mat); 47 PETSC_EXTERN PetscErrorCode DMLoad_Moab(DM dm, PetscViewer viewer); 48 PETSC_EXTERN PetscErrorCode DMGetDimPoints_Moab(DM dm, PetscInt dim, PetscInt *pStart, PetscInt *pEnd); 49 PETSC_EXTERN PetscErrorCode DMCreateSubDM_Moab(DM dm, PetscInt numFields, PetscInt fields[], IS *is, DM *subdm); 50 PETSC_EXTERN PetscErrorCode DMLocatePoints_Moab(DM dm, Vec v, IS *cellIS); 51 */ 52 53 /*@ 54 DMMoabCreate - Creates a DMMoab object, which encapsulates a moab instance 55 56 Collective on MPI_Comm 57 58 Input Parameter: 59 . comm - The communicator for the DMMoab object 60 61 Output Parameter: 62 . dmb - The DMMoab object 63 64 Level: beginner 65 66 .keywords: DMMoab, create 67 @*/ 68 PetscErrorCode DMMoabCreate(MPI_Comm comm, DM *dmb) 69 { 70 PetscErrorCode ierr; 71 72 PetscFunctionBegin; 73 PetscValidPointer(dmb, 2); 74 ierr = DMCreate(comm, dmb);CHKERRQ(ierr); 75 ierr = DMSetType(*dmb, DMMOAB);CHKERRQ(ierr); 76 PetscFunctionReturn(0); 77 } 78 79 /*@ 80 DMMoabCreateMoab - Creates a DMMoab object, optionally from an instance and other data 81 82 Collective on MPI_Comm 83 84 Input Parameter: 85 . comm - The communicator for the DMMoab object 86 . mbiface - (ptr to) the MOAB Instance; if passed in NULL, MOAB instance is created inside PETSc, and destroyed 87 along with the DMMoab 88 . pcomm - (ptr to) a ParallelComm; if NULL, creates one internally for the whole communicator 89 . ltog_tag - A tag to use to retrieve global id for an entity; if 0, will use GLOBAL_ID_TAG_NAME/tag 90 . range - If non-NULL, contains range of entities to which DOFs will be assigned 91 92 Output Parameter: 93 . dmb - The DMMoab object 94 95 Level: intermediate 96 97 .keywords: DMMoab, create 98 @*/ 99 PetscErrorCode DMMoabCreateMoab(MPI_Comm comm, moab::Interface *mbiface, moab::Tag *ltog_tag, moab::Range *range, DM *dmb) 100 { 101 PetscErrorCode ierr; 102 moab::ErrorCode merr; 103 DM dmmb; 104 DM_Moab *dmmoab; 105 106 PetscFunctionBegin; 107 PetscValidPointer(dmb, 6); 108 109 ierr = DMMoabCreate(comm, &dmmb);CHKERRQ(ierr); 110 dmmoab = (DM_Moab*)(dmmb)->data; 111 112 if (!mbiface) { 113 dmmoab->mbiface = new moab::Core(); 114 dmmoab->icreatedinstance = PETSC_TRUE; 115 } 116 else { 117 dmmoab->mbiface = mbiface; 118 dmmoab->icreatedinstance = PETSC_FALSE; 119 } 120 121 /* by default the fileset = root set. This set stores the hierarchy of entities belonging to current DM */ 122 dmmoab->fileset = 0; 123 dmmoab->hlevel = 0; 124 dmmoab->nghostrings = 0; 125 126 #ifdef MOAB_HAVE_MPI 127 moab::EntityHandle partnset; 128 129 /* Create root sets for each mesh. Then pass these 130 to the load_file functions to be populated. */ 131 merr = dmmoab->mbiface->create_meshset(moab::MESHSET_SET, partnset); MBERR("Creating partition set failed", merr); 132 133 /* Create the parallel communicator object with the partition handle associated with MOAB */ 134 dmmoab->pcomm = moab::ParallelComm::get_pcomm(dmmoab->mbiface, partnset, &comm); 135 #endif 136 137 /* do the remaining initializations for DMMoab */ 138 dmmoab->bs = 1; 139 dmmoab->numFields = 1; 140 ierr = PetscMalloc(dmmoab->numFields * sizeof(char*), &dmmoab->fieldNames);CHKERRQ(ierr); 141 ierr = PetscStrallocpy("DEFAULT", (char**) &dmmoab->fieldNames[0]);CHKERRQ(ierr); 142 dmmoab->rw_dbglevel = 0; 143 dmmoab->partition_by_rank = PETSC_FALSE; 144 dmmoab->extra_read_options[0] = '\0'; 145 dmmoab->extra_write_options[0] = '\0'; 146 dmmoab->read_mode = READ_PART; 147 dmmoab->write_mode = WRITE_PART; 148 149 /* set global ID tag handle */ 150 if (ltog_tag && *ltog_tag) { 151 ierr = DMMoabSetLocalToGlobalTag(dmmb, *ltog_tag);CHKERRQ(ierr); 152 } 153 else { 154 merr = dmmoab->mbiface->tag_get_handle(GLOBAL_ID_TAG_NAME, dmmoab->ltog_tag); MBERRNM(merr); 155 if (ltog_tag) *ltog_tag = dmmoab->ltog_tag; 156 } 157 158 merr = dmmoab->mbiface->tag_get_handle(MATERIAL_SET_TAG_NAME, dmmoab->material_tag); MBERRNM(merr); 159 160 /* set the local range of entities (vertices) of interest */ 161 if (range) { 162 ierr = DMMoabSetLocalVertices(dmmb, range);CHKERRQ(ierr); 163 } 164 *dmb = dmmb; 165 PetscFunctionReturn(0); 166 } 167 168 169 #ifdef MOAB_HAVE_MPI 170 171 /*@ 172 DMMoabGetParallelComm - Get the ParallelComm used with this DMMoab 173 174 Collective on MPI_Comm 175 176 Input Parameter: 177 . dm - The DMMoab object being set 178 179 Output Parameter: 180 . pcomm - The ParallelComm for the DMMoab 181 182 Level: beginner 183 184 .keywords: DMMoab, create 185 @*/ 186 PetscErrorCode DMMoabGetParallelComm(DM dm, moab::ParallelComm **pcomm) 187 { 188 PetscFunctionBegin; 189 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 190 *pcomm = ((DM_Moab*)(dm)->data)->pcomm; 191 PetscFunctionReturn(0); 192 } 193 194 #endif /* MOAB_HAVE_MPI */ 195 196 197 /*@ 198 DMMoabSetInterface - Set the MOAB instance used with this DMMoab 199 200 Collective on MPI_Comm 201 202 Input Parameter: 203 . dm - The DMMoab object being set 204 . mbiface - The MOAB instance being set on this DMMoab 205 206 Level: beginner 207 208 .keywords: DMMoab, create 209 @*/ 210 PetscErrorCode DMMoabSetInterface(DM dm, moab::Interface *mbiface) 211 { 212 DM_Moab *dmmoab = (DM_Moab*)(dm)->data; 213 214 PetscFunctionBegin; 215 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 216 PetscValidPointer(mbiface, 2); 217 #ifdef MOAB_HAVE_MPI 218 dmmoab->pcomm = NULL; 219 #endif 220 dmmoab->mbiface = mbiface; 221 dmmoab->icreatedinstance = PETSC_FALSE; 222 PetscFunctionReturn(0); 223 } 224 225 226 /*@ 227 DMMoabGetInterface - Get the MOAB instance used with this DMMoab 228 229 Collective on MPI_Comm 230 231 Input Parameter: 232 . dm - The DMMoab object being set 233 234 Output Parameter: 235 . mbiface - The MOAB instance set on this DMMoab 236 237 Level: beginner 238 239 .keywords: DMMoab, create 240 @*/ 241 PetscErrorCode DMMoabGetInterface(DM dm, moab::Interface **mbiface) 242 { 243 PetscErrorCode ierr; 244 static PetscBool cite = PETSC_FALSE; 245 246 PetscFunctionBegin; 247 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 248 ierr = PetscCitationsRegister("@techreport{tautges_moab:_2004,\n type = {{SAND2004-1592}},\n title = {{MOAB:} A Mesh-Oriented Database}, institution = {Sandia National Laboratories},\n author = {Tautges, T. J. and Meyers, R. and Merkley, K. and Stimpson, C. and Ernst, C.},\n year = {2004}, note = {Report}\n}\n", &cite);CHKERRQ(ierr); 249 *mbiface = ((DM_Moab*)dm->data)->mbiface; 250 PetscFunctionReturn(0); 251 } 252 253 254 /*@ 255 DMMoabSetLocalVertices - Set the entities having DOFs on this DMMoab 256 257 Collective on MPI_Comm 258 259 Input Parameter: 260 . dm - The DMMoab object being set 261 . range - The entities treated by this DMMoab 262 263 Level: beginner 264 265 .keywords: DMMoab, create 266 @*/ 267 PetscErrorCode DMMoabSetLocalVertices(DM dm, moab::Range *range) 268 { 269 moab::Range tmpvtxs; 270 DM_Moab *dmmoab = (DM_Moab*)(dm)->data; 271 272 PetscFunctionBegin; 273 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 274 dmmoab->vlocal->clear(); 275 dmmoab->vowned->clear(); 276 277 dmmoab->vlocal->insert(range->begin(), range->end()); 278 279 #ifdef MOAB_HAVE_MPI 280 moab::ErrorCode merr; 281 /* filter based on parallel status */ 282 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->vlocal, PSTATUS_NOT_OWNED, PSTATUS_NOT, -1, dmmoab->vowned); MBERRNM(merr); 283 284 /* filter all the non-owned and shared entities out of the list */ 285 tmpvtxs = moab::subtract(*dmmoab->vlocal, *dmmoab->vowned); 286 merr = dmmoab->pcomm->filter_pstatus(tmpvtxs, PSTATUS_INTERFACE, PSTATUS_OR, -1, dmmoab->vghost); MBERRNM(merr); 287 tmpvtxs = moab::subtract(tmpvtxs, *dmmoab->vghost); 288 *dmmoab->vlocal = moab::subtract(*dmmoab->vlocal, tmpvtxs); 289 #else 290 *dmmoab->vowned = *dmmoab->vlocal; 291 #endif 292 293 /* compute and cache the sizes of local and ghosted entities */ 294 dmmoab->nloc = dmmoab->vowned->size(); 295 dmmoab->nghost = dmmoab->vghost->size(); 296 #ifdef MOAB_HAVE_MPI 297 PetscErrorCode ierr; 298 ierr = MPIU_Allreduce(&dmmoab->nloc, &dmmoab->n, 1, MPI_INTEGER, MPI_SUM, ((PetscObject)dm)->comm);CHKERRQ(ierr); 299 #else 300 dmmoab->n = dmmoab->nloc; 301 #endif 302 PetscFunctionReturn(0); 303 } 304 305 306 /*@ 307 DMMoabGetAllVertices - Get the entities having DOFs on this DMMoab 308 309 Collective on MPI_Comm 310 311 Input Parameter: 312 . dm - The DMMoab object being set 313 314 Output Parameter: 315 . owned - The local vertex entities in this DMMoab = (owned+ghosted) 316 317 Level: beginner 318 319 .keywords: DMMoab, create 320 @*/ 321 PetscErrorCode DMMoabGetAllVertices(DM dm, moab::Range *local) 322 { 323 PetscFunctionBegin; 324 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 325 if (local) *local = *((DM_Moab*)dm->data)->vlocal; 326 PetscFunctionReturn(0); 327 } 328 329 330 331 /*@ 332 DMMoabGetLocalVertices - Get the entities having DOFs on this DMMoab 333 334 Collective on MPI_Comm 335 336 Input Parameter: 337 . dm - The DMMoab object being set 338 339 Output Parameter: 340 . owned - The owned vertex entities in this DMMoab 341 . ghost - The ghosted entities (non-owned) stored locally in this partition 342 343 Level: beginner 344 345 .keywords: DMMoab, create 346 @*/ 347 PetscErrorCode DMMoabGetLocalVertices(DM dm, const moab::Range **owned, const moab::Range **ghost) 348 { 349 PetscFunctionBegin; 350 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 351 if (owned) *owned = ((DM_Moab*)dm->data)->vowned; 352 if (ghost) *ghost = ((DM_Moab*)dm->data)->vghost; 353 PetscFunctionReturn(0); 354 } 355 356 /*@ 357 DMMoabGetLocalElements - Get the higher-dimensional entities that are locally owned 358 359 Collective on MPI_Comm 360 361 Input Parameter: 362 . dm - The DMMoab object being set 363 364 Output Parameter: 365 . range - The entities owned locally 366 367 Level: beginner 368 369 .keywords: DMMoab, create 370 @*/ 371 PetscErrorCode DMMoabGetLocalElements(DM dm, const moab::Range **range) 372 { 373 PetscFunctionBegin; 374 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 375 if (range) *range = ((DM_Moab*)dm->data)->elocal; 376 PetscFunctionReturn(0); 377 } 378 379 380 /*@ 381 DMMoabSetLocalElements - Set the entities having DOFs on this DMMoab 382 383 Collective on MPI_Comm 384 385 Input Parameter: 386 . dm - The DMMoab object being set 387 . range - The entities treated by this DMMoab 388 389 Level: beginner 390 391 .keywords: DMMoab, create 392 @*/ 393 PetscErrorCode DMMoabSetLocalElements(DM dm, moab::Range *range) 394 { 395 DM_Moab *dmmoab = (DM_Moab*)(dm)->data; 396 397 PetscFunctionBegin; 398 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 399 dmmoab->elocal->clear(); 400 dmmoab->eghost->clear(); 401 dmmoab->elocal->insert(range->begin(), range->end()); 402 #ifdef MOAB_HAVE_MPI 403 moab::ErrorCode merr; 404 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->elocal, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 405 *dmmoab->eghost = moab::subtract(*range, *dmmoab->elocal); 406 #endif 407 dmmoab->neleloc = dmmoab->elocal->size(); 408 dmmoab->neleghost = dmmoab->eghost->size(); 409 #ifdef MOAB_HAVE_MPI 410 PetscErrorCode ierr; 411 ierr = MPIU_Allreduce(&dmmoab->neleloc, &dmmoab->nele, 1, MPI_INTEGER, MPI_SUM, ((PetscObject)dm)->comm);CHKERRQ(ierr); 412 PetscInfo2(dm, "Created %D local and %D global elements.\n", dmmoab->neleloc, dmmoab->nele); 413 #else 414 dmmoab->nele = dmmoab->neleloc; 415 #endif 416 PetscFunctionReturn(0); 417 } 418 419 420 /*@ 421 DMMoabSetLocalToGlobalTag - Set the tag used for local to global numbering 422 423 Collective on MPI_Comm 424 425 Input Parameter: 426 . dm - The DMMoab object being set 427 . ltogtag - The MOAB tag used for local to global ids 428 429 Level: beginner 430 431 .keywords: DMMoab, create 432 @*/ 433 PetscErrorCode DMMoabSetLocalToGlobalTag(DM dm, moab::Tag ltogtag) 434 { 435 PetscFunctionBegin; 436 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 437 ((DM_Moab*)dm->data)->ltog_tag = ltogtag; 438 PetscFunctionReturn(0); 439 } 440 441 442 /*@ 443 DMMoabGetLocalToGlobalTag - Get the tag used for local to global numbering 444 445 Collective on MPI_Comm 446 447 Input Parameter: 448 . dm - The DMMoab object being set 449 450 Output Parameter: 451 . ltogtag - The MOAB tag used for local to global ids 452 453 Level: beginner 454 455 .keywords: DMMoab, create 456 @*/ 457 PetscErrorCode DMMoabGetLocalToGlobalTag(DM dm, moab::Tag *ltog_tag) 458 { 459 PetscFunctionBegin; 460 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 461 *ltog_tag = ((DM_Moab*)dm->data)->ltog_tag; 462 PetscFunctionReturn(0); 463 } 464 465 466 /*@ 467 DMMoabSetBlockSize - Set the block size used with this DMMoab 468 469 Collective on MPI_Comm 470 471 Input Parameter: 472 . dm - The DMMoab object being set 473 . bs - The block size used with this DMMoab 474 475 Level: beginner 476 477 .keywords: DMMoab, create 478 @*/ 479 PetscErrorCode DMMoabSetBlockSize(DM dm, PetscInt bs) 480 { 481 PetscFunctionBegin; 482 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 483 ((DM_Moab*)dm->data)->bs = bs; 484 PetscFunctionReturn(0); 485 } 486 487 488 /*@ 489 DMMoabGetBlockSize - Get the block size used with this DMMoab 490 491 Collective on MPI_Comm 492 493 Input Parameter: 494 . dm - The DMMoab object being set 495 496 Output Parameter: 497 . bs - The block size used with this DMMoab 498 499 Level: beginner 500 501 .keywords: DMMoab, create 502 @*/ 503 PetscErrorCode DMMoabGetBlockSize(DM dm, PetscInt *bs) 504 { 505 PetscFunctionBegin; 506 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 507 *bs = ((DM_Moab*)dm->data)->bs; 508 PetscFunctionReturn(0); 509 } 510 511 512 /*@ 513 DMMoabGetSize - Get the global vertex size used with this DMMoab 514 515 Collective on DM 516 517 Input Parameter: 518 . dm - The DMMoab object being set 519 520 Output Parameter: 521 . neg - The number of global elements in the DMMoab instance 522 . nvg - The number of global vertices in the DMMoab instance 523 524 Level: beginner 525 526 .keywords: DMMoab, create 527 @*/ 528 PetscErrorCode DMMoabGetSize(DM dm, PetscInt *neg, PetscInt *nvg) 529 { 530 PetscFunctionBegin; 531 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 532 if (neg) *neg = ((DM_Moab*)dm->data)->nele; 533 if (nvg) *nvg = ((DM_Moab*)dm->data)->n; 534 PetscFunctionReturn(0); 535 } 536 537 538 /*@ 539 DMMoabGetLocalSize - Get the local and ghosted vertex size used with this DMMoab 540 541 Collective on DM 542 543 Input Parameter: 544 . dm - The DMMoab object being set 545 546 Output Parameter: 547 + nel - The number of owned elements in this processor 548 . neg - The number of ghosted elements in this processor 549 . nvl - The number of owned vertices in this processor 550 . nvg - The number of ghosted vertices in this processor 551 552 Level: beginner 553 554 .keywords: DMMoab, create 555 @*/ 556 PetscErrorCode DMMoabGetLocalSize(DM dm, PetscInt *nel, PetscInt *neg, PetscInt *nvl, PetscInt *nvg) 557 { 558 PetscFunctionBegin; 559 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 560 if (nel) *nel = ((DM_Moab*)dm->data)->neleloc; 561 if (neg) *neg = ((DM_Moab*)dm->data)->neleghost; 562 if (nvl) *nvl = ((DM_Moab*)dm->data)->nloc; 563 if (nvg) *nvg = ((DM_Moab*)dm->data)->nghost; 564 PetscFunctionReturn(0); 565 } 566 567 568 /*@ 569 DMMoabGetOffset - Get the local offset for the global vector 570 571 Collective on MPI_Comm 572 573 Input Parameter: 574 . dm - The DMMoab object being set 575 576 Output Parameter: 577 . offset - The local offset for the global vector 578 579 Level: beginner 580 581 .keywords: DMMoab, create 582 @*/ 583 PetscErrorCode DMMoabGetOffset(DM dm, PetscInt *offset) 584 { 585 PetscFunctionBegin; 586 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 587 *offset = ((DM_Moab*)dm->data)->vstart; 588 PetscFunctionReturn(0); 589 } 590 591 592 /*@ 593 DMMoabGetDimension - Get the dimension of the DM Mesh 594 595 Collective on MPI_Comm 596 597 Input Parameter: 598 . dm - The DMMoab object 599 600 Output Parameter: 601 . dim - The dimension of DM 602 603 Level: beginner 604 605 .keywords: DMMoab, create 606 @*/ 607 PetscErrorCode DMMoabGetDimension(DM dm, PetscInt *dim) 608 { 609 PetscFunctionBegin; 610 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 611 *dim = ((DM_Moab*)dm->data)->dim; 612 PetscFunctionReturn(0); 613 } 614 615 616 #undef __FUNCT__ 617 #define __FUNCT__ "DMMoabGetHierarchyLevel" 618 /*@ 619 DMMoabGetHierarchyLevel - Get the current level of the mesh hierarchy 620 generated through uniform refinement. 621 622 Collective on DM 623 624 Input Parameter: 625 . dm - The DMMoab object being set 626 627 Output Parameter: 628 . nvg - The current mesh hierarchy level 629 630 Level: beginner 631 632 .keywords: DMMoab, multigrid 633 @*/ 634 PetscErrorCode DMMoabGetHierarchyLevel(DM dm, PetscInt *nlevel) 635 { 636 PetscFunctionBegin; 637 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 638 if (nlevel) *nlevel = ((DM_Moab*)dm->data)->hlevel; 639 PetscFunctionReturn(0); 640 } 641 642 643 #undef __FUNCT__ 644 #define __FUNCT__ "DMMoabGetMaterialBlock" 645 /*@ 646 DMMoabGetMaterialBlock - Get the material ID corresponding to the current entity of the DM Mesh 647 648 Collective on MPI_Comm 649 650 Input Parameter: 651 . dm - The DMMoab object 652 . ehandle - The element entity handle 653 654 Output Parameter: 655 . mat - The material ID for the current entity 656 657 Level: beginner 658 659 .keywords: DMMoab, create 660 @*/ 661 PetscErrorCode DMMoabGetMaterialBlock(DM dm, const moab::EntityHandle ehandle, PetscInt *mat) 662 { 663 DM_Moab *dmmoab; 664 moab::ErrorCode merr; 665 666 PetscFunctionBegin; 667 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 668 if (*mat) { 669 dmmoab = (DM_Moab*)(dm)->data; 670 merr = dmmoab->mbiface->tag_get_data(dmmoab->material_tag, &ehandle, 1, mat); MBERRNM(merr); 671 } 672 PetscFunctionReturn(0); 673 } 674 675 676 /*@ 677 DMMoabGetVertexCoordinates - Get the coordinates corresponding to the requested vertex entities 678 679 Collective on MPI_Comm 680 681 Input Parameter: 682 . dm - The DMMoab object 683 . nconn - Number of entities whose coordinates are needed 684 . conn - The vertex entity handles 685 686 Output Parameter: 687 . vpos - The coordinates of the requested vertex entities 688 689 Level: beginner 690 691 .seealso: DMMoabGetVertexConnectivity() 692 @*/ 693 PetscErrorCode DMMoabGetVertexCoordinates(DM dm, PetscInt nconn, const moab::EntityHandle *conn, PetscReal *vpos) 694 { 695 DM_Moab *dmmoab; 696 moab::ErrorCode merr; 697 698 PetscFunctionBegin; 699 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 700 PetscValidPointer(conn, 3); 701 PetscValidPointer(vpos, 4); 702 dmmoab = (DM_Moab*)(dm)->data; 703 704 /* Get connectivity information in MOAB canonical ordering */ 705 if (dmmoab->hlevel) { 706 merr = dmmoab->hierarchy->get_coordinates(const_cast<moab::EntityHandle*>(conn), nconn, dmmoab->hlevel, vpos);MBERRNM(merr); 707 } 708 else { 709 merr = dmmoab->mbiface->get_coords(conn, nconn, vpos);MBERRNM(merr); 710 } 711 PetscFunctionReturn(0); 712 } 713 714 715 /*@ 716 DMMoabGetVertexConnectivity - Get the vertex adjacency for the given entity 717 718 Collective on MPI_Comm 719 720 Input Parameter: 721 . dm - The DMMoab object 722 . vhandle - Vertex entity handle 723 724 Output Parameter: 725 . nconn - Number of entities whose coordinates are needed 726 . conn - The vertex entity handles 727 728 Level: beginner 729 730 .seealso: DMMoabGetVertexCoordinates(), DMMoabRestoreVertexConnectivity() 731 @*/ 732 PetscErrorCode DMMoabGetVertexConnectivity(DM dm, moab::EntityHandle vhandle, PetscInt* nconn, moab::EntityHandle **conn) 733 { 734 DM_Moab *dmmoab; 735 std::vector<moab::EntityHandle> adj_entities, connect; 736 PetscErrorCode ierr; 737 moab::ErrorCode merr; 738 739 PetscFunctionBegin; 740 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 741 PetscValidPointer(conn, 4); 742 dmmoab = (DM_Moab*)(dm)->data; 743 744 /* Get connectivity information in MOAB canonical ordering */ 745 merr = dmmoab->mbiface->get_adjacencies(&vhandle, 1, 1, true, adj_entities, moab::Interface::UNION); MBERRNM(merr); 746 merr = dmmoab->mbiface->get_connectivity(&adj_entities[0], adj_entities.size(), connect); MBERRNM(merr); 747 748 if (conn) { 749 ierr = PetscMalloc(sizeof(moab::EntityHandle) * connect.size(), conn);CHKERRQ(ierr); 750 ierr = PetscMemcpy(*conn, &connect[0], sizeof(moab::EntityHandle) * connect.size());CHKERRQ(ierr); 751 } 752 if (nconn) *nconn = connect.size(); 753 PetscFunctionReturn(0); 754 } 755 756 757 /*@ 758 DMMoabRestoreVertexConnectivity - Restore the vertex connectivity for the given entity 759 760 Collective on MPI_Comm 761 762 Input Parameter: 763 . dm - The DMMoab object 764 . vhandle - Vertex entity handle 765 . nconn - Number of entities whose coordinates are needed 766 . conn - The vertex entity handles 767 768 Level: beginner 769 770 .seealso: DMMoabGetVertexCoordinates(), DMMoabGetVertexConnectivity() 771 @*/ 772 PetscErrorCode DMMoabRestoreVertexConnectivity(DM dm, moab::EntityHandle ehandle, PetscInt* nconn, moab::EntityHandle **conn) 773 { 774 PetscErrorCode ierr; 775 776 PetscFunctionBegin; 777 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 778 PetscValidPointer(conn, 4); 779 780 if (conn) { 781 ierr = PetscFree(*conn);CHKERRQ(ierr); 782 } 783 if (nconn) *nconn = 0; 784 PetscFunctionReturn(0); 785 } 786 787 788 /*@ 789 DMMoabGetElementConnectivity - Get the vertex adjacency for the given entity 790 791 Collective on MPI_Comm 792 793 Input Parameter: 794 . dm - The DMMoab object 795 . ehandle - Vertex entity handle 796 797 Output Parameter: 798 . nconn - Number of entities whose coordinates are needed 799 . conn - The vertex entity handles 800 801 Level: beginner 802 803 .seealso: DMMoabGetVertexCoordinates(), DMMoabGetVertexConnectivity(), DMMoabRestoreVertexConnectivity() 804 @*/ 805 PetscErrorCode DMMoabGetElementConnectivity(DM dm, moab::EntityHandle ehandle, PetscInt* nconn, const moab::EntityHandle **conn) 806 { 807 DM_Moab *dmmoab; 808 const moab::EntityHandle *connect; 809 std::vector<moab::EntityHandle> vconn; 810 moab::ErrorCode merr; 811 PetscInt nnodes; 812 813 PetscFunctionBegin; 814 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 815 PetscValidPointer(conn, 4); 816 dmmoab = (DM_Moab*)(dm)->data; 817 818 /* Get connectivity information in MOAB canonical ordering */ 819 merr = dmmoab->mbiface->get_connectivity(ehandle, connect, nnodes); MBERRNM(merr); 820 if (conn) *conn = connect; 821 if (nconn) *nconn = nnodes; 822 PetscFunctionReturn(0); 823 } 824 825 826 /*@ 827 DMMoabIsEntityOnBoundary - Check whether a given entity is on the boundary (vertex, edge, face, element) 828 829 Collective on MPI_Comm 830 831 Input Parameter: 832 . dm - The DMMoab object 833 . ent - Entity handle 834 835 Output Parameter: 836 . ent_on_boundary - PETSC_TRUE if entity on boundary; PETSC_FALSE otherwise 837 838 Level: beginner 839 840 .seealso: DMMoabCheckBoundaryVertices() 841 @*/ 842 PetscErrorCode DMMoabIsEntityOnBoundary(DM dm, const moab::EntityHandle ent, PetscBool* ent_on_boundary) 843 { 844 moab::EntityType etype; 845 DM_Moab *dmmoab; 846 PetscInt edim; 847 848 PetscFunctionBegin; 849 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 850 PetscValidPointer(ent_on_boundary, 3); 851 dmmoab = (DM_Moab*)(dm)->data; 852 853 /* get the entity type and handle accordingly */ 854 etype = dmmoab->mbiface->type_from_handle(ent); 855 if (etype >= moab::MBPOLYHEDRON) SETERRQ1(PETSC_COMM_WORLD, PETSC_ERR_ARG_OUTOFRANGE, "Entity type on the boundary skin is invalid. EntityType = %D\n", etype); 856 857 /* get the entity dimension */ 858 edim = dmmoab->mbiface->dimension_from_handle(ent); 859 860 *ent_on_boundary = PETSC_FALSE; 861 if (etype == moab::MBVERTEX && edim == 0) { 862 *ent_on_boundary = ((dmmoab->bndyvtx->index(ent) >= 0) ? PETSC_TRUE : PETSC_FALSE); 863 } 864 else { 865 if (edim == dmmoab->dim) { /* check the higher-dimensional elements first */ 866 if (dmmoab->bndyelems->index(ent) >= 0) *ent_on_boundary = PETSC_TRUE; 867 } 868 else { /* next check the lower-dimensional faces */ 869 if (dmmoab->bndyfaces->index(ent) >= 0) *ent_on_boundary = PETSC_TRUE; 870 } 871 } 872 PetscFunctionReturn(0); 873 } 874 875 876 /*@ 877 DMMoabIsEntityOnBoundary - Check whether a given entity is on the boundary (vertex, edge, face, element) 878 879 Input Parameter: 880 . dm - The DMMoab object 881 . nconn - Number of handles 882 . cnt - Array of entity handles 883 884 Output Parameter: 885 . isbdvtx - Array of boundary markers - PETSC_TRUE if entity on boundary; PETSC_FALSE otherwise 886 887 Level: beginner 888 889 .seealso: DMMoabIsEntityOnBoundary() 890 @*/ 891 PetscErrorCode DMMoabCheckBoundaryVertices(DM dm, PetscInt nconn, const moab::EntityHandle *cnt, PetscBool* isbdvtx) 892 { 893 DM_Moab *dmmoab; 894 PetscInt i; 895 896 PetscFunctionBegin; 897 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 898 PetscValidPointer(cnt, 3); 899 PetscValidPointer(isbdvtx, 4); 900 dmmoab = (DM_Moab*)(dm)->data; 901 902 for (i = 0; i < nconn; ++i) { 903 isbdvtx[i] = (dmmoab->bndyvtx->index(cnt[i]) >= 0 ? PETSC_TRUE : PETSC_FALSE); 904 } 905 PetscFunctionReturn(0); 906 } 907 908 909 /*@ 910 DMMoabGetBoundaryMarkers - Return references to the vertices, faces, elements on the boundary 911 912 Input Parameter: 913 . dm - The DMMoab object 914 915 Output Parameter: 916 . bdvtx - Boundary vertices 917 . bdelems - Boundary elements 918 . bdfaces - Boundary faces 919 920 Level: beginner 921 922 .seealso: DMMoabCheckBoundaryVertices(), DMMoabIsEntityOnBoundary() 923 @*/ 924 PetscErrorCode DMMoabGetBoundaryMarkers(DM dm, const moab::Range **bdvtx, const moab::Range** bdelems, const moab::Range** bdfaces) 925 { 926 DM_Moab *dmmoab; 927 928 PetscFunctionBegin; 929 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 930 dmmoab = (DM_Moab*)(dm)->data; 931 932 if (bdvtx) *bdvtx = dmmoab->bndyvtx; 933 if (bdfaces) *bdfaces = dmmoab->bndyfaces; 934 if (bdelems) *bdfaces = dmmoab->bndyelems; 935 PetscFunctionReturn(0); 936 } 937 938 939 PETSC_EXTERN PetscErrorCode DMDestroy_Moab(DM dm) 940 { 941 PetscErrorCode ierr; 942 PetscInt i; 943 moab::ErrorCode merr; 944 DM_Moab *dmmoab = (DM_Moab*)dm->data; 945 946 PetscFunctionBegin; 947 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 948 949 dmmoab->refct--; 950 if (!dmmoab->refct) { 951 delete dmmoab->vlocal; 952 delete dmmoab->vowned; 953 delete dmmoab->vghost; 954 delete dmmoab->elocal; 955 delete dmmoab->eghost; 956 delete dmmoab->bndyvtx; 957 delete dmmoab->bndyfaces; 958 delete dmmoab->bndyelems; 959 960 ierr = PetscFree(dmmoab->gsindices);CHKERRQ(ierr); 961 ierr = PetscFree2(dmmoab->gidmap, dmmoab->lidmap);CHKERRQ(ierr); 962 ierr = PetscFree(dmmoab->dfill);CHKERRQ(ierr); 963 ierr = PetscFree(dmmoab->ofill);CHKERRQ(ierr); 964 ierr = PetscFree(dmmoab->materials);CHKERRQ(ierr); 965 if (dmmoab->fieldNames) { 966 for (i = 0; i < dmmoab->numFields; i++) { 967 ierr = PetscFree(dmmoab->fieldNames[i]);CHKERRQ(ierr); 968 } 969 ierr = PetscFree(dmmoab->fieldNames);CHKERRQ(ierr); 970 } 971 972 if (dmmoab->nhlevels) { 973 ierr = PetscFree(dmmoab->hsets);CHKERRQ(ierr); 974 dmmoab->nhlevels = 0; 975 if (!dmmoab->hlevel && dmmoab->icreatedinstance) delete dmmoab->hierarchy; 976 dmmoab->hierarchy = NULL; 977 } 978 979 if (dmmoab->icreatedinstance) { 980 delete dmmoab->pcomm; 981 merr = dmmoab->mbiface->delete_mesh(); MBERRNM(merr); 982 delete dmmoab->mbiface; 983 } 984 dmmoab->mbiface = NULL; 985 #ifdef MOAB_HAVE_MPI 986 dmmoab->pcomm = NULL; 987 #endif 988 ierr = VecScatterDestroy(&dmmoab->ltog_sendrecv);CHKERRQ(ierr); 989 ierr = ISLocalToGlobalMappingDestroy(&dmmoab->ltog_map);CHKERRQ(ierr); 990 ierr = PetscFree(dm->data);CHKERRQ(ierr); 991 } 992 PetscFunctionReturn(0); 993 } 994 995 996 #undef __FUNCT__ 997 #define __FUNCT__ "DMSetFromOptions_Moab" 998 PETSC_EXTERN PetscErrorCode DMSetFromOptions_Moab(PetscOptionItems *PetscOptionsObject, DM dm) 999 { 1000 PetscErrorCode ierr; 1001 DM_Moab *dmmoab = (DM_Moab*)dm->data; 1002 1003 PetscFunctionBegin; 1004 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1005 ierr = PetscOptionsHead(PetscOptionsObject, "DMMoab Options");CHKERRQ(ierr); 1006 ierr = PetscOptionsInt("-dm_moab_rw_dbg", "The verbosity level for reading and writing MOAB meshes", "DMView", dmmoab->rw_dbglevel, &dmmoab->rw_dbglevel, NULL);CHKERRQ(ierr); 1007 ierr = PetscOptionsBool("-dm_moab_partiton_by_rank", "Use partition by rank when reading MOAB meshes from file", "DMView", dmmoab->partition_by_rank, &dmmoab->partition_by_rank, NULL);CHKERRQ(ierr); 1008 /* TODO: typically, the read options are needed before a DM is completely created and available in which case, the options wont be available ?? */ 1009 ierr = PetscOptionsString("-dm_moab_read_opts", "Extra options to enable MOAB reader to load DM from file", "DMView", dmmoab->extra_read_options, dmmoab->extra_read_options, PETSC_MAX_PATH_LEN, NULL);CHKERRQ(ierr); 1010 ierr = PetscOptionsString("-dm_moab_write_opts", "Extra options to enable MOAB writer to serialize DM to file", "DMView", dmmoab->extra_write_options, dmmoab->extra_write_options, PETSC_MAX_PATH_LEN, NULL);CHKERRQ(ierr); 1011 ierr = PetscOptionsEnum("-dm_moab_read_mode", "MOAB parallel read mode", "DMView", MoabReadModes, (PetscEnum)dmmoab->read_mode, (PetscEnum*)&dmmoab->read_mode, NULL);CHKERRQ(ierr); 1012 ierr = PetscOptionsEnum("-dm_moab_write_mode", "MOAB parallel write mode", "DMView", MoabWriteModes, (PetscEnum)dmmoab->write_mode, (PetscEnum*)&dmmoab->write_mode, NULL);CHKERRQ(ierr); 1013 PetscFunctionReturn(0); 1014 } 1015 1016 1017 PETSC_EXTERN PetscErrorCode DMSetUp_Moab(DM dm) 1018 { 1019 PetscErrorCode ierr; 1020 moab::ErrorCode merr; 1021 Vec local, global; 1022 IS from, to; 1023 moab::Range::iterator iter; 1024 PetscInt i, j, f, bs, vent, totsize, *lgmap; 1025 DM_Moab *dmmoab = (DM_Moab*)dm->data; 1026 moab::Range adjs; 1027 1028 PetscFunctionBegin; 1029 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1030 /* Get the local and shared vertices and cache it */ 1031 if (dmmoab->mbiface == NULL) SETERRQ(PETSC_COMM_WORLD, PETSC_ERR_ORDER, "Set the MOAB Interface before calling SetUp."); 1032 #ifdef MOAB_HAVE_MPI 1033 if (dmmoab->pcomm == NULL) SETERRQ(PETSC_COMM_WORLD, PETSC_ERR_ORDER, "Set the MOAB ParallelComm object before calling SetUp."); 1034 #endif 1035 1036 /* Get the entities recursively in the current part of the mesh, if user did not set the local vertices explicitly */ 1037 if (dmmoab->vlocal->empty()) 1038 { 1039 //merr = dmmoab->mbiface->get_entities_by_type(dmmoab->fileset,moab::MBVERTEX,*dmmoab->vlocal,true);MBERRNM(merr); 1040 merr = dmmoab->mbiface->get_entities_by_dimension(dmmoab->fileset, 0, *dmmoab->vlocal, false); MBERRNM(merr); 1041 1042 #ifdef MOAB_HAVE_MPI 1043 /* filter based on parallel status */ 1044 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->vlocal, PSTATUS_NOT_OWNED, PSTATUS_NOT, -1, dmmoab->vowned); MBERRNM(merr); 1045 1046 /* filter all the non-owned and shared entities out of the list */ 1047 // *dmmoab->vghost = moab::subtract(*dmmoab->vlocal, *dmmoab->vowned); 1048 adjs = moab::subtract(*dmmoab->vlocal, *dmmoab->vowned); 1049 merr = dmmoab->pcomm->filter_pstatus(adjs, PSTATUS_GHOST | PSTATUS_INTERFACE, PSTATUS_OR, -1, dmmoab->vghost); MBERRNM(merr); 1050 adjs = moab::subtract(adjs, *dmmoab->vghost); 1051 *dmmoab->vlocal = moab::subtract(*dmmoab->vlocal, adjs); 1052 #else 1053 *dmmoab->vowned = *dmmoab->vlocal; 1054 #endif 1055 1056 /* compute and cache the sizes of local and ghosted entities */ 1057 dmmoab->nloc = dmmoab->vowned->size(); 1058 dmmoab->nghost = dmmoab->vghost->size(); 1059 1060 #ifdef MOAB_HAVE_MPI 1061 ierr = MPIU_Allreduce(&dmmoab->nloc, &dmmoab->n, 1, MPI_INTEGER, MPI_SUM, ((PetscObject)dm)->comm);CHKERRQ(ierr); 1062 PetscInfo4(NULL, "Filset ID: %u, Vertices: local - %D, owned - %D, ghosted - %D.\n", dmmoab->fileset, dmmoab->vlocal->size(), dmmoab->nloc, dmmoab->nghost); 1063 #else 1064 dmmoab->n = dmmoab->nloc; 1065 #endif 1066 } 1067 1068 { 1069 /* get the information about the local elements in the mesh */ 1070 dmmoab->eghost->clear(); 1071 1072 /* first decipher the leading dimension */ 1073 for (i = 3; i > 0; i--) { 1074 dmmoab->elocal->clear(); 1075 merr = dmmoab->mbiface->get_entities_by_dimension(dmmoab->fileset, i, *dmmoab->elocal, false); MBERRNM(merr); 1076 1077 /* store the current mesh dimension */ 1078 if (dmmoab->elocal->size()) { 1079 dmmoab->dim = i; 1080 break; 1081 } 1082 } 1083 1084 ierr = DMSetDimension(dm, dmmoab->dim);CHKERRQ(ierr); 1085 1086 #ifdef MOAB_HAVE_MPI 1087 /* filter the ghosted and owned element list */ 1088 *dmmoab->eghost = *dmmoab->elocal; 1089 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->elocal, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1090 *dmmoab->eghost = moab::subtract(*dmmoab->eghost, *dmmoab->elocal); 1091 #endif 1092 1093 dmmoab->neleloc = dmmoab->elocal->size(); 1094 dmmoab->neleghost = dmmoab->eghost->size(); 1095 1096 #ifdef MOAB_HAVE_MPI 1097 ierr = MPIU_Allreduce(&dmmoab->neleloc, &dmmoab->nele, 1, MPI_INTEGER, MPI_SUM, ((PetscObject)dm)->comm);CHKERRQ(ierr); 1098 PetscInfo3(NULL, "%d-dim elements: owned - %D, ghosted - %D.\n", dmmoab->dim, dmmoab->neleloc, dmmoab->neleghost); 1099 #else 1100 dmmoab->nele = dmmoab->neleloc; 1101 #endif 1102 } 1103 1104 bs = dmmoab->bs; 1105 if (!dmmoab->ltog_tag) { 1106 /* Get the global ID tag. The global ID tag is applied to each 1107 vertex. It acts as an global identifier which MOAB uses to 1108 assemble the individual pieces of the mesh */ 1109 merr = dmmoab->mbiface->tag_get_handle(GLOBAL_ID_TAG_NAME, dmmoab->ltog_tag); MBERRNM(merr); 1110 } 1111 1112 totsize = dmmoab->vlocal->size(); 1113 if (totsize != dmmoab->nloc + dmmoab->nghost) SETERRQ2(PETSC_COMM_SELF, PETSC_ERR_ARG_OUTOFRANGE, "Mismatch between local and owned+ghost vertices. %D != %D.", totsize, dmmoab->nloc + dmmoab->nghost); 1114 ierr = PetscCalloc1(totsize, &dmmoab->gsindices);CHKERRQ(ierr); 1115 { 1116 /* first get the local indices */ 1117 merr = dmmoab->mbiface->tag_get_data(dmmoab->ltog_tag, *dmmoab->vowned, &dmmoab->gsindices[0]); MBERRNM(merr); 1118 if (dmmoab->nghost) { /* next get the ghosted indices */ 1119 merr = dmmoab->mbiface->tag_get_data(dmmoab->ltog_tag, *dmmoab->vghost, &dmmoab->gsindices[dmmoab->nloc]); MBERRNM(merr); 1120 } 1121 1122 /* find out the local and global minima of GLOBAL_ID */ 1123 dmmoab->lminmax[0] = dmmoab->lminmax[1] = dmmoab->gsindices[0]; 1124 for (i = 0; i < totsize; ++i) { 1125 if (dmmoab->lminmax[0] > dmmoab->gsindices[i]) dmmoab->lminmax[0] = dmmoab->gsindices[i]; 1126 if (dmmoab->lminmax[1] < dmmoab->gsindices[i]) dmmoab->lminmax[1] = dmmoab->gsindices[i]; 1127 } 1128 1129 ierr = MPIU_Allreduce(&dmmoab->lminmax[0], &dmmoab->gminmax[0], 1, MPI_INT, MPI_MIN, ((PetscObject)dm)->comm);CHKERRQ(ierr); 1130 ierr = MPIU_Allreduce(&dmmoab->lminmax[1], &dmmoab->gminmax[1], 1, MPI_INT, MPI_MAX, ((PetscObject)dm)->comm);CHKERRQ(ierr); 1131 1132 /* set the GID map */ 1133 for (i = 0; i < totsize; ++i) { 1134 dmmoab->gsindices[i] -= dmmoab->gminmax[0]; /* zero based index needed for IS */ 1135 PetscInfo2(NULL, "GLOBAL_ID %d: %D\n", i, dmmoab->gsindices[i]); 1136 1137 } 1138 dmmoab->lminmax[0] -= dmmoab->gminmax[0]; 1139 dmmoab->lminmax[1] -= dmmoab->gminmax[0]; 1140 1141 PetscInfo4(NULL, "GLOBAL_ID: Local [min, max] - [%D, %D], Global [min, max] - [%D, %D]\n", dmmoab->lminmax[0], dmmoab->lminmax[1], dmmoab->gminmax[0], dmmoab->gminmax[1]); 1142 } 1143 if (!(dmmoab->bs == dmmoab->numFields || dmmoab->bs == 1)) SETERRQ3(PETSC_COMM_SELF, PETSC_ERR_ARG_WRONG, "Mismatch between block size and number of component fields. %D != 1 OR %D != %D.", dmmoab->bs, dmmoab->bs, dmmoab->numFields); 1144 1145 { 1146 dmmoab->seqstart = dmmoab->mbiface->id_from_handle(dmmoab->vlocal->front()); 1147 dmmoab->seqend = dmmoab->mbiface->id_from_handle(dmmoab->vlocal->back()); 1148 PetscInfo2(NULL, "SEQUENCE: Local [min, max] - [%D, %D]\n", dmmoab->seqstart, dmmoab->seqend); 1149 1150 ierr = PetscMalloc2(dmmoab->seqend - dmmoab->seqstart + 1, &dmmoab->gidmap, dmmoab->seqend - dmmoab->seqstart + 1, &dmmoab->lidmap);CHKERRQ(ierr); 1151 ierr = PetscMalloc1(totsize * dmmoab->numFields, &lgmap);CHKERRQ(ierr); 1152 1153 i = j = 0; 1154 /* set the owned vertex data first */ 1155 for (moab::Range::iterator iter = dmmoab->vowned->begin(); iter != dmmoab->vowned->end(); iter++, i++) { 1156 vent = (PetscInt)(*iter) - dmmoab->seqstart; 1157 dmmoab->gidmap[vent] = dmmoab->gsindices[i]; 1158 dmmoab->lidmap[vent] = i; 1159 for (f = 0; f < dmmoab->numFields; f++, j++) { 1160 lgmap[j] = (bs > 1 ? dmmoab->gsindices[i] * dmmoab->numFields + f : totsize * f + dmmoab->gsindices[i]); 1161 } 1162 } 1163 /* next arrange all the ghosted data information */ 1164 for (moab::Range::iterator iter = dmmoab->vghost->begin(); iter != dmmoab->vghost->end(); iter++, i++) { 1165 vent = (PetscInt)(*iter) - dmmoab->seqstart; 1166 dmmoab->gidmap[vent] = dmmoab->gsindices[i]; 1167 dmmoab->lidmap[vent] = i; 1168 for (f = 0; f < dmmoab->numFields; f++, j++) { 1169 lgmap[j] = (bs > 1 ? dmmoab->gsindices[i] * dmmoab->numFields + f : totsize * f + dmmoab->gsindices[i]); 1170 } 1171 } 1172 1173 /* We need to create the Global to Local Vector Scatter Contexts 1174 1) First create a local and global vector 1175 2) Create a local and global IS 1176 3) Create VecScatter and LtoGMapping objects 1177 4) Cleanup the IS and Vec objects 1178 */ 1179 ierr = DMCreateGlobalVector(dm, &global);CHKERRQ(ierr); 1180 ierr = DMCreateLocalVector(dm, &local);CHKERRQ(ierr); 1181 1182 ierr = VecGetOwnershipRange(global, &dmmoab->vstart, &dmmoab->vend);CHKERRQ(ierr); 1183 1184 /* global to local must retrieve ghost points */ 1185 ierr = ISCreateStride(((PetscObject)dm)->comm, dmmoab->nloc * dmmoab->numFields, dmmoab->vstart, 1, &from);CHKERRQ(ierr); 1186 ierr = ISSetBlockSize(from, bs);CHKERRQ(ierr); 1187 1188 ierr = ISCreateGeneral(((PetscObject)dm)->comm, dmmoab->nloc * dmmoab->numFields, &lgmap[0], PETSC_COPY_VALUES, &to);CHKERRQ(ierr); 1189 ierr = ISSetBlockSize(to, bs);CHKERRQ(ierr); 1190 1191 if (!dmmoab->ltog_map) { 1192 /* create to the local to global mapping for vectors in order to use VecSetValuesLocal */ 1193 ierr = ISLocalToGlobalMappingCreate(((PetscObject)dm)->comm, dmmoab->bs, totsize * dmmoab->numFields, lgmap, 1194 PETSC_COPY_VALUES, &dmmoab->ltog_map);CHKERRQ(ierr); 1195 } 1196 1197 /* now create the scatter object from local to global vector */ 1198 ierr = VecScatterCreate(local, from, global, to, &dmmoab->ltog_sendrecv);CHKERRQ(ierr); 1199 1200 /* clean up IS, Vec */ 1201 ierr = PetscFree(lgmap);CHKERRQ(ierr); 1202 ierr = ISDestroy(&from);CHKERRQ(ierr); 1203 ierr = ISDestroy(&to);CHKERRQ(ierr); 1204 ierr = VecDestroy(&local);CHKERRQ(ierr); 1205 ierr = VecDestroy(&global);CHKERRQ(ierr); 1206 } 1207 1208 dmmoab->bndyvtx = new moab::Range(); 1209 dmmoab->bndyfaces = new moab::Range(); 1210 dmmoab->bndyelems = new moab::Range(); 1211 /* skin the boundary and store nodes */ 1212 if (!dmmoab->hlevel) { 1213 /* get the skin vertices of boundary faces for the current partition and then filter 1214 the local, boundary faces, vertices and elements alone via PSTATUS flags; 1215 this should not give us any ghosted boundary, but if user needs such a functionality 1216 it would be easy to add it based on the find_skin query below */ 1217 moab::Skinner skinner(dmmoab->mbiface); 1218 1219 /* get the entities on the skin - only the faces */ 1220 merr = skinner.find_skin(dmmoab->fileset, *dmmoab->elocal, false, *dmmoab->bndyfaces, NULL, true, true, false); MBERRNM(merr); // 'false' param indicates we want faces back, not vertices 1221 1222 #ifdef MOAB_HAVE_MPI 1223 /* filter all the non-owned and shared entities out of the list */ 1224 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyfaces, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1225 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyfaces, PSTATUS_INTERFACE, PSTATUS_NOT); MBERRNM(merr); 1226 #endif 1227 1228 /* get all the nodes via connectivity and the parent elements via adjacency information */ 1229 merr = dmmoab->mbiface->get_connectivity(*dmmoab->bndyfaces, *dmmoab->bndyvtx, false); MBERRNM(ierr); 1230 merr = dmmoab->mbiface->get_adjacencies(*dmmoab->bndyvtx, dmmoab->dim, false, *dmmoab->bndyelems, moab::Interface::UNION); MBERRNM(ierr); 1231 } 1232 else { 1233 /* Let us query the hierarchy manager and get the results directly for this level */ 1234 for (moab::Range::iterator iter = dmmoab->elocal->begin(); iter != dmmoab->elocal->end(); iter++) { 1235 moab::EntityHandle elemHandle = *iter; 1236 if (dmmoab->hierarchy->is_entity_on_boundary(elemHandle)) { 1237 dmmoab->bndyelems->insert(elemHandle); 1238 /* For this boundary element, query the vertices and add them to the list */ 1239 std::vector<moab::EntityHandle> connect; 1240 merr = dmmoab->hierarchy->get_connectivity(elemHandle, dmmoab->hlevel, connect); MBERRNM(ierr); 1241 for (unsigned iv=0; iv < connect.size(); ++iv) 1242 if (dmmoab->hierarchy->is_entity_on_boundary(connect[iv])) 1243 dmmoab->bndyvtx->insert(connect[iv]); 1244 /* Next, let us query the boundary faces and add them also to the list */ 1245 std::vector<moab::EntityHandle> faces; 1246 merr = dmmoab->hierarchy->get_adjacencies(elemHandle, dmmoab->dim-1, faces); MBERRNM(ierr); 1247 for (unsigned ifa=0; ifa < faces.size(); ++ifa) 1248 if (dmmoab->hierarchy->is_entity_on_boundary(faces[ifa])) 1249 dmmoab->bndyfaces->insert(faces[ifa]); 1250 } 1251 } 1252 #ifdef MOAB_HAVE_MPI 1253 /* filter all the non-owned and shared entities out of the list */ 1254 // merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyfaces, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1255 // merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyfaces, PSTATUS_INTERFACE, PSTATUS_NOT); MBERRNM(merr); 1256 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyvtx, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1257 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyfaces, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1258 merr = dmmoab->pcomm->filter_pstatus(*dmmoab->bndyelems, PSTATUS_NOT_OWNED, PSTATUS_NOT); MBERRNM(merr); 1259 #endif 1260 1261 } 1262 PetscInfo3(NULL, "Found %D boundary vertices, %D boundary faces and %D boundary elements.\n", dmmoab->bndyvtx->size(), dmmoab->bndyfaces->size(), dmmoab->bndyelems->size()); 1263 PetscFunctionReturn(0); 1264 } 1265 1266 1267 #undef __FUNCT__ 1268 #define __FUNCT__ "DMMoabCreateVertices" 1269 /*@ 1270 DMMoabCreateVertices - Creates and adds several vertices to the primary set represented by the DM. 1271 1272 Collective on MPI_Comm 1273 1274 Input Parameters: 1275 + dm - The DM object 1276 . type - The type of element to create and add (Edge/Tri/Quad/Tet/Hex/Prism/Pyramid/Polygon/Polyhedra) 1277 . conn - The connectivity of the element 1278 . nverts - The number of vertices that form the element 1279 1280 Output Parameter: 1281 . overts - The list of vertices that were created (can be NULL) 1282 1283 Level: beginner 1284 1285 .keywords: DM, create vertices 1286 1287 .seealso: DMMoabCreateSubmesh(), DMMoabCreateElement() 1288 @*/ 1289 PetscErrorCode DMMoabCreateVertices(DM dm, const PetscReal* coords, PetscInt nverts, moab::Range* overts) 1290 { 1291 moab::ErrorCode merr; 1292 DM_Moab *dmmoab; 1293 moab::Range verts; 1294 1295 PetscFunctionBegin; 1296 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1297 PetscValidPointer(coords, 2); 1298 1299 dmmoab = (DM_Moab*) dm->data; 1300 1301 /* Insert new points */ 1302 merr = dmmoab->mbiface->create_vertices(&coords[0], nverts, verts); MBERRNM(merr); 1303 merr = dmmoab->mbiface->add_entities(dmmoab->fileset, verts); MBERRNM(merr); 1304 1305 if (overts) *overts = verts; 1306 PetscFunctionReturn(0); 1307 } 1308 1309 1310 #undef __FUNCT__ 1311 #define __FUNCT__ "DMMoabCreateElement" 1312 /*@ 1313 DMMoabCreateElement - Adds an element of specified type to the primary set represented by the DM. 1314 1315 Collective on MPI_Comm 1316 1317 Input Parameters: 1318 + dm - The DM object 1319 . type - The type of element to create and add (Edge/Tri/Quad/Tet/Hex/Prism/Pyramid/Polygon/Polyhedra) 1320 . conn - The connectivity of the element 1321 . nverts - The number of vertices that form the element 1322 1323 Output Parameter: 1324 . oelem - The handle to the element created and added to the DM object 1325 1326 Level: beginner 1327 1328 .keywords: DM, create element 1329 1330 .seealso: DMMoabCreateSubmesh(), DMMoabCreateVertices() 1331 @*/ 1332 PetscErrorCode DMMoabCreateElement(DM dm, const moab::EntityType type, const moab::EntityHandle* conn, PetscInt nverts, moab::EntityHandle* oelem) 1333 { 1334 moab::ErrorCode merr; 1335 DM_Moab *dmmoab; 1336 moab::EntityHandle elem; 1337 1338 PetscFunctionBegin; 1339 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1340 PetscValidPointer(conn, 3); 1341 1342 dmmoab = (DM_Moab*) dm->data; 1343 1344 /* Insert new element */ 1345 merr = dmmoab->mbiface->create_element(type, conn, nverts, elem); MBERRNM(merr); 1346 merr = dmmoab->mbiface->add_entities(dmmoab->fileset, &elem, 1); MBERRNM(merr); 1347 1348 if (oelem) *oelem = elem; 1349 PetscFunctionReturn(0); 1350 } 1351 1352 1353 #undef __FUNCT__ 1354 #define __FUNCT__ "DMMoabCreateSubmesh" 1355 /*@ 1356 DMMoabCreateSubmesh - Creates a sub-DM object with a set that contains all vertices/elements of the parent 1357 in addition to providing support for dynamic mesh modifications. This is useful for AMR calculations to 1358 create a DM object on a refined level. 1359 1360 Collective on MPI_Comm 1361 1362 Input Parameters: 1363 + dm - The DM object 1364 1365 Output Parameter: 1366 . newdm - The sub DM object with updated set information 1367 1368 Level: advanced 1369 1370 .keywords: DM, sub-DM 1371 1372 .seealso: DMCreate(), DMMoabCreateVertices(), DMMoabCreateElement() 1373 @*/ 1374 PetscErrorCode DMMoabCreateSubmesh(DM dm, DM *newdm) 1375 { 1376 DM_Moab *dmmoab; 1377 DM_Moab *ndmmoab; 1378 moab::ErrorCode merr; 1379 PetscErrorCode ierr; 1380 1381 PetscFunctionBegin; 1382 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1383 1384 dmmoab = (DM_Moab*) dm->data; 1385 1386 /* Create the basic DMMoab object and keep the default parameters created by DM impls */ 1387 ierr = DMMoabCreateMoab(((PetscObject)dm)->comm, dmmoab->mbiface, &dmmoab->ltog_tag, PETSC_NULL, newdm);CHKERRQ(ierr); 1388 1389 /* get all the necessary handles from the private DM object */ 1390 ndmmoab = (DM_Moab*) (*newdm)->data; 1391 1392 /* set the sub-mesh's parent DM reference */ 1393 ndmmoab->parent = &dm; 1394 1395 /* create a file set to associate all entities in current mesh */ 1396 merr = ndmmoab->mbiface->create_meshset(moab::MESHSET_SET, ndmmoab->fileset); MBERR("Creating file set failed", merr); 1397 1398 /* create a meshset and then add old fileset as child */ 1399 merr = ndmmoab->mbiface->add_entities(ndmmoab->fileset, *dmmoab->vlocal); MBERR("Adding child vertices to parent failed", merr); 1400 merr = ndmmoab->mbiface->add_entities(ndmmoab->fileset, *dmmoab->elocal); MBERR("Adding child elements to parent failed", merr); 1401 1402 /* preserve the field association between the parent and sub-mesh objects */ 1403 ierr = DMMoabSetFieldNames(*newdm, dmmoab->numFields, dmmoab->fieldNames);CHKERRQ(ierr); 1404 PetscFunctionReturn(0); 1405 } 1406 1407 1408 #undef __FUNCT__ 1409 #define __FUNCT__ "DMMoabView_Ascii" 1410 PETSC_EXTERN PetscErrorCode DMMoabView_Ascii(DM dm, PetscViewer viewer) 1411 { 1412 DM_Moab *dmmoab = (DM_Moab*)(dm)->data; 1413 const char *name; 1414 MPI_Comm comm; 1415 PetscMPIInt size; 1416 PetscErrorCode ierr; 1417 1418 PetscFunctionBegin; 1419 ierr = PetscObjectGetComm((PetscObject)dm, &comm);CHKERRQ(ierr); 1420 ierr = MPI_Comm_size(comm, &size);CHKERRQ(ierr); 1421 ierr = PetscObjectGetName((PetscObject) dm, &name);CHKERRQ(ierr); 1422 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 1423 if (name) {ierr = PetscViewerASCIIPrintf(viewer, "%s in %D dimensions:\n", name, dmmoab->dim);CHKERRQ(ierr);} 1424 else {ierr = PetscViewerASCIIPrintf(viewer, "Mesh in %D dimensions:\n", dmmoab->dim);CHKERRQ(ierr);} 1425 /* print details about the global mesh */ 1426 { 1427 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 1428 ierr = PetscViewerASCIIPrintf(viewer, "Sizes: cells=%D, vertices=%D, blocks=%D\n", dmmoab->nele, dmmoab->n, dmmoab->bs);CHKERRQ(ierr); 1429 /* print boundary data */ 1430 ierr = PetscViewerASCIIPrintf(viewer, "Boundary trace:\n", dmmoab->bndyelems->size(), dmmoab->bndyfaces->size(), dmmoab->bndyvtx->size());CHKERRQ(ierr); 1431 { 1432 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 1433 ierr = PetscViewerASCIIPrintf(viewer, "cells=%D, faces=%D, vertices=%D\n", dmmoab->bndyelems->size(), dmmoab->bndyfaces->size(), dmmoab->bndyvtx->size());CHKERRQ(ierr); 1434 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 1435 } 1436 /* print field data */ 1437 ierr = PetscViewerASCIIPrintf(viewer, "Fields: %D components\n", dmmoab->numFields);CHKERRQ(ierr); 1438 { 1439 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 1440 for (int i = 0; i < dmmoab->numFields; ++i) { 1441 ierr = PetscViewerASCIIPrintf(viewer, "[%D] - %s\n", i, dmmoab->fieldNames[i]);CHKERRQ(ierr); 1442 } 1443 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 1444 } 1445 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 1446 } 1447 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 1448 ierr = PetscViewerFlush(viewer);CHKERRQ(ierr); 1449 PetscFunctionReturn(0); 1450 } 1451 1452 #undef __FUNCT__ 1453 #define __FUNCT__ "DMMoabView_VTK" 1454 PETSC_EXTERN PetscErrorCode DMMoabView_VTK(DM dm, PetscViewer v) 1455 { 1456 PetscFunctionReturn(0); 1457 } 1458 1459 #undef __FUNCT__ 1460 #define __FUNCT__ "DMMoabView_HDF5" 1461 PETSC_EXTERN PetscErrorCode DMMoabView_HDF5(DM dm, PetscViewer v) 1462 { 1463 PetscFunctionReturn(0); 1464 } 1465 1466 #undef __FUNCT__ 1467 #define __FUNCT__ "DMView_Moab" 1468 PETSC_EXTERN PetscErrorCode DMView_Moab(DM dm, PetscViewer viewer) 1469 { 1470 PetscBool iascii, ishdf5, isvtk; 1471 PetscErrorCode ierr; 1472 1473 PetscFunctionBegin; 1474 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1475 PetscValidHeaderSpecific(viewer, PETSC_VIEWER_CLASSID, 2); 1476 ierr = PetscObjectTypeCompare((PetscObject) viewer, PETSCVIEWERASCII, &iascii);CHKERRQ(ierr); 1477 ierr = PetscObjectTypeCompare((PetscObject) viewer, PETSCVIEWERVTK, &isvtk);CHKERRQ(ierr); 1478 ierr = PetscObjectTypeCompare((PetscObject) viewer, PETSCVIEWERHDF5, &ishdf5);CHKERRQ(ierr); 1479 if (iascii) { 1480 ierr = DMMoabView_Ascii(dm, viewer);CHKERRQ(ierr); 1481 } else if (ishdf5) { 1482 #if defined(PETSC_HAVE_HDF5) && defined(MOAB_HAVE_HDF5) 1483 ierr = PetscViewerPushFormat(viewer, PETSC_VIEWER_HDF5_VIZ);CHKERRQ(ierr); 1484 ierr = DMMoabView_HDF5(dm, viewer);CHKERRQ(ierr); 1485 ierr = PetscViewerPopFormat(viewer);CHKERRQ(ierr); 1486 #else 1487 SETERRQ(PetscObjectComm((PetscObject) dm), PETSC_ERR_SUP, "HDF5 not supported in this build.\nPlease reconfigure using --download-hdf5"); 1488 #endif 1489 } 1490 else if (isvtk) { 1491 ierr = DMMoabView_VTK(dm, viewer);CHKERRQ(ierr); 1492 } 1493 PetscFunctionReturn(0); 1494 } 1495 1496 1497 #undef __FUNCT__ 1498 #define __FUNCT__ "DMInitialize_Moab" 1499 PETSC_EXTERN PetscErrorCode DMInitialize_Moab(DM dm) 1500 { 1501 PetscFunctionBegin; 1502 dm->ops->view = DMView_Moab; 1503 dm->ops->load = NULL /*DMLoad_Moab*/; 1504 dm->ops->setfromoptions = DMSetFromOptions_Moab; 1505 dm->ops->clone = DMClone_Moab; 1506 dm->ops->setup = DMSetUp_Moab; 1507 dm->ops->createdefaultsection = NULL; 1508 dm->ops->createdefaultconstraints = NULL; 1509 dm->ops->createglobalvector = DMCreateGlobalVector_Moab; 1510 dm->ops->createlocalvector = DMCreateLocalVector_Moab; 1511 dm->ops->getlocaltoglobalmapping = NULL; 1512 dm->ops->createfieldis = NULL; 1513 dm->ops->createcoordinatedm = NULL /*DMCreateCoordinateDM_Moab*/; 1514 dm->ops->getcoloring = NULL; 1515 dm->ops->creatematrix = DMCreateMatrix_Moab; 1516 dm->ops->createinterpolation = DMCreateInterpolation_Moab; 1517 dm->ops->getaggregates = NULL; 1518 dm->ops->getinjection = NULL /*DMCreateInjection_Moab*/; 1519 dm->ops->refine = DMRefine_Moab; 1520 dm->ops->coarsen = DMCoarsen_Moab; 1521 dm->ops->refinehierarchy = DMRefineHierarchy_Moab; 1522 dm->ops->coarsenhierarchy = DMCoarsenHierarchy_Moab; 1523 dm->ops->globaltolocalbegin = DMGlobalToLocalBegin_Moab; 1524 dm->ops->globaltolocalend = DMGlobalToLocalEnd_Moab; 1525 dm->ops->localtoglobalbegin = DMLocalToGlobalBegin_Moab; 1526 dm->ops->localtoglobalend = DMLocalToGlobalEnd_Moab; 1527 dm->ops->destroy = DMDestroy_Moab; 1528 dm->ops->createsubdm = NULL /*DMCreateSubDM_Moab*/; 1529 dm->ops->getdimpoints = NULL /*DMGetDimPoints_Moab*/; 1530 dm->ops->locatepoints = NULL /*DMLocatePoints_Moab*/; 1531 PetscFunctionReturn(0); 1532 } 1533 1534 1535 #undef __FUNCT__ 1536 #define __FUNCT__ "DMClone_Moab" 1537 PETSC_EXTERN PetscErrorCode DMClone_Moab(DM dm, DM *newdm) 1538 { 1539 PetscErrorCode ierr; 1540 1541 PetscFunctionBegin; 1542 ierr = PetscObjectChangeTypeName((PetscObject) * newdm, DMMOAB);CHKERRQ(ierr); 1543 1544 /* get all the necessary handles from the private DM object */ 1545 (*newdm)->data = (DM_Moab*) dm->data; 1546 ((DM_Moab*)dm->data)->refct++; 1547 1548 ierr = DMInitialize_Moab(*newdm);CHKERRQ(ierr); 1549 PetscFunctionReturn(0); 1550 } 1551 1552 1553 #undef __FUNCT__ 1554 #define __FUNCT__ "DMCreate_Moab" 1555 PETSC_EXTERN PetscErrorCode DMCreate_Moab(DM dm) 1556 { 1557 PetscErrorCode ierr; 1558 1559 PetscFunctionBegin; 1560 PetscValidHeaderSpecific(dm, DM_CLASSID, 1); 1561 ierr = PetscNewLog(dm, (DM_Moab**)&dm->data);CHKERRQ(ierr); 1562 1563 ((DM_Moab*)dm->data)->bs = 1; 1564 ((DM_Moab*)dm->data)->numFields = 1; 1565 ((DM_Moab*)dm->data)->n = 0; 1566 ((DM_Moab*)dm->data)->nloc = 0; 1567 ((DM_Moab*)dm->data)->nghost = 0; 1568 ((DM_Moab*)dm->data)->nele = 0; 1569 ((DM_Moab*)dm->data)->neleloc = 0; 1570 ((DM_Moab*)dm->data)->neleghost = 0; 1571 ((DM_Moab*)dm->data)->ltog_map = NULL; 1572 ((DM_Moab*)dm->data)->ltog_sendrecv = NULL; 1573 1574 ((DM_Moab*)dm->data)->refct = 1; 1575 ((DM_Moab*)dm->data)->parent = NULL; 1576 ((DM_Moab*)dm->data)->vlocal = new moab::Range(); 1577 ((DM_Moab*)dm->data)->vowned = new moab::Range(); 1578 ((DM_Moab*)dm->data)->vghost = new moab::Range(); 1579 ((DM_Moab*)dm->data)->elocal = new moab::Range(); 1580 ((DM_Moab*)dm->data)->eghost = new moab::Range(); 1581 1582 ierr = DMInitialize_Moab(dm);CHKERRQ(ierr); 1583 PetscFunctionReturn(0); 1584 } 1585 1586