Actual source code: bag.c

  1: #define PETSC_DLL

 3:  #include petsc.h
 4:  #include petscsys.h
 5:  #include src/sys/bag/bagimpl.h

  7: /*
  8:    Ugly variable to indicate if we are inside a PetscBagLoad() and should not call PetscOptions....
  9: */
 10: static PetscTruth PetscBagInLoad = PETSC_FALSE;

 14: /*
 15:       Adds item to the linked list in a bag
 16: */
 17: static PetscErrorCode PetscBagRegister_Private(PetscBag bag,PetscBagItem item,const char*name,const char*help)
 18: {

 22:   item->freelist = PETSC_FALSE;
 23:   PetscStrncpy(item->name,name,PETSC_BAG_NAME_LENGTH-1);
 24:   PetscStrncpy(item->help,help,PETSC_BAG_HELP_LENGTH-1);
 25:   if (!bag->bagitems) bag->bagitems = item;
 26:   else {
 27:     PetscBagItem nitem = bag->bagitems;
 28:     while (nitem->next) {
 29:       nitem = nitem->next;
 30:     }
 31:     nitem->next = item;
 32:   }
 33:   bag->count++;
 34:   return(0);
 35: }

 39: /*@C
 40:    PetscBagRegisterEnum - add an enum value to the bag

 42:    Collective on PetscBag

 44:    Input Parameter:
 45: +  bag - the bag of values
 46: .  addr - location of enum in struct
 47: .  mdefault - the initial value
 48: .  list - array of strings containing names of enum values followed by enum name followed by enum prefix
 49: -  help - longer string with more information about the value

 51:    Level: beginner

 53: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
 54:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
 55:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName()

 57: @*/
 58: PetscErrorCode PetscBagRegisterEnum(PetscBag bag,void *addr,const char **list,PetscEnum mdefault, const char *name, const char* help)
 59: {
 61:   PetscBagItem   item;
 62:   char           nname[PETSC_BAG_NAME_LENGTH+1];
 63:   PetscTruth     printhelp;
 64:   PetscInt       i = 0;

 67:   if (!PetscBagInLoad) {
 68:     nname[0] = '-';
 69:     nname[1] = 0;
 70:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
 71:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
 72:     if (printhelp) {
 73:       while (list[i++]);
 74:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%s>: (%s) %s (choose one of) ",nname,list[mdefault],list[i-3],help);
 75:       for (i=0; list[i+2]; i++){
 76:         (*PetscHelpPrintf)(bag->bagcomm," %s",list[i]);
 77:       }
 78:       (*PetscHelpPrintf)(bag->bagcomm,"\n");
 79:     }
 80:     PetscOptionsGetEnum(PETSC_NULL,nname,list,&mdefault,PETSC_NULL);
 81:   }

 83:   PetscNew(struct _n_PetscBagItem,&item);
 84:   item->dtype  = PETSC_ENUM;
 85:   item->offset = ((char*)addr) - ((char*)bag);
 86:   item->next   = 0;
 87:   item->msize  = 1;
 88:   item->list   = list;
 89:   *(PetscEnum*)addr = mdefault;
 90:   PetscBagRegister_Private(bag,item,name,help);
 91:   return(0);
 92: }

 96: /*@C
 97:    PetscBagRegisterInt - add an integer value to the bag

 99:    Collective on PetscBag

101:    Input Parameter:
102: +  bag - the bag of values
103: .  addr - location of integer in struct
104: .  mdefault - the initial value
105: .  name - name of the integer
106: -  help - longer string with more information about the value

108:    Level: beginner

110: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
111:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
112:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

114: @*/
115: PetscErrorCode PetscBagRegisterInt(PetscBag bag,void *addr,PetscInt mdefault, const char* name, const char* help)
116: {
118:   PetscBagItem   item;
119:   char           nname[PETSC_BAG_NAME_LENGTH+1];
120:   PetscTruth     printhelp;

123:   if (!PetscBagInLoad) {
124:     nname[0] = '-';
125:     nname[1] = 0;
126:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
127:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
128:     if (printhelp) {
129:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%d>: %s \n",nname,mdefault,help);
130:     }
131:     PetscOptionsGetInt(PETSC_NULL,nname,&mdefault,PETSC_NULL);
132:   }

134:   PetscNew(struct _n_PetscBagItem,&item);
135:   item->dtype  = PETSC_INT;
136:   item->offset = ((char*)addr) - ((char*)bag);
137:   item->next   = 0;
138:   item->msize  = 1;
139:   *(PetscInt*)addr = mdefault;
140:   PetscBagRegister_Private(bag,item,name,help);
141:   return(0);
142: }

