1 #define PETSC_DLL 2 /* 3 Provides utility routines for manipulating any type of PETSc object. 4 */ 5 #include "petsc.h" /*I "petsc.h" I*/ 6 #include "petscsys.h" 7 8 EXTERN PetscErrorCode PetscObjectGetComm_Petsc(PetscObject,MPI_Comm *); 9 EXTERN PetscErrorCode PetscObjectCompose_Petsc(PetscObject,const char[],PetscObject); 10 EXTERN PetscErrorCode PetscObjectQuery_Petsc(PetscObject,const char[],PetscObject *); 11 EXTERN PetscErrorCode PetscObjectComposeFunction_Petsc(PetscObject,const char[],const char[],void (*)(void)); 12 EXTERN PetscErrorCode PetscObjectQueryFunction_Petsc(PetscObject,const char[],void (**)(void)); 13 14 #undef __FUNCT__ 15 #define __FUNCT__ "PetscHeaderCreate_Private" 16 /* 17 PetscHeaderCreate_Private - Creates a base PETSc object header and fills 18 in the default values. Called by the macro PetscHeaderCreate(). 19 */ 20 PetscErrorCode PETSC_DLLEXPORT PetscHeaderCreate_Private(PetscObject h,PetscCookie cookie,PetscInt type,const char class_name[],MPI_Comm comm, 21 PetscErrorCode (*des)(PetscObject),PetscErrorCode (*vie)(PetscObject,PetscViewer)) 22 { 23 static PetscInt idcnt = 1; 24 PetscErrorCode ierr; 25 26 PetscFunctionBegin; 27 h->cookie = cookie; 28 h->type = type; 29 h->class_name = (char*)class_name; 30 h->prefix = 0; 31 h->refct = 1; 32 h->amem = -1; 33 h->id = idcnt++; 34 h->parentid = 0; 35 h->qlist = 0; 36 h->olist = 0; 37 h->bops->destroy = des; 38 h->bops->view = vie; 39 h->bops->getcomm = PetscObjectGetComm_Petsc; 40 h->bops->compose = PetscObjectCompose_Petsc; 41 h->bops->query = PetscObjectQuery_Petsc; 42 h->bops->composefunction = PetscObjectComposeFunction_Petsc; 43 h->bops->queryfunction = PetscObjectQueryFunction_Petsc; 44 ierr = PetscCommDuplicate(comm,&h->comm,&h->tag);CHKERRQ(ierr); 45 PetscFunctionReturn(0); 46 } 47 48 extern PetscTruth PetscMemoryCollectMaximumUsage; 49 extern PetscLogDouble PetscMemoryMaximumUsage; 50 51 #undef __FUNCT__ 52 #define __FUNCT__ "PetscHeaderDestroy_Private" 53 /* 54 PetscHeaderDestroy_Private - Destroys a base PETSc object header. Called by 55 the macro PetscHeaderDestroy(). 56 */ 57 PetscErrorCode PETSC_DLLEXPORT PetscHeaderDestroy_Private(PetscObject h) 58 { 59 PetscErrorCode ierr; 60 61 PetscFunctionBegin; 62 if (PetscMemoryCollectMaximumUsage) { 63 PetscLogDouble usage; 64 ierr = PetscMemoryGetCurrentUsage(&usage);CHKERRQ(ierr); 65 if (usage > PetscMemoryMaximumUsage) PetscMemoryMaximumUsage = usage; 66 } 67 ierr = PetscCommDestroy(&h->comm);CHKERRQ(ierr); 68 ierr = PetscFree(h->bops);CHKERRQ(ierr); 69 ierr = PetscFree(h->ops);CHKERRQ(ierr); 70 ierr = PetscOListDestroy(&h->olist);CHKERRQ(ierr); 71 ierr = PetscFListDestroy(&h->qlist);CHKERRQ(ierr); 72 ierr = PetscStrfree(h->type_name);CHKERRQ(ierr); 73 ierr = PetscStrfree(h->name);CHKERRQ(ierr); 74 h->cookie = PETSCFREEDHEADER; 75 ierr = PetscStrfree(h->prefix);CHKERRQ(ierr); 76 if (h->fortran_func_pointers) { 77 ierr = PetscFree(h->fortran_func_pointers);CHKERRQ(ierr); 78 } 79 if (h->intcomposeddata) { 80 ierr = PetscFree(h->intcomposeddata);CHKERRQ(ierr); 81 } 82 if (h->intcomposedstate) { 83 ierr = PetscFree(h->intcomposedstate);CHKERRQ(ierr); 84 } 85 if (h->realcomposeddata) { 86 ierr = PetscFree(h->realcomposeddata);CHKERRQ(ierr); 87 } 88 if (h->realcomposedstate) { 89 ierr = PetscFree(h->realcomposedstate);CHKERRQ(ierr); 90 } 91 if (h->scalarcomposeddata) { 92 ierr = PetscFree(h->scalarcomposeddata);CHKERRQ(ierr); 93 } 94 if (h->scalarcomposedstate) { 95 ierr = PetscFree(h->scalarcomposedstate);CHKERRQ(ierr); 96 } 97 PetscFunctionReturn(0); 98 } 99 100 #undef __FUNCT__ 101 #define __FUNCT__ "PetscObjectReference" 102 /*@C 103 PetscObjectReference - Indicates to any PetscObject that it is being 104 referenced by another PetscObject. This increases the reference 105 count for that object by one. 106 107 Collective on PetscObject 108 109 Input Parameter: 110 . obj - the PETSc object. This must be cast with (PetscObject), for example, 111 PetscObjectReference((PetscObject)mat); 112 113 Level: advanced 114 115 .seealso: PetscObjectCompose(), PetscObjectDereference() 116 @*/ 117 PetscErrorCode PETSC_DLLEXPORT PetscObjectReference(PetscObject obj) 118 { 119 PetscFunctionBegin; 120 PetscValidHeader(obj,1); 121 obj->refct++; 122 PetscFunctionReturn(0); 123 } 124 125 #undef __FUNCT__ 126 #define __FUNCT__ "PetscObjectGetReference" 127 /*@C 128 PetscObjectGetReference - Gets the current reference count for 129 any PETSc object. 130 131 Not Collective 132 133 Input Parameter: 134 . obj - the PETSc object; this must be cast with (PetscObject), for example, 135 PetscObjectGetReference((PetscObject)mat,&cnt); 136 137 Output Parameter: 138 . cnt - the reference count 139 140 Level: advanced 141 142 .seealso: PetscObjectCompose(), PetscObjectDereference(), PetscObjectReference() 143 @*/ 144 PetscErrorCode PETSC_DLLEXPORT PetscObjectGetReference(PetscObject obj,PetscInt *cnt) 145 { 146 PetscFunctionBegin; 147 PetscValidHeader(obj,1); 148 PetscValidIntPointer(cnt,2); 149 *cnt = obj->refct; 150 PetscFunctionReturn(0); 151 } 152 153 #undef __FUNCT__ 154 #define __FUNCT__ "PetscObjectDereference" 155 /*@ 156 PetscObjectDereference - Indicates to any PetscObject that it is being 157 referenced by one less PetscObject. This decreases the reference 158 count for that object by one. 159 160 Collective on PetscObject 161 162 Input Parameter: 163 . obj - the PETSc object; this must be cast with (PetscObject), for example, 164 PetscObjectDereference((PetscObject)mat); 165 166 Level: advanced 167 168 .seealso: PetscObjectCompose(), PetscObjectReference() 169 @*/ 170 PetscErrorCode PETSC_DLLEXPORT PetscObjectDereference(PetscObject obj) 171 { 172 PetscErrorCode ierr; 173 174 PetscFunctionBegin; 175 PetscValidHeader(obj,1); 176 if (obj->bops->destroy) { 177 ierr = (*obj->bops->destroy)(obj);CHKERRQ(ierr); 178 } else if (!--obj->refct) { 179 SETERRQ(PETSC_ERR_SUP,"This PETSc object does not have a generic destroy routine"); 180 } 181 PetscFunctionReturn(0); 182 } 183 184 /* ----------------------------------------------------------------------- */ 185 /* 186 The following routines are the versions private to the PETSc object 187 data structures. 188 */ 189 #undef __FUNCT__ 190 #define __FUNCT__ "PetscObjectGetComm_Petsc" 191 PetscErrorCode PetscObjectGetComm_Petsc(PetscObject obj,MPI_Comm *comm) 192 { 193 PetscFunctionBegin; 194 *comm = obj->comm; 195 PetscFunctionReturn(0); 196 } 197 198 #undef __FUNCT__ 199 #define __FUNCT__ "PetscObjectCompose_Petsc" 200 PetscErrorCode PetscObjectCompose_Petsc(PetscObject obj,const char name[],PetscObject ptr) 201 { 202 PetscErrorCode ierr; 203 char *tname; 204 205 PetscFunctionBegin; 206 if (ptr) { 207 ierr = PetscOListReverseFind(ptr->olist,obj,&tname);CHKERRQ(ierr); 208 if (tname){ 209 SETERRQ(PETSC_ERR_ARG_INCOMP,"An object cannot be composed with an object that was compose with it"); 210 } 211 } 212 ierr = PetscOListAdd(&obj->olist,name,ptr);CHKERRQ(ierr); 213 PetscFunctionReturn(0); 214 } 215 216 #undef __FUNCT__ 217 #define __FUNCT__ "PetscObjectQuery_Petsc" 218 PetscErrorCode PetscObjectQuery_Petsc(PetscObject obj,const char name[],PetscObject *ptr) 219 { 220 PetscErrorCode ierr; 221 222 PetscFunctionBegin; 223 ierr = PetscOListFind(obj->olist,name,ptr);CHKERRQ(ierr); 224 PetscFunctionReturn(0); 225 } 226 227 #undef __FUNCT__ 228 #define __FUNCT__ "PetscObjectComposeFunction_Petsc" 229 PetscErrorCode PetscObjectComposeFunction_Petsc(PetscObject obj,const char name[],const char fname[],void (*ptr)(void)) 230 { 231 PetscErrorCode ierr; 232 233 PetscFunctionBegin; 234 ierr = PetscFListAdd(&obj->qlist,name,fname,ptr);CHKERRQ(ierr); 235 PetscFunctionReturn(0); 236 } 237 238 #undef __FUNCT__ 239 #define __FUNCT__ "PetscObjectQueryFunction_Petsc" 240 PetscErrorCode PetscObjectQueryFunction_Petsc(PetscObject obj,const char name[],void (**ptr)(void)) 241 { 242 PetscErrorCode ierr; 243 244 PetscFunctionBegin; 245 ierr = PetscFListFind(obj->comm,obj->qlist,name,ptr);CHKERRQ(ierr); 246 PetscFunctionReturn(0); 247 } 248 249 /* 250 These are the versions that are usable to any CCA compliant objects 251 */ 252 #undef __FUNCT__ 253 #define __FUNCT__ "PetscObjectCompose" 254 /*@C 255 PetscObjectCompose - Associates another PETSc object with a given PETSc object. 256 257 Not Collective 258 259 Input Parameters: 260 + obj - the PETSc object; this must be cast with (PetscObject), for example, 261 PetscObjectCompose((PetscObject)mat,...); 262 . name - name associated with the child object 263 - ptr - the other PETSc object to associate with the PETSc object; this must also be 264 cast with (PetscObject) 265 266 Level: advanced 267 268 Notes: 269 The second objects reference count is automatically increased by one when it is 270 composed. 271 272 Replaces any previous object that had the same name. 273 274 If ptr is null and name has previously been composed using an object, then that 275 entry is removed from the obj. 276 277 PetscObjectCompose() can be used with any PETSc object (such as 278 Mat, Vec, KSP, SNES, etc.) or any user-provided object. See 279 PetscObjectContainerCreate() for info on how to create an object from a 280 user-provided pointer that may then be composed with PETSc objects. 281 282 Concepts: objects^composing 283 Concepts: composing objects 284 285 .seealso: PetscObjectQuery(), PetscObjectContainerCreate() 286 @*/ 287 PetscErrorCode PETSC_DLLEXPORT PetscObjectCompose(PetscObject obj,const char name[],PetscObject ptr) 288 { 289 PetscErrorCode ierr; 290 291 PetscFunctionBegin; 292 ierr = (*obj->bops->compose)(obj,name,ptr);CHKERRQ(ierr); 293 PetscFunctionReturn(0); 294 } 295 296 #undef __FUNCT__ 297 #define __FUNCT__ "PetscObjectQuery" 298 /*@C 299 PetscObjectQuery - Gets a PETSc object associated with a given object. 300 301 Not Collective 302 303 Input Parameters: 304 + obj - the PETSc object 305 Thus must be cast with a (PetscObject), for example, 306 PetscObjectCompose((PetscObject)mat,...); 307 . name - name associated with child object 308 - ptr - the other PETSc object associated with the PETSc object, this must also be 309 cast with (PetscObject) 310 311 Level: advanced 312 313 Concepts: objects^composing 314 Concepts: composing objects 315 Concepts: objects^querying 316 Concepts: querying objects 317 318 .seealso: PetscObjectQuery() 319 @*/ 320 PetscErrorCode PETSC_DLLEXPORT PetscObjectQuery(PetscObject obj,const char name[],PetscObject *ptr) 321 { 322 PetscErrorCode ierr; 323 324 PetscFunctionBegin; 325 ierr = (*obj->bops->query)(obj,name,ptr);CHKERRQ(ierr); 326 PetscFunctionReturn(0); 327 } 328 329 #undef __FUNCT__ 330 #define __FUNCT__ "PetscObjectComposeFunction" 331 PetscErrorCode PETSC_DLLEXPORT PetscObjectComposeFunction(PetscObject obj,const char name[],const char fname[],void (*ptr)(void)) 332 { 333 PetscErrorCode ierr; 334 335 PetscFunctionBegin; 336 ierr = (*obj->bops->composefunction)(obj,name,fname,ptr);CHKERRQ(ierr); 337 PetscFunctionReturn(0); 338 } 339 340 #undef __FUNCT__ 341 #define __FUNCT__ "PetscObjectQueryFunction" 342 /*@C 343 PetscObjectQueryFunction - Gets a function associated with a given object. 344 345 Collective on PetscObject 346 347 Input Parameters: 348 + obj - the PETSc object; this must be cast with (PetscObject), for example, 349 PetscObjectQueryFunction((PetscObject)ksp,...); 350 - name - name associated with the child function 351 352 Output Parameter: 353 . ptr - function pointer 354 355 Level: advanced 356 357 Concepts: objects^composing functions 358 Concepts: composing functions 359 Concepts: functions^querying 360 Concepts: objects^querying 361 Concepts: querying objects 362 363 .seealso: PetscObjectComposeFunctionDynamic() 364 @*/ 365 PetscErrorCode PETSC_DLLEXPORT PetscObjectQueryFunction(PetscObject obj,const char name[],void (**ptr)(void)) 366 { 367 PetscErrorCode ierr; 368 369 PetscFunctionBegin; 370 ierr = (*obj->bops->queryfunction)(obj,name,ptr);CHKERRQ(ierr); 371 PetscFunctionReturn(0); 372 } 373 374 struct _p_PetscObjectContainer { 375 PETSCHEADER(int); 376 void *ptr; 377 PetscErrorCode (*userdestroy)(void*); 378 }; 379 380 #undef __FUNCT__ 381 #define __FUNCT__ "PetscObjectContainerGetPointer" 382 /*@C 383 PetscObjectContainerGetPointer - Gets the pointer value contained in the container. 384 385 Collective on PetscObjectContainer 386 387 Input Parameter: 388 . obj - the object created with PetscObjectContainerCreate() 389 390 Output Parameter: 391 . ptr - the pointer value 392 393 Level: advanced 394 395 .seealso: PetscObjectContainerCreate(), PetscObjectContainerDestroy(), 396 PetscObjectContainerSetPointer() 397 @*/ 398 PetscErrorCode PETSC_DLLEXPORT PetscObjectContainerGetPointer(PetscObjectContainer obj,void **ptr) 399 { 400 PetscFunctionBegin; 401 *ptr = obj->ptr; 402 PetscFunctionReturn(0); 403 } 404 405 406 #undef __FUNCT__ 407 #define __FUNCT__ "PetscObjectContainerSetPointer" 408 /*@C 409 PetscObjectContainerSetPointer - Sets the pointer value contained in the container. 410 411 Collective on PetscObjectContainer 412 413 Input Parameters: 414 + obj - the object created with PetscObjectContainerCreate() 415 - ptr - the pointer value 416 417 Level: advanced 418 419 .seealso: PetscObjectContainerCreate(), PetscObjectContainerDestroy(), 420 PetscObjectContainerGetPointer() 421 @*/ 422 PetscErrorCode PETSC_DLLEXPORT PetscObjectContainerSetPointer(PetscObjectContainer obj,void *ptr) 423 { 424 PetscFunctionBegin; 425 obj->ptr = ptr; 426 PetscFunctionReturn(0); 427 } 428 429 #undef __FUNCT__ 430 #define __FUNCT__ "PetscObjectContainerDestroy" 431 /*@C 432 PetscObjectContainerDestroy - Destroys a PETSc container object. 433 434 Collective on PetscObjectContainer 435 436 Input Parameter: 437 . obj - an object that was created with PetscObjectContainerCreate() 438 439 Level: advanced 440 441 .seealso: PetscObjectContainerCreate() 442 @*/ 443 PetscErrorCode PETSC_DLLEXPORT PetscObjectContainerDestroy(PetscObjectContainer obj) 444 { 445 PetscErrorCode ierr; 446 PetscFunctionBegin; 447 if (--obj->refct > 0) PetscFunctionReturn(0); 448 if (obj->userdestroy) (*obj->userdestroy)(obj->ptr); 449 ierr = PetscHeaderDestroy(obj);CHKERRQ(ierr); 450 PetscFunctionReturn(0); 451 } 452 453 #undef __FUNCT__ 454 #define __FUNCT__ "PetscObjectContainerSetUserDestroy" 455 /*@C 456 PetscObjectContainerSetUserDestroy - Sets name of the user destroy function. 457 458 Collective on PetscObjectContainer 459 460 Input Parameter: 461 + obj - an object that was created with PetscObjectContainerCreate() 462 - des - name of the user destroy function 463 464 Level: advanced 465 466 .seealso: PetscObjectContainerDestroy() 467 @*/ 468 PetscErrorCode PETSC_DLLEXPORT PetscObjectContainerSetUserDestroy(PetscObjectContainer obj, PetscErrorCode (*des)(void*)) 469 { 470 PetscFunctionBegin; 471 obj->userdestroy = des; 472 PetscFunctionReturn(0); 473 } 474 475 PetscCookie PETSC_DLLEXPORT CONTAINER_COOKIE = 0; 476 477 #undef __FUNCT__ 478 #define __FUNCT__ "PetscObjectContainerCreate" 479 /*@C 480 PetscObjectContainerCreate - Creates a PETSc object that has room to hold 481 a single pointer. This allows one to attach any type of data (accessible 482 through a pointer) with the PetscObjectCompose() function to a PetscObject. 483 The data item itself is attached by a call to PetscObjectContainerSetPointer. 484 485 Collective on MPI_Comm 486 487 Input Parameters: 488 . comm - MPI communicator that shares the object 489 490 Output Parameters: 491 . container - the container created 492 493 Level: advanced 494 495 .seealso: PetscObjectContainerDestroy(), PetscObjectContainerSetPointer(), PetscObjectContainerGetPointer() 496 @*/ 497 PetscErrorCode PETSC_DLLEXPORT PetscObjectContainerCreate(MPI_Comm comm,PetscObjectContainer *container) 498 { 499 PetscErrorCode ierr; 500 PetscObjectContainer contain; 501 502 PetscFunctionBegin; 503 if (!CONTAINER_COOKIE) { 504 ierr = PetscLogClassRegister(&CONTAINER_COOKIE, "Container");CHKERRQ(ierr); 505 } 506 ierr = PetscHeaderCreate(contain,_p_PetscObjectContainer,PetscInt,CONTAINER_COOKIE,0,"container",comm,PetscObjectContainerDestroy,0);CHKERRQ(ierr); 507 *container = contain; 508 PetscFunctionReturn(0); 509 } 510 511 #undef __FUNCT__ 512 #define __FUNCT__ "PetscObjectSetFromOptions" 513 /*@ 514 PetscObjectSetFromOptions - Sets generic parameters from user options. 515 516 Collective on obj 517 518 Input Parameter: 519 . obj - the PetscObjcet 520 521 Options Database Keys: 522 523 Notes: 524 We have no generic options at present, so this does nothing 525 526 Level: beginner 527 528 .keywords: set, options, database 529 .seealso: PetscObjectSetOptionsPrefix(), PetscObjectGetOptionsPrefix() 530 @*/ 531 PetscErrorCode PETSC_DLLEXPORT PetscObjectSetFromOptions(PetscObject obj) 532 { 533 PetscFunctionBegin; 534 if (!obj) SETERRQ(PETSC_ERR_ARG_CORRUPT, "Null object"); 535 PetscFunctionReturn(0); 536 } 537 538 #undef __FUNCT__ 539 #define __FUNCT__ "PetscObjectSetUp" 540 /*@ 541 PetscObjectSetUp - Sets up the internal data structures for the later use. 542 543 Collective on PetscObject 544 545 Input Parameters: 546 . obj - the PetscObject 547 548 Notes: 549 This does nothing at present. 550 551 Level: advanced 552 553 .keywords: setup 554 .seealso: PetscObjectDestroy() 555 @*/ 556 PetscErrorCode PETSC_DLLEXPORT PetscObjectSetUp(PetscObject obj) 557 { 558 PetscFunctionBegin; 559 if (!obj) SETERRQ(PETSC_ERR_ARG_CORRUPT, "Null object"); 560 PetscFunctionReturn(0); 561 } 562