Actual source code: bag.c
2: #include <../src/sys/bag/bagimpl.h> /*I "petscbag.h" I*/
4: /*
5: Ugly variable to indicate if we are inside a PetscBagLoad() and should not call PetscOptions....
6: */
7: static PetscBool PetscBagInLoad = PETSC_FALSE;
11: /*
12: Adds item to the linked list in a bag
13: */
14: static PetscErrorCode PetscBagRegister_Private(PetscBag bag,PetscBagItem item,const char*name,const char*help)
15: {
19: item->freelist = PETSC_FALSE;
20: PetscStrncpy(item->name,name,PETSC_BAG_NAME_LENGTH-1);
21: PetscStrncpy(item->help,help,PETSC_BAG_HELP_LENGTH-1);
22: if (!bag->bagitems) bag->bagitems = item;
23: else {
24: PetscBagItem nitem = bag->bagitems;
25: while (nitem->next) {
26: nitem = nitem->next;
27: }
28: nitem->next = item;
29: }
30: bag->count++;
31: return(0);
32: }
36: /*@C
37: PetscBagRegisterEnum - add an enum value to the bag
39: Logically Collective on PetscBag
41: Input Parameter:
42: + bag - the bag of values
43: . addr - location of enum in struct
44: . mdefault - the initial value
45: . list - array of strings containing names of enum values followed by enum name followed by enum prefix
46: - help - longer string with more information about the value
48: Level: beginner
50: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
51: PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
52: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName()
54: @*/
55: PetscErrorCode PetscBagRegisterEnum(PetscBag bag,void *addr,const char **list,PetscEnum mdefault, const char *name, const char* help)
56: {
58: PetscBagItem item;
59: char nname[PETSC_BAG_NAME_LENGTH+1];
60: PetscBool printhelp;
61: PetscInt i = 0;
64: if (!PetscBagInLoad) {
65: nname[0] = '-';
66: nname[1] = 0;
67: PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
68: PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
69: if (printhelp) {
70: while (list[i++]);
71: (*PetscHelpPrintf)(bag->bagcomm," -%s%s <%s>: (%s) %s (choose one of) ",bag->bagprefix?bag->bagprefix:"",name,list[mdefault],list[i-3],help);
72: for (i=0; list[i+2]; i++){
73: (*PetscHelpPrintf)(bag->bagcomm," %s",list[i]);
74: }
75: (*PetscHelpPrintf)(bag->bagcomm,"\n");
76: }
77: PetscOptionsGetEnum(bag->bagprefix,nname,list,&mdefault,PETSC_NULL);
78: }
80: PetscNew(struct _n_PetscBagItem,&item);
81: item->dtype = PETSC_ENUM;
82: item->offset = ((char*)addr) - ((char*)bag);
83: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
84: item->next = 0;
85: item->msize = 1;
86: item->list = list;
87: *(PetscEnum*)addr = mdefault;
88: PetscBagRegister_Private(bag,item,name,help);
89: return(0);
90: }
94: /*@C
95: PetscBagRegisterInt - add an integer value to the bag
97: Logically Collective on PetscBag
99: Input Parameter:
100: + bag - the bag of values
101: . addr - location of integer in struct
102: . mdefault - the initial value
103: . name - name of the integer
104: - help - longer string with more information about the value
106: Level: beginner
108: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
109: PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
110: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
112: @*/
113: PetscErrorCode PetscBagRegisterInt(PetscBag bag,void *addr,PetscInt mdefault, const char* name, const char* help)
114: {
116: PetscBagItem item;
117: char nname[PETSC_BAG_NAME_LENGTH+1];
118: PetscBool printhelp;
121: if (!PetscBagInLoad) {
122: nname[0] = '-';
123: nname[1] = 0;
124: PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
125: PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
126: if (printhelp) {
127: (*PetscHelpPrintf)(bag->bagcomm," -%s%s <%d>: %s \n",bag->bagprefix?bag->bagprefix:"",name,mdefault,help);
128: }
129: PetscOptionsGetInt(bag->bagprefix,nname,&mdefault,PETSC_NULL);
130: }
132: PetscNew(struct _n_PetscBagItem,&item);
133: item->dtype = PETSC_INT;
134: item->offset = ((char*)addr) - ((char*)bag);
135: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
136: item->next = 0;
137: item->msize = 1;
138: *(PetscInt*)addr = mdefault;
139: PetscBagRegister_Private(bag,item,name,help);
140: return(0);
141: }
145: /*@C
146: PetscBagRegisterString - add a string value to the bag
148: Logically Collective on PetscBag
150: Input Parameter:
151: + bag - the bag of values
152: . addr - location of start of string in struct
153: . msize - length of the string space in the struct
154: . mdefault - the initial value
155: . name - name of the string
156: - help - longer string with more information about the value
158: Level: beginner
160: Note: The struct should have the field char mystring[msize]; not char *mystring
162: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
163: PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
164: PetscBagSetFromOptions(),PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
166: @*/
167: PetscErrorCode PetscBagRegisterString(PetscBag bag,void *addr,PetscInt msize,const char* mdefault, const char* name, const char* help)
168: {
170: PetscBagItem item;
171: char nname[PETSC_BAG_NAME_LENGTH+1];
172: PetscBool printhelp;
175: if (!PetscBagInLoad) {
176: nname[0] = '-';
177: nname[1] = 0;
178: PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
179: PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
180: if (printhelp) {
181: (*PetscHelpPrintf)(bag->bagcomm," -%s%s <%s>: %s \n",bag->bagprefix?bag->bagprefix:"",name,mdefault,help);
182: }
183: }
185: PetscNew(struct _n_PetscBagItem,&item);
186: item->dtype = PETSC_CHAR;
187: item->offset = ((char*)addr) - ((char*)bag);
188: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
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(bag->bagprefix,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: Logically 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(), PetscBagRegisterBool(), 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: PetscBool 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%s <%G>: %s \n",bag->bagprefix?bag->bagprefix:"",name,mdefault,help);
237: }
238: PetscOptionsGetReal(bag->bagprefix,nname,&mdefault,PETSC_NULL);
239: }
241: PetscNew(struct _n_PetscBagItem,&item);
242: item->dtype = PETSC_REAL;
243: item->offset = ((char*)addr) - ((char*)bag);
244: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
245: item->next = 0;
246: item->msize = 1;
247: *(PetscReal*)addr = mdefault;
248: PetscBagRegister_Private(bag,item,name,help);
249: return(0);
250: }
254: /*@C
255: PetscBagRegisterScalar - add a real or complex number value to the bag
257: Logically Collective on PetscBag
259: Input Parameter:
260: + bag - the bag of values
261: . addr - location of scalar in struct
262: . mdefault - the initial value
263: . name - name of the variable
264: - help - longer string with more information about the value
267: Level: beginner
269: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
270: PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
271: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
273: @*/
274: PetscErrorCode PetscBagRegisterScalar(PetscBag bag,void *addr,PetscScalar mdefault, const char* name, const char* help)
275: {
277: PetscBagItem item;
278: char nname[PETSC_BAG_NAME_LENGTH+1];
279: PetscBool printhelp;
282: if (!PetscBagInLoad) {
283: nname[0] = '-';
284: nname[1] = 0;
285: PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
286: PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
287: if (printhelp) {
288: (*PetscHelpPrintf)(bag->bagcomm," -%s%s <%G + %Gi>: %s \n",bag->bagprefix?bag->bagprefix:"",name,PetscRealPart(mdefault),PetscImaginaryPart(mdefault),help);
289: }
290: PetscOptionsGetScalar(bag->bagprefix,nname,&mdefault,PETSC_NULL);
291: }
293: PetscNew(struct _n_PetscBagItem,&item);
294: item->dtype = PETSC_SCALAR;
295: item->offset = ((char*)addr) - ((char*)bag);
296: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
297: item->next = 0;
298: item->msize = 1;
299: *(PetscScalar*)addr = mdefault;
300: PetscBagRegister_Private(bag,item,name,help);
301: return(0);
302: }
306: /*@C
307: PetscBagRegisterBool - add a logical value to the bag
309: Logically Collective on PetscBag
311: Input Parameter:
312: + bag - the bag of values
313: . addr - location of logical in struct
314: . mdefault - the initial value
315: . name - name of the variable
316: - help - longer string with more information about the value
319: Level: beginner
321: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
322: PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
323: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
325: @*/
326: PetscErrorCode PetscBagRegisterBool(PetscBag bag,void *addr,PetscBool mdefault, const char* name, const char* help)
327: {
329: PetscBagItem item;
330: char nname[PETSC_BAG_NAME_LENGTH+1];
331: PetscBool printhelp;
334: /* the checks here with != PETSC_FALSE and PETSC_TRUE is a special case; here we truly demand that the value be 0 or 1 */
335: if (mdefault != PETSC_FALSE && mdefault != PETSC_TRUE) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Boolean %s %s must be boolean; integer value %d",name,help,(int)mdefault);
336: if (!PetscBagInLoad) {
337: nname[0] = '-';
338: nname[1] = 0;
339: PetscStrncat(nname,name,PETSC_BAG_NAME_LENGTH-1);
340: PetscOptionsHasName(PETSC_NULL,"-help",&printhelp);
341: if (printhelp) {
342: (*PetscHelpPrintf)(bag->bagcomm," -%s%s <%s>: %s \n",bag->bagprefix?bag->bagprefix:"",name,PetscBools[mdefault],help);
343: }
344: PetscOptionsGetBool(bag->bagprefix,nname,&mdefault,PETSC_NULL);
345: }
347: PetscNew(struct _n_PetscBagItem,&item);
348: item->dtype = PETSC_BOOL;
349: item->offset = ((char*)addr) - ((char*)bag);
350: if (item->offset > bag->bagsize) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Registered item %s %s is not in bag memory space",name,help);
351: item->next = 0;
352: item->msize = 1;
353: *(PetscBool*)addr = mdefault;
354: PetscBagRegister_Private(bag,item,name,help);
355: return(0);
356: }
360: /*@C
361: PetscBagDestroy - Destroys a bag values
363: Collective on PetscBag
365: Input Parameter:
366: . bag - the bag of values
368: Level: beginner
370: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
371: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
372: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
374: @*/
375: PetscErrorCode PetscBagDestroy(PetscBag *bag)
376: {
378: PetscBagItem nitem = (*bag)->bagitems,item;
381: while (nitem) {
382: item = nitem->next;
383: if (nitem->freelist) {
384: void *v = (void*)nitem->list;
385: PetscFree(v);
386: }
387: PetscFree(nitem);
388: nitem = item;
389: }
390: if ((*bag)->bagprefix) { PetscFree((*bag)->bagprefix); }
391: PetscFree(*bag);
392: return(0);
393: }
397: /*@C
398: PetscBagSetFromOptions - Allows setting options from a bag
400: Collective on PetscBag
402: Input Parameter:
403: . bag - the bag of values
405: Level: beginner
407: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagLoad(), PetscBagGetData()
408: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
409: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagView(), PetscBagRegisterEnum()
411: @*/
412: PetscErrorCode PetscBagSetFromOptions(PetscBag bag)
413: {
415: PetscBagItem nitem = bag->bagitems;
416: char name[PETSC_BAG_NAME_LENGTH+1],helpname[PETSC_BAG_NAME_LENGTH+PETSC_BAG_HELP_LENGTH+3];
417:
419: PetscStrcpy(helpname,bag->bagname);
420: PetscStrcat(helpname," ");
421: PetscStrcat(helpname,bag->baghelp);
422: PetscOptionsBegin(bag->bagcomm,PETSC_NULL,helpname,0);
423: while (nitem) {
424: name[0] = '-';
425: name[1] = 0;
426: PetscStrcat(name,nitem->name);
427: if (nitem->dtype == PETSC_CHAR) { /* special handling for fortran required? [due to space padding vs null termination] */
428: char *value = (char*)(((char*)bag) + nitem->offset);
429: PetscOptionsString(name,nitem->help,"",value,value,nitem->msize,PETSC_NULL);
430: } else if (nitem->dtype == PETSC_REAL) {
431: PetscReal *value = (PetscReal*)(((char*)bag) + nitem->offset);
432: PetscOptionsReal(name,nitem->help,"",*value,value,PETSC_NULL);
433: } else if (nitem->dtype == PETSC_SCALAR) {
434: PetscScalar *value = (PetscScalar*)(((char*)bag) + nitem->offset);
435: PetscOptionsScalar(name,nitem->help,"",*value,value,PETSC_NULL);
436: } else if (nitem->dtype == PETSC_INT) {
437: PetscInt *value = (PetscInt*)(((char*)bag) + nitem->offset);
438: PetscOptionsInt(name,nitem->help,"",*value,value,PETSC_NULL);
439: } else if (nitem->dtype == PETSC_ENUM) {
440: PetscEnum *value = (PetscEnum*)(((char*)bag) + nitem->offset);
441: PetscInt i = 0;
442: while (nitem->list[i++]);
443: PetscOptionsEnum(name,nitem->help,nitem->list[i-3],nitem->list,*value,value,PETSC_NULL);
444: } else if (nitem->dtype == PETSC_BOOL) {
445: PetscBool *value = (PetscBool*)(((char*)bag) + nitem->offset);
446: PetscOptionsBool(name,nitem->help,"",*value,value,PETSC_NULL);
447: }
448: nitem = nitem->next;
449: }
450: PetscOptionsEnd();
451: return(0);
452: }
456: /*@C
457: PetscBagView - Views a bag of values as either ASCII text or a binary file
459: Collective on PetscBag
461: Input Parameter:
462: + bag - the bag of values
463: - viewer - location to view the values
465: Level: beginner
467: Warning: Currently PETSc bags saved in a binary file can only be read back
468: in on a machine of the same architecture. Let us know when this is a problem
469: and we'll fix it.
471: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagLoad(), PetscBagGetData()
472: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar(), PetscBagRegisterEnum()
473: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName()
475: @*/
476: PetscErrorCode PetscBagView(PetscBag bag,PetscViewer view)
477: {
478: PetscBool isascii,isbinary;
480: PetscBagItem nitem = bag->bagitems;
481:
483: PetscTypeCompare((PetscObject)view,PETSCVIEWERASCII,&isascii);
484: PetscTypeCompare((PetscObject)view,PETSCVIEWERBINARY,&isbinary);
485: if (isascii) {
486: PetscViewerASCIIPrintf(view,"PetscBag Object: %s %s\n",bag->bagname,bag->baghelp);
487: while (nitem) {
488: if (nitem->dtype == PETSC_CHAR) {
489: char* value = (char*)(((char*)bag) + nitem->offset);
490: char tmp = value[nitem->msize-1]; /* special handling for fortran chars wihout null terminator */
491: value[nitem->msize-1] =0;
492: PetscViewerASCIIPrintf(view," %s = %s; %s\n",nitem->name,value,nitem->help);
493: value[nitem->msize-1] =tmp;
494: } else if (nitem->dtype == PETSC_REAL) {
495: PetscReal value = *(PetscReal*)(((char*)bag) + nitem->offset);
496: PetscViewerASCIIPrintf(view," %s = %G; %s\n",nitem->name,value,nitem->help);
497: } else if (nitem->dtype == PETSC_SCALAR) {
498: PetscScalar value = *(PetscScalar*)(((char*)bag) + nitem->offset);
499: #if defined(PETSC_USE_COMPLEX)
500: PetscViewerASCIIPrintf(view," %s = %G + %Gi; %s\n",nitem->name,PetscRealPart(value),PetscImaginaryPart(value),nitem->help);
501: #else
502: PetscViewerASCIIPrintf(view," %s = %G; %s\n",nitem->name,value,nitem->help);
503: #endif
504: } else if (nitem->dtype == PETSC_INT) {
505: PetscInt value = *(PetscInt*)(((char*)bag) + nitem->offset);
506: PetscViewerASCIIPrintf(view," %s = %D; %s\n",nitem->name,value,nitem->help);
507: } else if (nitem->dtype == PETSC_BOOL) {
508: PetscBool value = *(PetscBool*)(((char*)bag) + nitem->offset);
509: /* some Fortran compilers use -1 as boolean */
510: if (((int) value) == -1) value = PETSC_TRUE;
511: /* the checks here with != PETSC_FALSE and PETSC_TRUE is a special case; here we truly demand that the value be 0 or 1 */
512: if (value != PETSC_FALSE && value != PETSC_TRUE) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Boolean value for %s %s is corrupt; integer value %d",nitem->name,nitem->help,value);
513: PetscViewerASCIIPrintf(view," %s = %s; %s\n",nitem->name,PetscBools[value],nitem->help);
514: } else if (nitem->dtype == PETSC_ENUM) {
515: PetscEnum value = *(PetscEnum*)(((char*)bag) + nitem->offset);
516: PetscInt i = 0;
517: while (nitem->list[i++]);
518: PetscViewerASCIIPrintf(view," %s = %s; (%s) %s\n",nitem->name,nitem->list[value],nitem->list[i-3],nitem->help);
519: }
520: nitem = nitem->next;
521: }
522: } else if (isbinary) {
523: PetscInt classid = PETSC_BAG_FILE_CLASSID, bagsize = (PetscInt) bag->bagsize, dtype;
524: PetscViewerBinaryWrite(view,&classid,1,PETSC_INT,PETSC_TRUE);
525: PetscViewerBinaryWrite(view,&bagsize,1,PETSC_INT,PETSC_TRUE);
526: PetscViewerBinaryWrite(view,&bag->count,1,PETSC_INT,PETSC_FALSE);
527: PetscViewerBinaryWrite(view,bag->bagname,PETSC_BAG_NAME_LENGTH,PETSC_CHAR,PETSC_FALSE);
528: PetscViewerBinaryWrite(view,bag->baghelp,PETSC_BAG_HELP_LENGTH,PETSC_CHAR,PETSC_FALSE);
529: while (nitem) {
530: PetscViewerBinaryWrite(view,&nitem->offset,1,PETSC_INT,PETSC_FALSE);
531: dtype = (PetscInt)nitem->dtype;
532: PetscViewerBinaryWrite(view,&dtype,1,PETSC_INT,PETSC_FALSE);
533: PetscViewerBinaryWrite(view,nitem->name,PETSC_BAG_NAME_LENGTH,PETSC_CHAR,PETSC_FALSE);
534: PetscViewerBinaryWrite(view,nitem->help,PETSC_BAG_HELP_LENGTH,PETSC_CHAR,PETSC_FALSE);
535: PetscViewerBinaryWrite(view,&nitem->msize,1,PETSC_INT,PETSC_FALSE);
536: /* some Fortran compilers use -1 as boolean */
537: if (dtype == PETSC_BOOL && ((*(int*) (((char*)bag) + nitem->offset) == -1))) *(int*) (((char*)bag) + nitem->offset) = PETSC_TRUE;
539: PetscViewerBinaryWrite(view,(((char*)bag) + nitem->offset),nitem->msize,nitem->dtype,PETSC_FALSE);
540: if (dtype == PETSC_ENUM) {
541: PetscViewerBinaryWriteStringArray(view,(char **)nitem->list);
542: }
543: nitem = nitem->next;
544: }
545: } else {
546: SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"No support for this viewer type");
547: }
548: return(0);
549: }
553: /*@C
554: PetscBagLoad - Loads a bag of values from a binary file
556: Collective on PetscViewer
558: Input Parameter:
559: . viewer - file to load values from
561: Output Parameter:
562: . bag - the bag of values
564: Level: beginner
566: .seealso: PetscBag, PetscBagSetName(), PetscBagDestroy(), PetscBagView(), PetscBagGetData()
567: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
568: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagGetName(), PetscBagRegisterEnum()
570: @*/
571: PetscErrorCode PetscBagLoad(PetscViewer view,PetscBag *bag)
572: {
574: PetscBool isbinary,skipoptions;
575: PetscInt classid,bagsizecount[2],i,offsetdtype[2],msize;
576: char name[PETSC_BAG_NAME_LENGTH],help[PETSC_BAG_HELP_LENGTH],**list;
577: PetscBagItem nitem;
578: MPI_Comm comm;
581: PetscTypeCompare((PetscObject)view,PETSCVIEWERBINARY,&isbinary);
582: if (!isbinary) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"No support for this viewer type");
584: PetscViewerBinaryRead(view,&classid,1,PETSC_INT);
585: if (classid != PETSC_BAG_FILE_CLASSID) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Not PetscBag next in binary file");
586: PetscViewerBinaryRead(view,bagsizecount,2,PETSC_INT);
587: PetscObjectGetComm((PetscObject)view,&comm);
588: PetscBagCreate(comm,bagsizecount[0]-sizeof(struct _n_PetscBag)-sizeof(PetscScalar),bag);
590: PetscViewerBinaryRead(view,(*bag)->bagname,PETSC_BAG_NAME_LENGTH,PETSC_CHAR);
591: PetscViewerBinaryRead(view,(*bag)->baghelp,PETSC_BAG_HELP_LENGTH,PETSC_CHAR);
593: PetscViewerBinaryGetSkipOptions(view,&skipoptions);
594: if (skipoptions) PetscBagInLoad = PETSC_TRUE;
596: for (i=0; i<bagsizecount[1]; i++) {
597: PetscViewerBinaryRead(view,offsetdtype,2,PETSC_INT);
598: PetscViewerBinaryRead(view,name,PETSC_BAG_NAME_LENGTH,PETSC_CHAR);
599: PetscViewerBinaryRead(view,help,PETSC_BAG_HELP_LENGTH,PETSC_CHAR);
600: PetscViewerBinaryRead(view,&msize,1,PETSC_INT);
602: if (offsetdtype[1] == (PetscInt) PETSC_CHAR) {
603: PetscViewerBinaryRead(view,((char*)(*bag))+offsetdtype[0],msize,PETSC_CHAR);
604: PetscBagRegisterString(*bag,((char*)(*bag))+offsetdtype[0],msize,((char*)(*bag))+offsetdtype[0],name,help);
605: } else if (offsetdtype[1] == (PetscInt) PETSC_REAL) {
606: PetscReal mdefault;
607: PetscViewerBinaryRead(view,&mdefault,1,PETSC_REAL);
608: PetscBagRegisterReal(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
609: } else if (offsetdtype[1] == (PetscInt) PETSC_SCALAR) {
610: PetscScalar mdefault;
611: PetscViewerBinaryRead(view,&mdefault,1,PETSC_SCALAR);
612: PetscBagRegisterScalar(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
613: } else if (offsetdtype[1] == (PetscInt) PETSC_INT) {
614: PetscInt mdefault;
615: PetscViewerBinaryRead(view,&mdefault,1,PETSC_INT);
616: PetscBagRegisterInt(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
617: } else if (offsetdtype[1] == (PetscInt) PETSC_BOOL) {
618: PetscBool mdefault;
619: PetscViewerBinaryRead(view,&mdefault,1,PETSC_BOOL);
620: PetscBagRegisterBool(*bag,((char*)(*bag))+offsetdtype[0],mdefault,name,help);
621: } else if (offsetdtype[1] == (PetscInt) PETSC_ENUM) {
622: PetscEnum mdefault;
623: PetscViewerBinaryRead(view,&mdefault,1,PETSC_ENUM);
624: PetscViewerBinaryReadStringArray(view,&list);
625: PetscBagRegisterEnum(*bag,((char*)(*bag))+offsetdtype[0],(const char**)list,mdefault,name,help);
626: /* we malloced list in PetscViewerBinaryReadStringArray() so must free ourselves */
627: nitem = (*bag)->bagitems;
628: while (nitem->next) nitem = nitem->next;
629: nitem->freelist = PETSC_TRUE;
630: }
631: }
632: PetscBagInLoad = PETSC_FALSE;
633: return(0);
634: }
638: /*@
639: PetscBagCreate - Create a bag of values
641: Collective on MPI_Comm
643: Level: Intermediate
645: Input Parameters:
646: + comm - communicator to share bag
647: - bagsize - size of the C structure holding the values
649: Output Parameter:
650: . bag - the bag of values
652: Notes:
653: The size of the A struct must be small enough to fit in a PetscInt; by default
654: PetscInt is 4 bytes. The warning about casting to a shorter length can be ignored
655: below unless your A struct is too large
657: .seealso: PetscBag, PetscBagGetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
658: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
659: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
660: @*/
661: PetscErrorCode PetscBagCreate(MPI_Comm comm, size_t bagsize, PetscBag *bag)
662: {
666: PetscMalloc(bagsize+sizeof(struct _n_PetscBag)+sizeof(PetscScalar),bag);
667: PetscMemzero(*bag,bagsize+sizeof(struct _n_PetscBag)+sizeof(PetscScalar));
668: (*bag)->bagsize = bagsize+sizeof(struct _n_PetscBag)+sizeof(PetscScalar);
669: (*bag)->bagcomm = comm;
670: (*bag)->bagprefix = PETSC_NULL;
671: (*bag)->structlocation = (void*)(((char*)(*bag)) + sizeof(PetscScalar)*(sizeof(struct _n_PetscBag)/sizeof(PetscScalar)) + sizeof(PetscScalar));
672: return(0);
673: }
674:
677: /*@C
678: PetscBagSetName - Sets the name of a bag of values
680: Not Collective
682: Level: Intermediate
684: Input Parameters:
685: + bag - the bag of values
686: . name - the name assigned to the bag
687: - help - help message for bag
689: .seealso: PetscBag, PetscBagGetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
690: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
691: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
692: @*/
694: PetscErrorCode PetscBagSetName(PetscBag bag, const char *name, const char *help)
695: {
698: PetscStrncpy(bag->bagname,name,PETSC_BAG_NAME_LENGTH-1);
699: PetscStrncpy(bag->baghelp,help,PETSC_BAG_HELP_LENGTH-1);
700: return(0);
701: }
706: /*@C
707: PetscBagGetName - Gets the name of a bag of values
709: Not Collective
711: Level: Intermediate
713: Input Parameter:
714: . bag - the bag of values
716: Output Parameter:
717: . name - the name assigned to the bag
719: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad(), PetscBagGetData()
720: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
721: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
722: @*/
723: PetscErrorCode PetscBagGetName(PetscBag bag, char **name)
724: {
726: *name = bag->bagname;
727: return(0);
728: }
732: /*@C
733: PetscBagGetData - Gives back the user - access to memory that
734: should be used for storing user-data-structure
736: Not Collective
738: Level: Intermediate
740: Input Parameter:
741: . bag - the bag of values
743: Output Parameter:
744: . data - pointer to memory that will have user-data-structure
746: .seealso: PetscBag, PetscBagSetName(), PetscBagView(), PetscBagLoad()
747: PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
748: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
749: @*/
750: PetscErrorCode PetscBagGetData(PetscBag bag, void **data)
751: {
753: *data = bag->structlocation;
754: return(0);
755: }
759: /*@C
760: PetscBagSetOptionsPrefix - Sets the prefix used for searching for all
761: PetscBag items in the options database.
763: Logically collective on Bag.
765: Level: Intermediate
767: Input Parameters:
768: + bag - the bag of values
769: - prefix - the prefix to prepend all Bag item names with.
771: NOTES: Must be called prior to registering any of the bag items.
773: .seealso: PetscBag, PetscBagRegisterReal(), PetscBagRegisterInt(), PetscBagRegisterBool(), PetscBagRegisterScalar()
774: PetscBagSetFromOptions(), PetscBagCreate(), PetscBagDestroy(), PetscBagRegisterEnum()
775: @*/
777: PetscErrorCode PetscBagSetOptionsPrefix(PetscBag bag, const char pre[])
778: {
781: if (!pre) {
782: PetscFree(bag->bagprefix);
783: } else {
784: if (pre[0] == '-') SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Options prefix should not begin with a hypen");
785: PetscFree(bag->bagprefix);
786: PetscStrallocpy(pre,&(bag->bagprefix));
787: }
788: return(0);
789: }