146: /*@C
147:    PetscBagRegisterString - add a string value to the bag

149:    Collective on PetscBag

151:    Input Parameter:
152: +  bag - the bag of values
153: .  addr - location of start of string in struct
154: .  msize - length of the string space in the struct
155: .  mdefault - the initial value
156: .  name - name of the string
157: -  help - longer string with more information about the value

159:    Level: beginner

161:    Note: The struct should have the field char mystring[msize]; not char *mystring

163: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
164:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
165:            PetscBagSetFromOptions(),PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

167: @*/
168: PetscErrorCode PetscBagRegisterString(PetscBag bag,void *addr,PetscInt msize,const char* mdefault, const char* name, const char* help)
169: {
171:   PetscBagItem   item;
172:   char           nname[PETSC_BAG_NAME_LENGTH+1];
173:   PetscTruth     printhelp;

176:   if (!PetscBagInLoad) {
177:     nname[0] = '-';
178:     nname[1] = 0;
179:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
180:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
181:     if (printhelp) {
182:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%s>: %s \n",nname,mdefault,help);
183:     }
184:   }

186:   PetscNew(struct _n_PetscBagItem,&item);
187:   item->dtype  = PETSC_CHAR;
188:   item->offset = ((char*)addr) - ((char*)bag);
189:   item->next   = 0;
190:   item->msize  = msize;
191:   if (mdefault != (char*)addr) {
192:     PetscStrncpy((char*)addr,mdefault,msize-1);
193:   }
194:   if (!PetscBagInLoad) {
195:     PetscOptionsGetString(PETSC_NULL,nname,(char*)addr,msize,PETSC_NULL);
196:   }
197:   PetscBagRegister_Private(bag,item,name,help);
198:   return(0);
199: }

203: /*@C
204:    PetscBagRegisterReal - add a real value to the bag

206:    Collective on PetscBag

208:    Input Parameter:
209: +  bag - the bag of values
210: .  addr - location of double in struct
211: .  mdefault - the initial value
212: .  name - name of the variable
213: -  help - longer string with more information about the value

215:    Level: beginner

217: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
218:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
219:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

221: @*/
222: PetscErrorCode PetscBagRegisterReal(PetscBag bag,void *addr,PetscReal mdefault, const char* name, const char* help)
223: {
225:   PetscBagItem   item;
226:   char           nname[PETSC_BAG_NAME_LENGTH+1];
227:   PetscTruth     printhelp;

230:   if (!PetscBagInLoad) {
231:     nname[0] = '-';
232:     nname[1] = 0;
233:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
234:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
235:     if (printhelp) {
236:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%G>: %s \n",nname,mdefault,help);
237:     }
238:     PetscOptionsGetReal(PETSC_NULL,nname,&mdefault,PETSC_NULL);
239:   }

241:   PetscNew(struct _n_PetscBagItem,&item);
242:   item->dtype  = PETSC_REAL;
243:   item->offset = ((char*)addr) - ((char*)bag);
244:   item->next   = 0;
245:   item->msize  = 1;
246:   *(PetscReal*)addr = mdefault;
247:   PetscBagRegister_Private(bag,item,name,help);
248:   return(0);
249: }

253: /*@C
254:    PetscBagRegisterScalar - add a real value to the bag

256:    Collective on PetscBag

258:    Input Parameter:
259: +  bag - the bag of values
260: .  addr - location of scalar in struct
261: .  mdefault - the initial value
262: .  name - name of the variable
263: -  help - longer string with more information about the value


266:    Level: beginner

268: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
269:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
270:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

272: @*/
273: PetscErrorCode PetscBagRegisterScalar(PetscBag bag,void *addr,PetscScalar mdefault, const char* name, const char* help)
274: {
276:   PetscBagItem   item;
277:   char           nname[PETSC_BAG_NAME_LENGTH+1];
278:   PetscTruth     printhelp;

281:   if (!PetscBagInLoad) {
282:     nname[0] = '-';
283:     nname[1] = 0;
284:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
285:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
286:     if (printhelp) {
287:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%G + %Gi>: %s \n",nname,PetscRealPart(mdefault),PetscImaginaryPart(mdefault),help);
288:     }
289:     PetscOptionsGetScalar(PETSC_NULL,nname,&mdefault,PETSC_NULL);
290:   }

292:   PetscNew(struct _n_PetscBagItem,&item);
293:   item->dtype  = PETSC_SCALAR;
294:   item->offset = ((char*)addr) - ((char*)bag);
295:   item->next   = 0;
296:   item->msize  = 1;
297:   *(PetscScalar*)addr = mdefault;
298:   PetscBagRegister_Private(bag,item,name,help);
299:   return(0);
300: }

304: /*@C
305:    PetscBagRegisterTruth - add a logical value to the bag

307:    Collective on PetscBag

309:    Input Parameter:
310: +  bag - the bag of values
311: .  addr - location of logical in struct
312: .  mdefault - the initial value
313: .  name - name of the variable
314: -  help - longer string with more information about the value


317:    Level: beginner

319: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
320:            PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
321:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

323: @*/
324: PetscErrorCode PetscBagRegisterTruth(PetscBag bag,void *addr,PetscTruth mdefault, const char* name, const char* help)
325: {
327:   PetscBagItem   item;
328:   char           nname[PETSC_BAG_NAME_LENGTH+1];
329:   PetscTruth     printhelp;

332:   if (!PetscBagInLoad) {
333:     nname[0] = '-';
334:     nname[1] = 0;
335:     PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
336:     PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
337:     if (printhelp) {
338:       (*PetscHelpPrintf)(bag->bagcomm,"  %s <%s>: %s \n",nname,PetscTruths[mdefault],help);
339:     }
340:     PetscOptionsGetTruth(PETSC_NULL,nname,&mdefault,PETSC_NULL);
341:   }

343:   PetscNew(struct _n_PetscBagItem,&item);
344:   item->dtype  = PETSC_TRUTH;
345:   item->offset = ((char*)addr) - ((char*)bag);
346:   item->next   = 0;
347:   item->msize  = 1;
348:   *(PetscTruth*)addr = mdefault;
349:   PetscBagRegister_Private(bag,item,name,help);
350:   return(0);
351: }

355: /*@C
356:    PetscBagDestroy - Destroys a bag values

358:    Collective on PetscBag

360:    Input Parameter:
361: .  bag - the bag of values

363:    Level: beginner

365: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
366:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
367:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

369: @*/
370: PetscErrorCode  PetscBagDestroy(PetscBag bag)
371: {
373:   PetscBagItem   nitem = bag->bagitems,item;

376:   while (nitem) {
377:     item  = nitem->next;
378:     if (nitem->freelist) {
379:       void *v = (void*)nitem->list;
380:       PetscFree(v);
381:     }
382:     PetscFree(nitem);
383:     nitem = item;
384:   }
385:   PetscFree(bag);
386:   return(0);
387: }

391: /*@C
392:    PetscBagSetFromOptions - Allows setting options from a bag

394:    Collective on PetscBag

396:    Input Parameter:
397: .  bag - the bag of values

399:    Level: beginner

401: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagLoad(), PetscBagGetData()
402:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
403:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagView(), PetscBagRegisterEnum()

405: @*/
406: PetscErrorCode  PetscBagSetFromOptions(PetscBag bag)
407: {
409:   PetscBagItem   nitem = bag->bagitems;
410:   char           name[PETSC_BAG_NAME_LENGTH+1],helpname[PETSC_BAG_NAME_LENGTH+PETSC_BAG_HELP_LENGTH+3];
411: 
413:   PetscStrcpy(helpname,bag->bagname);
414:   PetscStrcat(helpname," ");
415:   PetscStrcat(helpname,bag->baghelp);
416:   PetscOptionsBegin(bag->bagcomm,PETSC_NULL,helpname,0);
417:     while (nitem) {
418:       name[0] = '-';
419:       name[1] = 0;
420:       PetscStrcat(name,nitem->name);
421:       if (nitem->dtype == PETSC_CHAR) { /* special handling for fortran required? [due to space padding vs null termination] */
422:         char *value = (char*)(((char*)bag) + nitem->offset);
423:         PetscOptionsString(name,nitem->help,"",value,value,nitem->msize,PETSC_NULL);
424:       } else if (nitem->dtype == PETSC_REAL) {
425:         PetscReal *value = (PetscReal*)(((char*)bag) + nitem->offset);
426:         PetscOptionsReal(name,nitem->help,"",*value,value,PETSC_NULL);
427:       } else if (nitem->dtype == PETSC_SCALAR) {
428:         PetscScalar *value = (PetscScalar*)(((char*)bag) + nitem->offset);
429:         PetscOptionsScalar(name,nitem->help,"",*value,value,PETSC_NULL);
430:       } else if (nitem->dtype == PETSC_INT) {
431:         PetscInt *value = (PetscInt*)(((char*)bag) + nitem->offset);
432:         PetscOptionsInt(name,nitem->help,"",*value,value,PETSC_NULL);
433:       } else if (nitem->dtype == PETSC_ENUM) {
434:         PetscEnum *value = (PetscEnum*)(((char*)bag) + nitem->offset);
435:         PetscInt  i = 0;
436:         while (nitem->list[i++]);
437:         PetscOptionsEnum(name,nitem->help,nitem->list[i-3],nitem->list,*value,value,PETSC_NULL);
438:       } else if (nitem->dtype == PETSC_TRUTH) {
439:         PetscTruth *value = (PetscTruth*)(((char*)bag) + nitem->offset);
440:         PetscOptionsTruth(name,nitem->help,"",*value,value,PETSC_NULL);
441:       }
442:       nitem = nitem->next;
443:     }
444:   PetscOptionsEnd();
445:   return(0);
446: }

450: /*@C
451:    PetscBagView - Views a bag of values as either ASCII text or a binary file

453:    Collective on PetscBag

455:    Input Parameter:
456: +  bag - the bag of values
457: -  viewer - location to view the values

459:    Level: beginner

461:    Warning: Currently PETSc bags saved in a binary file can only be read back
462:      in on a machine of the same architecture. Let us know when this is a problem
463:      and we'll fix it.

465: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagLoad(), PetscBagGetData()
466:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar(), PetscBagRegisterEnum()
467:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName()

469: @*/
470: PetscErrorCode  PetscBagView(PetscBag bag,PetscViewer view)
471: {
472:   PetscTruth     isascii,isbinary;
474:   PetscBagItem   nitem = bag->bagitems;
475: 
477:   PetscTypeCompare((PetscObject)view,PETSC_VIEWER_ASCII,&isascii);
478:   PetscTypeCompare((PetscObject)view,PETSC_VIEWER_BINARY,&isbinary);
479:   if (isascii) {
480:     PetscViewerASCIIPrintf(view,"PetscBag Object:  %s %s\n",bag->bagname,bag->baghelp);
481:     while (nitem) {
482:       if (nitem->dtype == PETSC_CHAR) {
483:         char* value = (char*)(((char*)bag) + nitem->offset);
484:         char tmp = value[nitem->msize-1];  /* special handling for fortran chars wihout null terminator */
485:         value[nitem->msize-1] =0;
486:         PetscViewerASCIIPrintf(view,"  %s = %s; %s\n",nitem->name,value,nitem->help);
487:         value[nitem->msize-1] =tmp;
488:       } else if (nitem->dtype == PETSC_REAL) {
489:         PetscReal value = *(PetscReal*)(((char*)bag) + nitem->offset);
490:         PetscViewerASCIIPrintf(view,"  %s = %G; %s\n",nitem->name,value,nitem->help);
491:       } else if (nitem->dtype == PETSC_SCALAR) {
492:         PetscScalar value = *(PetscScalar*)(((char*)bag) + nitem->offset);
493: #if defined(PETSC_USE_COMPLEX)
494:         PetscViewerASCIIPrintf(view,"  %s = %G + %Gi; %s\n",nitem->name,PetscRealPart(value),PetscImaginaryPart(value),nitem->help);
495: #else
496:         PetscViewerASCIIPrintf(view,"  %s = %G; %s\n",nitem->name,value,nitem->help);
497: #endif
498:       } else if (nitem->dtype == PETSC_INT) {
499:         PetscInt value = *(PetscInt*)(((char*)bag) + nitem->offset);
500:         PetscViewerASCIIPrintf(view,"  %s = %D; %s\n",nitem->name,value,nitem->help);
501:       } else if (nitem->dtype == PETSC_TRUTH) {
502:         PetscTruth value = *(PetscTruth*)(((char*)bag) + nitem->offset);
503:         PetscViewerASCIIPrintf(view,"  %s = %s; %s\n",nitem->name,PetscTruths[value],nitem->help);
504:       } else if (nitem->dtype == PETSC_ENUM) {
505:         PetscEnum value = *(PetscEnum*)(((char*)bag) + nitem->offset);
506:         PetscInt  i = 0;
507:         while (nitem->list[i++]);
508:         PetscViewerASCIIPrintf(view,"  %s = %s; (%s) %s\n",nitem->name,nitem->list[value],nitem->list[i-3],nitem->help);
509:       }
510:       nitem = nitem->next;
511:     }
512:   } else if (isbinary) {
513:     PetscInt cookie = PETSC_BAG_FILE_COOKIE, bagsize = (PetscInt) bag->bagsize, dtype;
514:     PetscViewerBinaryWrite(view,&cookie,1,PETSC_INT,PETSC_TRUE);
515:     PetscViewerBinaryWrite(view,&bagsize,1,PETSC_INT,PETSC_TRUE);
516:     PetscViewerBinaryWrite(view,&bag->count,1,PETSC_INT,PETSC_FALSE);
517:     PetscViewerBinaryWrite(view,bag->bagname,PETSC_BAG_NAME_LENGTH,PETSC_CHAR,PETSC_FALSE);
518:     PetscViewerBinaryWrite(view,bag->baghelp,PETSC_BAG_HELP_LENGTH,PETSC_CHAR,PETSC_FALSE);
519:     while (nitem) {
520:       PetscViewerBinaryWrite(view,&nitem->offset,1,PETSC_INT,PETSC_FALSE);
521:       dtype = (PetscInt)nitem->dtype;
522:       PetscViewerBinaryWrite(view,&dtype,1,PETSC_INT,PETSC_FALSE);
523:       PetscViewerBinaryWrite(view,nitem->name,PETSC_BAG_NAME_LENGTH,PETSC_CHAR,PETSC_FALSE);
524:       PetscViewerBinaryWrite(view,nitem->help,PETSC_BAG_HELP_LENGTH,PETSC_CHAR,PETSC_FALSE);
525:       PetscViewerBinaryWrite(view,&nitem->msize,1,PETSC_INT,PETSC_FALSE);
526:       PetscViewerBinaryWrite(view,(((char*)bag) + nitem->offset),nitem->msize,nitem->dtype,PETSC_FALSE);
527:       if (dtype == PETSC_ENUM) {
528:         PetscViewerBinaryWriteStringArray(view,(char **)nitem->list);
529:       }
530:       nitem = nitem->next;
531:     }
532:   } else {
533:     SETERRQ(PETSC_ERR_SUP,"No support for this viewer type");
534:   }
535:   return(0);
536: }

540: /*@C
541:    PetscBagLoad - Loads a bag of values from a binary file

543:    Collective on PetscViewer

545:    Input Parameter:
546: .  viewer - file to load values from

548:    Output Parameter:
549: .  bag - the bag of values

551:    Level: beginner

553: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagView(), PetscBagGetData()
554:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
555:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()

557: @*/
558: PetscErrorCode  PetscBagLoad(PetscViewer view,PetscBag *bag)
559: {
561:   PetscTruth     isbinary,skipoptions;
562:   PetscInt       cookie,bagsizecount[2],i,offsetdtype[2],msize;
563:   char           name[PETSC_BAG_NAME_LENGTH],help[PETSC_BAG_HELP_LENGTH],**list;
564:   PetscBagItem   nitem;

567:   PetscTypeCompare((PetscObject)view,PETSC_VIEWER_BINARY,&isbinary);
568:   if (!isbinary) SETERRQ(PETSC_ERR_SUP,"No support for this viewer type");

570:   PetscViewerBinaryRead(view,&cookie,1,PETSC_INT);
571:   if (cookie != PETSC_BAG_FILE_COOKIE) SETERRQ(PETSC_ERR_ARG_WRONG,"Not PetscBag next in binary file");
572:   PetscViewerBinaryRead(view,bagsizecount,2,PETSC_INT);
573:   PetscMalloc(bagsizecount[0],bag);
574:   PetscMemzero(*bag,bagsizecount[0]);
575:   (*bag)->bagsize = bagsizecount[0];

577:   PetscViewerBinaryRead(view,(*bag)->bagname,PETSC_BAG_NAME_LENGTH,PETSC_CHAR);
578:   PetscViewerBinaryRead(view,(*bag)->baghelp,PETSC_BAG_HELP_LENGTH,PETSC_CHAR);

580:   PetscViewerBinaryGetSkipOptions(view,&skipoptions);
581:   if (skipoptions) PetscBagInLoad = PETSC_TRUE;

583:   for (i=0; i<bagsizecount[1]; i++) {
584:     PetscViewerBinaryRead(view,offsetdtype,2,PETSC_INT);
585:     PetscViewerBinaryRead(view,name,PETSC_BAG_NAME_LENGTH,PETSC_CHAR);
586:     PetscViewerBinaryRead(view,help,PETSC_BAG_HELP_LENGTH,PETSC_CHAR);
587:     PetscViewerBinaryRead(view,&msize,1,PETSC_INT);

589:     if (offsetdtype[1] == (PetscInt) PETSC_CHAR) {
590:       PetscViewerBinaryRead(view,((char*)(*bag))+offsetdtype[0],msize,PETSC_CHAR);
591:       PetscBagRegisterString(*bag,((char*)(*bag))+offsetdtype[0],msize,((char*)(*bag))+offsetdtype[0],name,help);
592:     } else if (offsetdtype[1] == (PetscInt) PETSC_REAL) {
593:       PetscReal mdefault;
594:       PetscViewerBinaryRead(view,&mdefault,1,PETSC_REAL);
595:       PetscBagRegisterReal(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
596:     } else if (offsetdtype[1] == (PetscInt) PETSC_SCALAR) {
597:       PetscScalar mdefault;
598:       PetscViewerBinaryRead(view,&mdefault,1,PETSC_SCALAR);
599:       PetscBagRegisterScalar(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
600:     } else if (offsetdtype[1] == (PetscInt) PETSC_INT) {
601:       PetscInt mdefault;
602:       PetscViewerBinaryRead(view,&mdefault,1,PETSC_INT);
603:       PetscBagRegisterInt(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
604:     } else if (offsetdtype[1] == (PetscInt) PETSC_TRUTH) {
605:       PetscTruth mdefault;
606:       PetscViewerBinaryRead(view,&mdefault,1,PETSC_TRUTH);
607:       PetscBagRegisterTruth(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
608:     } else if (offsetdtype[1] == (PetscInt) PETSC_ENUM) {
609:       PetscEnum mdefault;
610:       PetscViewerBinaryRead(view,&mdefault,1,PETSC_ENUM);
611:       PetscViewerBinaryReadStringArray(view,&list);
612:       PetscBagRegisterEnum(*bag,((char*)(*bag))+offsetdtype[0],(const char**)list,mdefault,name,help);
613:       /* we malloced list in PetscViewerBinaryReadStringArray() so must free ourselves */
614:       nitem = (*bag)->bagitems;
615:       while (nitem->next) nitem = nitem->next;
616:       nitem->freelist = PETSC_TRUE;
617:     }
618:   }
619:   PetscBagInLoad = PETSC_FALSE;
620:   return(0);
621: }

625: /*@C
626:     PetscBagCreate - Create a bag of values

628:   Collective on MPI_Comm

630:   Level: Intermediate

632:   Input Parameters:
633: +  comm - communicator to share bag
634: -  size - size of the C structure holding the values

636:   Output Parameter:
637: .   bag - the bag of values

639:    Notes:
640:       The size of the A struct must be small enough to fit in a PetscInt; by default
641:       PetscInt is 4 bytes. The warning about casting to a shorter length can be ignored
642:       below unless your A struct is too large

644: .seealso: PetscBag, PetscBagGetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
645:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
646:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
647: @*/
648: PetscErrorCode PetscBagCreate(MPI_Comm comm, size_t size, PetscBag *bag)
649: {
651:   size_t tsize;

654:   tsize = sizeof(struct _n_PetscBag)+size;
655:   PetscMalloc(tsize,bag);
656:   PetscMemzero(*bag,tsize);
657:   (*bag)->bagsize = tsize;
658:   (*bag)->bagcomm = comm;
659:   return(0);
660: }
661: 
664: /*@C
665:     PetscBagSetName - Sets the name of a bag of values

667:   Not Collective

669:   Level: Intermediate

671:   Input Parameters:
672: +   bag - the bag of values
673: .   name - the name assigned to the bag
674: -   help - help message for bag

676: .seealso: PetscBag, PetscBagGetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
677:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
678:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
679: @*/

681: PetscErrorCode PetscBagSetName(PetscBag bag, const char *name, const char *help)
682: {
685:   PetscStrncpy(bag->bagname,name,PETSC_BAG_NAME_LENGTH-1);
686:   PetscStrncpy(bag->baghelp,help,PETSC_BAG_HELP_LENGTH-1);
687:   return(0);
688: }

692: /*@C
693:     PetscBagGetName - Gets the name of a bag of values

695:   Not Collective

697:   Level: Intermediate

699:   Input Parameter:
700: .   bag - the bag of values

702:   Output Parameter:
703: .   name - the name assigned to the bag

705: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
706:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
707:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
708: @*/
709: PetscErrorCode PetscBagGetName(PetscBag bag, char **name)
710: {
712:   *name = bag->bagname;
713:   return(0);
714: }

716: /*@C
717:     PetscBagGetData - Gives back the user - access to memory that
718:     should be used for storing user-data-structure

720:   Not Collective

722:   Level: Intermediate

724:   Input Parameter:
725: .   bag - the bag of values

727:   Output Parameter:
728: .   data - pointer to memory that will have user-data-structure

730: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad()
731:            PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterTruth(), PetscBagRegisterScalar()
732:            PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
733: @*/
734: PetscErrorCode PetscBagGetData(PetscBag bag, void **data)
735: {
737:   *data = (char*)bag + sizeof(struct _n_PetscBag);
738:   return(0);
739: }