Actual source code: options.c

petsc-3.4.4 2014-03-13
  2: /* Define Feature test macros to make sure atoll is available (SVr4, POSIX.1-2001, 4.3BSD, C99), not in (C89 and POSIX.1-1996) */
  3: #define PETSC_DESIRE_FEATURE_TEST_MACROS

  5: /*
  6:    These routines simplify the use of command line, file options, etc., and are used to manipulate the options database.
  7:    This provides the low-level interface, the high level interface is in aoptions.c

  9:    Some routines use regular malloc and free because it cannot know  what malloc is requested with the
 10:    options database until it has already processed the input.
 11: */

 13: #include <petsc-private/petscimpl.h>        /*I  "petscsys.h"   I*/
 14: #include <petscviewer.h>
 15: #include <ctype.h>
 16: #if defined(PETSC_HAVE_MALLOC_H)
 17: #include <malloc.h>
 18: #endif
 19: #if defined(PETSC_HAVE_YAML)
 20: #include <yaml.h>
 21: #endif

 23: /*
 24:     This table holds all the options set by the user. For simplicity, we use a static size database
 25: */
 26: #define MAXOPTIONS 512
 27: #define MAXALIASES 25
 28: #define MAXOPTIONSMONITORS 5
 29: #define MAXPREFIXES 25

 31: typedef struct {
 32:   int            N,argc,Naliases;
 33:   char           **args,*names[MAXOPTIONS],*values[MAXOPTIONS];
 34:   char           *aliases1[MAXALIASES],*aliases2[MAXALIASES];
 35:   PetscBool      used[MAXOPTIONS];
 36:   PetscBool      namegiven;
 37:   char           programname[PETSC_MAX_PATH_LEN]; /* HP includes entire path in name */

 39:   /* --------User (or default) routines (most return -1 on error) --------*/
 40:   PetscErrorCode (*monitor[MAXOPTIONSMONITORS])(const char[], const char[], void*); /* returns control to user after */
 41:   PetscErrorCode (*monitordestroy[MAXOPTIONSMONITORS])(void**);         /* */
 42:   void           *monitorcontext[MAXOPTIONSMONITORS];                  /* to pass arbitrary user data into monitor */
 43:   PetscInt       numbermonitors;                                       /* to, for instance, detect options being set */

 45:   /* Prefixes */
 46:   PetscInt prefixind,prefixstack[MAXPREFIXES];
 47:   char     prefix[2048];
 48: } PetscOptionsTable;


 51: static PetscOptionsTable      *options = 0;
 52: extern PetscOptionsObjectType PetscOptionsObject;

 54: /*
 55:     Options events monitor
 56: */
 57: #define PetscOptionsMonitor(name,value)                              \
 58:   { PetscErrorCode _ierr; PetscInt _i,_im = options->numbermonitors; \
 59:     for (_i=0; _i<_im; _i++) { \
 60:       _(*options->monitor[_i])(name, value, options->monitorcontext[_i]);CHKERRQ(_ierr); \
 61:     } \
 62:   }

 66: /*
 67:    PetscOptionsStringToInt - Converts a string to an integer value. Handles special cases such as "default" and "decide"
 68: */
 69: PetscErrorCode  PetscOptionsStringToInt(const char name[],PetscInt *a)
 70: {
 72:   size_t         i,len;
 73:   PetscBool      decide,tdefault,mouse;

 76:   PetscStrlen(name,&len);
 77:   if (!len) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"character string of length zero has no numerical value");

 79:   PetscStrcasecmp(name,"PETSC_DEFAULT",&tdefault);
 80:   if (!tdefault) {
 81:     PetscStrcasecmp(name,"DEFAULT",&tdefault);
 82:   }
 83:   PetscStrcasecmp(name,"PETSC_DECIDE",&decide);
 84:   if (!decide) {
 85:     PetscStrcasecmp(name,"DECIDE",&decide);
 86:   }
 87:   PetscStrcasecmp(name,"mouse",&mouse);

 89:   if (tdefault)    *a = PETSC_DEFAULT;
 90:   else if (decide) *a = PETSC_DECIDE;
 91:   else if (mouse)  *a = -1;
 92:   else {
 93:     if (name[0] != '+' && name[0] != '-' && name[0] < '0' && name[0] > '9') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Input string %s has no integer value (do not include . in it)",name);

 95:     for (i=1; i<len; i++) {
 96:       if (name[i] < '0' || name[i] > '9') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Input string %s has no integer value (do not include . in it)",name);
 97:     }

 99: #if defined(PETSC_USE_64BIT_INDICES) && defined(PETSC_HAVE_ATOLL)
100:     *a = atoll(name);
101: #elif defined(PETSC_USE_64BIT_INDICES) && defined(PETSC_HAVE___INT64)
102:     *a = _atoi64(name);
103: #else
104:     *a = (PetscInt)atoi(name);
105: #endif
106:   }
107:   return(0);
108: }

112: /*
113:    Converts a string to PetscReal value. Handles special cases like "default" and "decide"
114: */
115: PetscErrorCode  PetscOptionsStringToReal(const char name[],PetscReal *a)
116: {
118:   size_t         len;
119:   PetscBool      decide,tdefault;

122:   PetscStrlen(name,&len);
123:   if (!len) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"character string of length zero has no numerical value");

125:   PetscStrcasecmp(name,"PETSC_DEFAULT",&tdefault);
126:   if (!tdefault) {
127:     PetscStrcasecmp(name,"DEFAULT",&tdefault);
128:   }
129:   PetscStrcasecmp(name,"PETSC_DECIDE",&decide);
130:   if (!decide) {
131:     PetscStrcasecmp(name,"DECIDE",&decide);
132:   }

134:   if (tdefault)    *a = PETSC_DEFAULT;
135:   else if (decide) *a = PETSC_DECIDE;
136:   else {
137:     if (name[0] != '+' && name[0] != '-' && name[0] != '.' && name[0] < '0' && name[0] > '9') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Input string %s has no numeric value ",name);
138:     *a = atof(name);
139:   }
140:   return(0);
141: }

145: /*
146:    PetscOptionsStringToBool - Converts string to PetscBool , handles cases like "yes", "no", "true", "false", "0", "1"
147: */
148: PetscErrorCode  PetscOptionsStringToBool(const char value[], PetscBool  *a)
149: {
150:   PetscBool      istrue, isfalse;
151:   size_t         len;

155:   PetscStrlen(value, &len);
156:   if (!len) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Character string of length zero has no logical value");
157:   PetscStrcasecmp(value,"TRUE",&istrue);
158:   if (istrue) {*a = PETSC_TRUE; return(0);}
159:   PetscStrcasecmp(value,"YES",&istrue);
160:   if (istrue) {*a = PETSC_TRUE; return(0);}
161:   PetscStrcasecmp(value,"1",&istrue);
162:   if (istrue) {*a = PETSC_TRUE; return(0);}
163:   PetscStrcasecmp(value,"on",&istrue);
164:   if (istrue) {*a = PETSC_TRUE; return(0);}
165:   PetscStrcasecmp(value,"FALSE",&isfalse);
166:   if (isfalse) {*a = PETSC_FALSE; return(0);}
167:   PetscStrcasecmp(value,"NO",&isfalse);
168:   if (isfalse) {*a = PETSC_FALSE; return(0);}
169:   PetscStrcasecmp(value,"0",&isfalse);
170:   if (isfalse) {*a = PETSC_FALSE; return(0);}
171:   PetscStrcasecmp(value,"off",&isfalse);
172:   if (isfalse) {*a = PETSC_FALSE; return(0);}
173:   SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Unknown logical value: %s", value);
174:   return(0);
175: }

179: /*@C
180:     PetscGetProgramName - Gets the name of the running program.

182:     Not Collective

184:     Input Parameter:
185: .   len - length of the string name

187:     Output Parameter:
188: .   name - the name of the running program

190:    Level: advanced

192:     Notes:
193:     The name of the program is copied into the user-provided character
194:     array of length len.  On some machines the program name includes
195:     its entire path, so one should generally set len >= PETSC_MAX_PATH_LEN.
196: @*/
197: PetscErrorCode  PetscGetProgramName(char name[],size_t len)
198: {

202:   if (!options) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Must call PetscInitialize() first");
203:   if (!options->namegiven) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Unable to determine program name");
204:   PetscStrncpy(name,options->programname,len);
205:   return(0);
206: }

210: PetscErrorCode  PetscSetProgramName(const char name[])
211: {

215:   options->namegiven = PETSC_TRUE;

217:   PetscStrncpy(options->programname,name,PETSC_MAX_PATH_LEN);
218:   return(0);
219: }

223: /*@
224:     PetscOptionsValidKey - PETSc Options database keys must begin with one or two dashes (-) followed by a letter.

226:    Input Parameter:
227: .    in_str - string to check if valid

229:    Output Parameter:
230: .    key - PETSC_TRUE if a valid key

232:   Level: intermediate

234: @*/
235: PetscErrorCode  PetscOptionsValidKey(const char in_str[],PetscBool  *key)
236: {
238:   *key = PETSC_FALSE;
239:   if (!in_str) return(0);
240:   if (in_str[0] != '-') return(0);
241:   if (in_str[1] == '-') in_str++;
242:   if (!isalpha(in_str[1])) return(0);
243:   if ((!strncmp(in_str+1,"inf",3) || !strncmp(in_str+1,"INF",3)) && !(in_str[4] == '_' || isalnum(in_str[4]))) return(0);
244:   *key = PETSC_TRUE;
245:   return(0);
246: }

250: /*@C
251:      PetscOptionsInsertString - Inserts options into the database from a string

253:      Not collective: but only processes that call this routine will set the options
254:                      included in the string

256:   Input Parameter:
257: .   in_str - string that contains options separated by blanks


260:   Level: intermediate

262:   Contributed by Boyana Norris

264: .seealso: PetscOptionsSetValue(), PetscOptionsView(), PetscOptionsHasName(), PetscOptionsGetInt(),
265:           PetscOptionsGetReal(), PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsBool(),
266:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
267:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
268:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
269:           PetscOptionsList(), PetscOptionsEList(), PetscOptionsInsertFile()

271: @*/
272: PetscErrorCode  PetscOptionsInsertString(const char in_str[])
273: {
274:   char           *first,*second;
276:   PetscToken     token;
277:   PetscBool      key,ispush,ispop;

280:   PetscTokenCreate(in_str,' ',&token);
281:   PetscTokenFind(token,&first);
282:   while (first) {
283:     PetscStrcasecmp(first,"-prefix_push",&ispush);
284:     PetscStrcasecmp(first,"-prefix_pop",&ispop);
285:     PetscOptionsValidKey(first,&key);
286:     if (ispush) {
287:       PetscTokenFind(token,&second);
288:       PetscOptionsPrefixPush(second);
289:       PetscTokenFind(token,&first);
290:     } else if (ispop) {
291:       PetscOptionsPrefixPop();
292:       PetscTokenFind(token,&first);
293:     } else if (key) {
294:       PetscTokenFind(token,&second);
295:       PetscOptionsValidKey(second,&key);
296:       if (!key) {
297:         PetscOptionsSetValue(first,second);
298:         PetscTokenFind(token,&first);
299:       } else {
300:         PetscOptionsSetValue(first,NULL);
301:         first = second;
302:       }
303:     } else {
304:       PetscTokenFind(token,&first);
305:     }
306:   }
307:   PetscTokenDestroy(&token);
308:   return(0);
309: }

311: /*
312:     Returns a line (ended by a \n, \r or null character of any length. Result should be freed with free()
313: */
314: static char *Petscgetline(FILE * f)
315: {
316:   size_t size  = 0;
317:   size_t len   = 0;
318:   size_t last  = 0;
319:   char   *buf  = NULL;

321:   if (feof(f)) return 0;
322:   do {
323:     size += 1024; /* BUFSIZ is defined as "the optimal read size for this platform" */
324:     buf   = (char*)realloc((void*)buf,size); /* realloc(NULL,n) is the same as malloc(n) */
325:     /* Actually do the read. Note that fgets puts a terminal '\0' on the
326:     end of the string, so we make sure we overwrite this */
327:     if (!fgets(buf+len,size,f)) buf[len]=0;
328:     PetscStrlen(buf,&len);
329:     last = len - 1;
330:   } while (!feof(f) && buf[last] != '\n' && buf[last] != '\r');
331:   if (len) return buf;
332:   free(buf);
333:   return 0;
334: }


339: /*@C
340:      PetscOptionsInsertFile - Inserts options into the database from a file.

342:      Collective on MPI_Comm

344:   Input Parameter:
345: +   comm - the processes that will share the options (usually PETSC_COMM_WORLD)
346: .   file - name of file
347: -   require - if PETSC_TRUE will generate an error if the file does not exist


350:   Notes: Use  # for lines that are comments and which should be ignored.

352:   Level: developer

354: .seealso: PetscOptionsSetValue(), PetscOptionsView(), PetscOptionsHasName(), PetscOptionsGetInt(),
355:           PetscOptionsGetReal(), PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsBool(),
356:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
357:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
358:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
359:           PetscOptionsList(), PetscOptionsEList()

361: @*/
362: PetscErrorCode  PetscOptionsInsertFile(MPI_Comm comm,const char file[],PetscBool require)
363: {
364:   char           *string,fname[PETSC_MAX_PATH_LEN],*first,*second,*third,*vstring = 0,*astring = 0,*packed = 0;
366:   size_t         i,len,bytes;
367:   FILE           *fd;
368:   PetscToken     token;
369:   int            err;
370:   char           cmt[1]={'#'},*cmatch;
371:   PetscMPIInt    rank,cnt=0,acnt=0,counts[2];

374:   MPI_Comm_rank(comm,&rank);
375:   if (!rank) {
376:     cnt        = 0;
377:     acnt       = 0;

379:     PetscFixFilename(file,fname);
380:     fd   = fopen(fname,"r");
381:     if (fd) {
382:       PetscSegBuffer vseg,aseg;
383:       PetscSegBufferCreate(1,4000,&vseg);
384:       PetscSegBufferCreate(1,2000,&aseg);

386:       /* the following line will not work when opening initial files (like .petscrc) since info is not yet set */
387:       PetscInfo1(0,"Opened options file %s\n",file);

389:       while ((string = Petscgetline(fd))) {
390:         /* eliminate comments from each line */
391:         for (i=0; i<1; i++) {
392:           PetscStrchr(string,cmt[i],&cmatch);
393:           if (cmatch) *cmatch = 0;
394:         }
395:         PetscStrlen(string,&len);
396:         /* replace tabs, ^M, \n with " " */
397:         for (i=0; i<len; i++) {
398:           if (string[i] == '\t' || string[i] == '\r' || string[i] == '\n') {
399:             string[i] = ' ';
400:           }
401:         }
402:         PetscTokenCreate(string,' ',&token);
403:         free(string);
404:         PetscTokenFind(token,&first);
405:         if (!first) {
406:           goto destroy;
407:         } else if (!first[0]) { /* if first token is empty spaces, redo first token */
408:           PetscTokenFind(token,&first);
409:         }
410:         PetscTokenFind(token,&second);
411:         if (!first) {
412:           goto destroy;
413:         } else if (first[0] == '-') {
414:           PetscStrlen(first,&len);
415:           PetscSegBufferGet(vseg,len+1,&vstring);
416:           PetscMemcpy(vstring,first,len);
417:           vstring[len] = ' ';
418:           if (second) {
419:             PetscStrlen(second,&len);
420:             PetscSegBufferGet(vseg,len+3,&vstring);
421:             vstring[0] = '"';
422:             PetscMemcpy(vstring+1,second,len);
423:             vstring[len+1] = '"';
424:             vstring[len+2] = ' ';
425:           }
426:         } else {
427:           PetscBool match;

429:           PetscStrcasecmp(first,"alias",&match);
430:           if (match) {
431:             PetscTokenFind(token,&third);
432:             if (!third) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Error in options file:alias missing (%s)",second);
433:             PetscStrlen(second,&len);
434:             PetscSegBufferGet(aseg,len+1,&astring);
435:             PetscMemcpy(astring,second,len);
436:             astring[len] = ' ';

438:             PetscStrlen(third,&len);
439:             PetscSegBufferGet(aseg,len+1,&astring);
440:             PetscMemcpy(astring,third,len);
441:             astring[len] = ' ';
442:           } else SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Unknown statement in options file: (%s)",string);
443:         }
444: destroy:
445:         PetscTokenDestroy(&token);
446:       }
447:       err = fclose(fd);
448:       if (err) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SYS,"fclose() failed on file");
449:       PetscSegBufferGetSize(aseg,&bytes); /* size without null termination */
450:       PetscMPIIntCast(bytes,&acnt);
451:       PetscSegBufferGet(aseg,1,&astring);
452:       astring[0] = 0;
453:       PetscSegBufferGetSize(vseg,&bytes); /* size without null termination */
454:       PetscMPIIntCast(bytes,&cnt);
455:       PetscSegBufferGet(vseg,1,&vstring);
456:       vstring[0] = 0;
457:       PetscMalloc((2+acnt+cnt)*sizeof(char),&packed);
458:       PetscSegBufferExtractTo(aseg,packed);
459:       PetscSegBufferExtractTo(vseg,packed+acnt+1);
460:       PetscSegBufferDestroy(&aseg);
461:       PetscSegBufferDestroy(&vseg);
462:     } else if (require) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_USER,"Unable to open Options File %s",fname);
463:   }

465:   counts[0] = acnt;
466:   counts[1] = cnt;
467:   MPI_Bcast(counts,2,MPI_INT,0,comm);
468:   acnt = counts[0];
469:   cnt = counts[1];
470:   if (rank) {
471:     PetscMalloc((2+acnt+cnt)*sizeof(char),&packed);
472:   }
473:   if (acnt || cnt) {
474:     MPI_Bcast(packed,2+acnt+cnt,MPI_CHAR,0,comm);
475:     astring = packed;
476:     vstring = packed + acnt + 1;
477:   }

479:   if (acnt) {
480:     PetscToken token;
481:     char       *first,*second;

483:     PetscTokenCreate(astring,' ',&token);
484:     PetscTokenFind(token,&first);
485:     while (first) {
486:       PetscTokenFind(token,&second);
487:       PetscOptionsSetAlias(first,second);
488:       PetscTokenFind(token,&first);
489:     }
490:     PetscTokenDestroy(&token);
491:   }

493:   if (cnt) {
494:     PetscOptionsInsertString(vstring);
495:   }
496:   PetscFree(packed);
497:   return(0);
498: }

502: static PetscErrorCode PetscOptionsInsertArgs_Private(int argc,char *args[])
503: {
505:   int            left    = argc - 1;
506:   char           **eargs = args + 1;

509:   while (left) {
510:     PetscBool isoptions_file,isprefixpush,isprefixpop,isp4,tisp4,isp4yourname,isp4rmrank,key;
511:     PetscStrcasecmp(eargs[0],"-options_file",&isoptions_file);
512:     PetscStrcasecmp(eargs[0],"-prefix_push",&isprefixpush);
513:     PetscStrcasecmp(eargs[0],"-prefix_pop",&isprefixpop);
514:     PetscStrcasecmp(eargs[0],"-p4pg",&isp4);
515:     PetscStrcasecmp(eargs[0],"-p4yourname",&isp4yourname);
516:     PetscStrcasecmp(eargs[0],"-p4rmrank",&isp4rmrank);
517:     PetscStrcasecmp(eargs[0],"-p4wd",&tisp4);
518:     isp4 = (PetscBool) (isp4 || tisp4);
519:     PetscStrcasecmp(eargs[0],"-np",&tisp4);
520:     isp4 = (PetscBool) (isp4 || tisp4);
521:     PetscStrcasecmp(eargs[0],"-p4amslave",&tisp4);
522:     PetscOptionsValidKey(eargs[0],&key);

524:     if (!key) {
525:       eargs++; left--;
526:     } else if (isoptions_file) {
527:       if (left <= 1) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"Missing filename for -options_file filename option");
528:       if (eargs[1][0] == '-') SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"Missing filename for -options_file filename option");
529:       PetscOptionsInsertFile(PETSC_COMM_WORLD,eargs[1],PETSC_TRUE);
530:       eargs += 2; left -= 2;
531:     } else if (isprefixpush) {
532:       if (left <= 1) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"Missing prefix for -prefix_push option");
533:       if (eargs[1][0] == '-') SETERRQ(PETSC_COMM_SELF,PETSC_ERR_USER,"Missing prefix for -prefix_push option (prefixes cannot start with '-')");
534:       PetscOptionsPrefixPush(eargs[1]);
535:       eargs += 2; left -= 2;
536:     } else if (isprefixpop) {
537:       PetscOptionsPrefixPop();
538:       eargs++; left--;

540:       /*
541:        These are "bad" options that MPICH, etc put on the command line
542:        we strip them out here.
543:        */
544:     } else if (tisp4 || isp4rmrank) {
545:       eargs += 1; left -= 1;
546:     } else if (isp4 || isp4yourname) {
547:       eargs += 2; left -= 2;
548:     } else {
549:       PetscBool nextiskey = PETSC_FALSE;
550:       if (left >= 2) {PetscOptionsValidKey(eargs[1],&nextiskey);}
551:       if (left < 2 || nextiskey) {
552:         PetscOptionsSetValue(eargs[0],NULL);
553:         eargs++; left--;
554:       } else {
555:         PetscOptionsSetValue(eargs[0],eargs[1]);
556:         eargs += 2; left -= 2;
557:       }
558:     }
559:   }
560:   return(0);
561: }


566: /*@C
567:    PetscOptionsInsert - Inserts into the options database from the command line,
568:                    the environmental variable and a file.

570:    Input Parameters:
571: +  argc - count of number of command line arguments
572: .  args - the command line arguments
573: -  file - optional filename, defaults to ~username/.petscrc

575:    Note:
576:    Since PetscOptionsInsert() is automatically called by PetscInitialize(),
577:    the user does not typically need to call this routine. PetscOptionsInsert()
578:    can be called several times, adding additional entries into the database.

580:    Options Database Keys:
581: +   -options_monitor <optional filename> - print options names and values as they are set
582: .   -options_file <filename> - read options from a file

584:    Level: advanced

586:    Concepts: options database^adding

588: .seealso: PetscOptionsDestroy_Private(), PetscOptionsView(), PetscOptionsInsertString(), PetscOptionsInsertFile(),
589:           PetscInitialize()
590: @*/
591: PetscErrorCode  PetscOptionsInsert(int *argc,char ***args,const char file[])
592: {
594:   PetscMPIInt    rank;
595:   char           pfile[PETSC_MAX_PATH_LEN];
596:   PetscBool      flag = PETSC_FALSE;

599:   if (!options) {
600:     fprintf(stderr, "Options have not been enabled.\nYou might have forgotten to call PetscInitialize().\n");
601:     MPI_Abort(MPI_COMM_WORLD, PETSC_ERR_SUP);
602:   }
603:   MPI_Comm_rank(PETSC_COMM_WORLD,&rank);

605:   options->argc = (argc) ? *argc : 0;
606:   options->args = (args) ? *args : NULL;

608:   if (file && file[0]) {
609:     char fullpath[PETSC_MAX_PATH_LEN];

611:     PetscStrreplace(PETSC_COMM_WORLD,file,fullpath,PETSC_MAX_PATH_LEN);
612:     PetscOptionsInsertFile(PETSC_COMM_WORLD,fullpath,PETSC_TRUE);
613:   }
614:   /*
615:      We want to be able to give -skip_petscrc on the command line, but need to parse it first.  Since the command line
616:      should take precedence, we insert it twice.  It would be sufficient to just scan for -skip_petscrc.
617:   */
618:   if (argc && args && *argc) {PetscOptionsInsertArgs_Private(*argc,*args);}
619:   PetscOptionsGetBool(NULL,"-skip_petscrc",&flag,NULL);
620:   if (!flag) {
621:     PetscGetHomeDirectory(pfile,PETSC_MAX_PATH_LEN-16);
622:     /* PetscOptionsInsertFile() does a fopen() on rank0 only - so only rank0 HomeDir value is relavent */
623:     if (pfile[0]) { PetscStrcat(pfile,"/.petscrc"); }
624:     PetscOptionsInsertFile(PETSC_COMM_WORLD,pfile,PETSC_FALSE);
625:     PetscOptionsInsertFile(PETSC_COMM_WORLD,".petscrc",PETSC_FALSE);
626:     PetscOptionsInsertFile(PETSC_COMM_WORLD,"petscrc",PETSC_FALSE);
627:   }

629:   /* insert environmental options */
630:   {
631:     char   *eoptions = 0;
632:     size_t len       = 0;
633:     if (!rank) {
634:       eoptions = (char*)getenv("PETSC_OPTIONS");
635:       PetscStrlen(eoptions,&len);
636:       MPI_Bcast(&len,1,MPIU_SIZE_T,0,PETSC_COMM_WORLD);
637:     } else {
638:       MPI_Bcast(&len,1,MPIU_SIZE_T,0,PETSC_COMM_WORLD);
639:       if (len) {
640:         PetscMalloc((len+1)*sizeof(char*),&eoptions);
641:       }
642:     }
643:     if (len) {
644:       MPI_Bcast(eoptions,len,MPI_CHAR,0,PETSC_COMM_WORLD);
645:       if (rank) eoptions[len] = 0;
646:       PetscOptionsInsertString(eoptions);
647:       if (rank) {PetscFree(eoptions);}
648:     }
649:   }

651: #if defined(PETSC_HAVE_YAML)
652:   char      yaml_file[PETSC_MAX_PATH_LEN];
653:   PetscBool yaml_flg = PETSC_FALSE;
654:   PetscOptionsGetString(NULL,"-options_file_yaml",yaml_file,PETSC_MAX_PATH_LEN,&yaml_flg);
655:   if (yaml_flg) PetscOptionsInsertFileYAML(PETSC_COMM_WORLD,yaml_file,PETSC_TRUE);
656: #endif

658:   /* insert command line options again because they take precedence over arguments in petscrc/environment */
659:   if (argc && args && *argc) {PetscOptionsInsertArgs_Private(*argc,*args);}
660:   return(0);
661: }

665: /*@C
666:    PetscOptionsView - Prints the options that have been loaded. This is
667:    useful for debugging purposes.

669:    Logically Collective on PetscViewer

671:    Input Parameter:
672: .  viewer - must be an PETSCVIEWERASCII viewer

674:    Options Database Key:
675: .  -options_table - Activates PetscOptionsView() within PetscFinalize()

677:    Level: advanced

679:    Concepts: options database^printing

681: .seealso: PetscOptionsAllUsed()
682: @*/
683: PetscErrorCode  PetscOptionsView(PetscViewer viewer)
684: {
686:   PetscInt       i;
687:   PetscBool      isascii;

690:   if (!viewer) viewer = PETSC_VIEWER_STDOUT_WORLD;
691:   PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&isascii);
692:   if (!isascii) SETERRQ(PetscObjectComm((PetscObject)viewer),PETSC_ERR_SUP,"Only supports ASCII viewer");

694:   if (!options) {PetscOptionsInsert(0,0,0);}
695:   if (options->N) {
696:     PetscViewerASCIIPrintf(viewer,"#PETSc Option Table entries:\n");
697:   } else {
698:     PetscViewerASCIIPrintf(viewer,"#No PETSc Option Table entries\n");
699:   }
700:   for (i=0; i<options->N; i++) {
701:     if (options->values[i]) {
702:       PetscViewerASCIIPrintf(viewer,"-%s %s\n",options->names[i],options->values[i]);
703:     } else {
704:       PetscViewerASCIIPrintf(viewer,"-%s\n",options->names[i]);
705:     }
706:   }
707:   if (options->N) {
708:     PetscViewerASCIIPrintf(viewer,"#End of PETSc Option Table entries\n");
709:   }
710:   return(0);
711: }

715: /*@C
716:    PetscOptionsGetAll - Lists all the options the program was run with in a single string.

718:    Not Collective

720:    Output Parameter:
721: .  copts - pointer where string pointer is stored

723:    Notes: the array and each entry in the array should be freed with PetscFree()

725:    Level: advanced

727:    Concepts: options database^listing

729: .seealso: PetscOptionsAllUsed(), PetscOptionsView()
730: @*/
731: PetscErrorCode  PetscOptionsGetAll(char *copts[])
732: {
734:   PetscInt       i;
735:   size_t         len       = 1,lent = 0;
736:   char           *coptions = NULL;

739:   if (!options) {PetscOptionsInsert(0,0,0);}

741:   /* count the length of the required string */
742:   for (i=0; i<options->N; i++) {
743:     PetscStrlen(options->names[i],&lent);
744:     len += 2 + lent;
745:     if (options->values[i]) {
746:       PetscStrlen(options->values[i],&lent);
747:       len += 1 + lent;
748:     }
749:   }
750:   PetscMalloc(len*sizeof(char),&coptions);
751:   coptions[0] = 0;
752:   for (i=0; i<options->N; i++) {
753:     PetscStrcat(coptions,"-");
754:     PetscStrcat(coptions,options->names[i]);
755:     PetscStrcat(coptions," ");
756:     if (options->values[i]) {
757:       PetscStrcat(coptions,options->values[i]);
758:       PetscStrcat(coptions," ");
759:     }
760:   }
761:   *copts = coptions;
762:   return(0);
763: }

767: /*@
768:    PetscOptionsPrefixPush - Designate a prefix to be used by all options insertions to follow.

770:    Not Collective, but prefix will only be applied on calling ranks

772:    Input Parameter:
773: .  prefix - The string to append to the existing prefix

775:    Options Database Keys:
776:  +   -prefix_push <some_prefix_> - push the given prefix
777:  -   -prefix_pop - pop the last prefix

779:    Notes:
780:    It is common to use this in conjunction with -options_file as in

782:  $ -prefix_push system1_ -options_file system1rc -prefix_pop -prefix_push system2_ -options_file system2rc -prefix_pop

784:    where the files no longer require all options to be prefixed with -system2_.

786: Level: advanced

788: .seealso: PetscOptionsPrefixPop()
789: @*/
790: PetscErrorCode  PetscOptionsPrefixPush(const char prefix[])
791: {
793:   size_t         n;
794:   PetscInt       start;
795:   char           buf[2048];
796:   PetscBool      key;

800:   /* Want to check validity of the key using PetscOptionsValidKey(), which requires that the first character is a '-' */
801:   buf[0] = '-';
802:   PetscStrncpy(buf+1,prefix,sizeof(buf) - 1);
803:   buf[sizeof(buf) - 1] = 0;
804:   PetscOptionsValidKey(buf,&key);
805:   if (!key) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_USER,"Given prefix \"%s\" not valid (the first character must be a letter, do not include leading '-')",prefix);

807:   if (!options) {PetscOptionsInsert(0,0,0);}
808:   if (options->prefixind >= MAXPREFIXES) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Maximum depth of prefix stack %d exceeded, recompile \n src/sys/objects/options.c with larger value for MAXPREFIXES",MAXPREFIXES);
809:   start = options->prefixind ? options->prefixstack[options->prefixind-1] : 0;
810:   PetscStrlen(prefix,&n);
811:   if (n+1 > sizeof(options->prefix)-start) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Maximum prefix length %d exceeded",sizeof(options->prefix));
812:   PetscMemcpy(options->prefix+start,prefix,n+1);
813:   options->prefixstack[options->prefixind++] = start+n;
814:   return(0);
815: }

819: /*@
820:    PetscOptionsPrefixPop - Remove the latest options prefix, see PetscOptionsPrefixPush() for details

822:    Not  Collective, but prefix will only be popped on calling ranks

824:    Level: advanced

826: .seealso: PetscOptionsPrefixPush()
827: @*/
828: PetscErrorCode  PetscOptionsPrefixPop(void)
829: {
830:   PetscInt offset;

833:   if (options->prefixind < 1) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"More prefixes popped than pushed");
834:   options->prefixind--;
835:   offset = options->prefixind ? options->prefixstack[options->prefixind-1] : 0;
836:   options->prefix[offset] = 0;
837:   return(0);
838: }

842: /*@C
843:     PetscOptionsClear - Removes all options form the database leaving it empty.

845:    Level: developer

847: .seealso: PetscOptionsInsert()
848: @*/
849: PetscErrorCode  PetscOptionsClear(void)
850: {
851:   PetscInt i;

854:   if (!options) return(0);
855:   for (i=0; i<options->N; i++) {
856:     if (options->names[i])  free(options->names[i]);
857:     if (options->values[i]) free(options->values[i]);
858:   }
859:   for (i=0; i<options->Naliases; i++) {
860:     free(options->aliases1[i]);
861:     free(options->aliases2[i]);
862:   }
863:   options->prefix[0] = 0;
864:   options->prefixind = 0;
865:   options->N         = 0;
866:   options->Naliases  = 0;
867:   return(0);
868: }

872: /*@C
873:     PetscOptionsDestroy - Destroys the option database.

875:     Note:
876:     Since PetscOptionsDestroy() is called by PetscFinalize(), the user
877:     typically does not need to call this routine.

879:    Level: developer

881: .seealso: PetscOptionsInsert()
882: @*/
883: PetscErrorCode  PetscOptionsDestroy(void)
884: {

888:   if (!options) return(0);
889:   PetscOptionsClear();
890:   free(options);
891:   options = 0;
892:   return(0);
893: }

897: /*@C
898:    PetscOptionsSetValue - Sets an option name-value pair in the options
899:    database, overriding whatever is already present.

901:    Not collective, but setting values on certain processors could cause problems
902:    for parallel objects looking for options.

904:    Input Parameters:
905: +  name - name of option, this SHOULD have the - prepended
906: -  value - the option value (not used for all options)

908:    Level: intermediate

910:    Note:
911:    Only some options have values associated with them, such as
912:    -ksp_rtol tol.  Other options stand alone, such as -ksp_monitor.

914:   Developers Note: Uses malloc() directly because PETSc may not yet have been fully initialized

916:   Concepts: options database^adding option

918: .seealso: PetscOptionsInsert()
919: @*/
920: PetscErrorCode  PetscOptionsSetValue(const char iname[],const char value[])
921: {
922:   size_t         len;
924:   PetscInt       N,n,i;
925:   char           **names;
926:   char           fullname[2048];
927:   const char     *name = iname;
928:   PetscBool      gt,match;

931:   if (!options) {PetscOptionsInsert(0,0,0);}

933:   /* this is so that -h and -hel\p are equivalent (p4 does not like -help)*/
934:   PetscStrcasecmp(name,"-h",&match);
935:   if (match) name = "-help";

937:   name++; /* skip starting hyphen */
938:   if (options->prefixind > 0) {
939:     PetscStrncpy(fullname,options->prefix,sizeof(fullname));
940:     PetscStrncat(fullname,name,sizeof(fullname));
941:     name = fullname;
942:   }

944:   /* check against aliases */
945:   N = options->Naliases;
946:   for (i=0; i<N; i++) {
947:     PetscStrcasecmp(options->aliases1[i],name,&match);
948:     if (match) {
949:       name = options->aliases2[i];
950:       break;
951:     }
952:   }

954:   N     = options->N;
955:   n     = N;
956:   names = options->names;

958:   for (i=0; i<N; i++) {
959:     PetscStrcasecmp(names[i],name,&match);
960:     PetscStrgrt(names[i],name,&gt);
961:     if (match) {
962:       if (options->values[i]) free(options->values[i]);
963:       PetscStrlen(value,&len);
964:       if (len) {
965:         options->values[i] = (char*)malloc((len+1)*sizeof(char));
966:         PetscStrcpy(options->values[i],value);
967:       } else options->values[i] = 0;
968:       PetscOptionsMonitor(name,value);
969:       return(0);
970:     } else if (gt) {
971:       n = i;
972:       break;
973:     }
974:   }
975:   if (N >= MAXOPTIONS) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_PLIB,"No more room in option table, limit %d recompile \n src/sys/objects/options.c with larger value for MAXOPTIONS\n",MAXOPTIONS);

977:   /* shift remaining values down 1 */
978:   for (i=N; i>n; i--) {
979:     options->names[i]  = options->names[i-1];
980:     options->values[i] = options->values[i-1];
981:     options->used[i]   = options->used[i-1];
982:   }
983:   /* insert new name and value */
984:   PetscStrlen(name,&len);
985:   options->names[n] = (char*)malloc((len+1)*sizeof(char));
986:   PetscStrcpy(options->names[n],name);
987:   PetscStrlen(value,&len);
988:   if (len) {
989:     options->values[n] = (char*)malloc((len+1)*sizeof(char));
990:     PetscStrcpy(options->values[n],value);
991:   } else options->values[n] = 0;
992:   options->used[n] = PETSC_FALSE;
993:   options->N++;
994:   PetscOptionsMonitor(name,value);
995:   return(0);
996: }

1000: /*@C
1001:    PetscOptionsClearValue - Clears an option name-value pair in the options
1002:    database, overriding whatever is already present.

1004:    Not Collective, but setting values on certain processors could cause problems
1005:    for parallel objects looking for options.

1007:    Input Parameter:
1008: .  name - name of option, this SHOULD have the - prepended

1010:    Level: intermediate

1012:    Concepts: options database^removing option
1013: .seealso: PetscOptionsInsert()
1014: @*/
1015: PetscErrorCode  PetscOptionsClearValue(const char iname[])
1016: {
1018:   PetscInt       N,n,i;
1019:   char           **names,*name=(char*)iname;
1020:   PetscBool      gt,match;

1023:   if (name[0] != '-') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Name must begin with -: Instead %s",name);
1024:   if (!options) {PetscOptionsInsert(0,0,0);}

1026:   name++;

1028:   N     = options->N; n = 0;
1029:   names = options->names;

1031:   for (i=0; i<N; i++) {
1032:     PetscStrcasecmp(names[i],name,&match);
1033:     PetscStrgrt(names[i],name,&gt);
1034:     if (match) {
1035:       if (options->names[i])  free(options->names[i]);
1036:       if (options->values[i]) free(options->values[i]);
1037:       PetscOptionsMonitor(name,"");
1038:       break;
1039:     } else if (gt) return(0); /* it was not listed */

1041:     n++;
1042:   }
1043:   if (n == N) return(0); /* it was not listed */

1045:   /* shift remaining values down 1 */
1046:   for (i=n; i<N-1; i++) {
1047:     options->names[i]  = options->names[i+1];
1048:     options->values[i] = options->values[i+1];
1049:     options->used[i]   = options->used[i+1];
1050:   }
1051:   options->N--;
1052:   return(0);
1053: }

1057: /*@C
1058:    PetscOptionsSetAlias - Makes a key and alias for another key

1060:    Not Collective, but setting values on certain processors could cause problems
1061:    for parallel objects looking for options.

1063:    Input Parameters:
1064: +  inewname - the alias
1065: -  ioldname - the name that alias will refer to

1067:    Level: advanced

1069: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),OptionsHasName(),
1070:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(),PetscOptionsBool(),
1071:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1072:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1073:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1074:           PetscOptionsList(), PetscOptionsEList()
1075: @*/
1076: PetscErrorCode  PetscOptionsSetAlias(const char inewname[],const char ioldname[])
1077: {
1079:   PetscInt       n = options->Naliases;
1080:   size_t         len;
1081:   char           *newname = (char*)inewname,*oldname = (char*)ioldname;

1084:   if (newname[0] != '-') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"aliased must have -: Instead %s",newname);
1085:   if (oldname[0] != '-') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"aliasee must have -: Instead %s",oldname);
1086:   if (n >= MAXALIASES) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_MEM,"You have defined to many PETSc options aliases, limit %d recompile \n  src/sys/objects/options.c with larger value for MAXALIASES",MAXALIASES);

1088:   newname++; oldname++;
1089:   PetscStrlen(newname,&len);
1090:   options->aliases1[n] = (char*)malloc((len+1)*sizeof(char));
1091:   PetscStrcpy(options->aliases1[n],newname);
1092:   PetscStrlen(oldname,&len);
1093:   options->aliases2[n] = (char*)malloc((len+1)*sizeof(char));
1094:   PetscStrcpy(options->aliases2[n],oldname);
1095:   options->Naliases++;
1096:   return(0);
1097: }

1101: PetscErrorCode PetscOptionsFindPair_Private(const char pre[],const char name[],char *value[],PetscBool  *flg)
1102: {
1104:   PetscInt       i,N;
1105:   size_t         len;
1106:   char           **names,tmp[256];
1107:   PetscBool      match;

1110:   if (!options) {PetscOptionsInsert(0,0,0);}
1111:   N     = options->N;
1112:   names = options->names;

1114:   if (name[0] != '-') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Name must begin with -: Instead %s",name);

1116:   /* append prefix to name, if prefix="foo_" and option='--bar", prefixed option is --foo_bar */
1117:   if (pre) {
1118:     char       *ptr   = tmp;
1119:     const char *namep = name;
1120:     if (pre[0] == '-') SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Prefix should not begin with a -");
1121:     if (name[1] == '-') {
1122:       *ptr++ = '-';
1123:       namep++;
1124:     }
1125:     PetscStrncpy(ptr,pre,tmp+sizeof(tmp)-ptr);
1126:     tmp[sizeof(tmp)-1] = 0;
1127:     PetscStrlen(tmp,&len);
1128:     PetscStrncat(tmp,namep+1,sizeof(tmp)-len-1);
1129:   } else {
1130:     PetscStrncpy(tmp,name+1,sizeof(tmp));
1131:     tmp[sizeof(tmp)-1] = 0;
1132:   }
1133: #if defined(PETSC_USE_DEBUG)
1134:   {
1135:     PetscBool valid;
1136:     char      key[sizeof(tmp)+1] = "-";

1138:     PetscMemcpy(key+1,tmp,sizeof(tmp));
1139:     PetscOptionsValidKey(key,&valid);
1140:     if (!valid) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Invalid option '%s' obtained from pre='%s' and name='%s'",key,pre?pre:"",name);
1141:   }
1142: #endif

1144:   /* slow search */
1145:   *flg = PETSC_FALSE;
1146:   for (i=0; i<N; i++) {
1147:     PetscStrcasecmp(names[i],tmp,&match);
1148:     if (match) {
1149:       *value           = options->values[i];
1150:       options->used[i] = PETSC_TRUE;
1151:       *flg             = PETSC_TRUE;
1152:       break;
1153:     }
1154:   }
1155:   if (!*flg) {
1156:     PetscInt j,cnt = 0,locs[16],loce[16];
1157:     size_t   n;
1158:     PetscStrlen(tmp,&n);
1159:     /* determine the location and number of all _%d_ in the key */
1160:     for (i=0; i< (PetscInt)n; i++) {
1161:       if (tmp[i] == '_') {
1162:         for (j=i+1; j< (PetscInt)n; j++) {
1163:           if (tmp[j] >= '0' && tmp[j] <= '9') continue;
1164:           if (tmp[j] == '_' && j > i+1) { /* found a number */
1165:             locs[cnt]   = i+1;
1166:             loce[cnt++] = j+1;
1167:           }
1168:           break;
1169:         }
1170:       }
1171:     }
1172:     if (cnt) {
1173:       char tmp2[256];
1174:       for (i=0; i<cnt; i++) {
1175:         PetscStrcpy(tmp2,"-");
1176:         PetscStrncat(tmp2,tmp,locs[i]);
1177:         PetscStrcat(tmp2,tmp+loce[i]);
1178:         PetscOptionsFindPair_Private(NULL,tmp2,value,flg);
1179:         if (*flg) break;
1180:       }
1181:     }
1182:   }
1183:   return(0);
1184: }

1188: PETSC_EXTERN PetscErrorCode PetscOptionsFindPairPrefix_Private(const char pre[], const char name[], char *value[], PetscBool *flg)
1189: {
1191:   PetscInt       i,N;
1192:   size_t         len;
1193:   char           **names,tmp[256];
1194:   PetscBool      match;

1197:   if (!options) {PetscOptionsInsert(0,0,0);}
1198:   N     = options->N;
1199:   names = options->names;

1201:   if (name[0] != '-') SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Name must begin with -: Instead %s",name);

1203:   /* append prefix to name, if prefix="foo_" and option='--bar", prefixed option is --foo_bar */
1204:   if (pre) {
1205:     char       *ptr   = tmp;
1206:     const char *namep = name;
1207:     if (pre[0] == '-') SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Prefix should not begin with a -");
1208:     if (name[1] == '-') {
1209:       *ptr++ = '-';
1210:       namep++;
1211:     }
1212:     PetscStrncpy(ptr,pre,tmp+sizeof(tmp)-ptr);
1213:     tmp[sizeof(tmp)-1] = 0;
1214:     PetscStrlen(tmp,&len);
1215:     PetscStrncat(tmp,namep+1,sizeof(tmp)-len-1);
1216:   } else {
1217:     PetscStrncpy(tmp,name+1,sizeof(tmp));
1218:     tmp[sizeof(tmp)-1] = 0;
1219:   }
1220: #if defined(PETSC_USE_DEBUG)
1221:   {
1222:     PetscBool valid;
1223:     char      key[sizeof(tmp)+1] = "-";

1225:     PetscMemcpy(key+1,tmp,sizeof(tmp));
1226:     PetscOptionsValidKey(key,&valid);
1227:     if (!valid) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Invalid option '%s' obtained from pre='%s' and name='%s'",key,pre?pre:"",name);
1228:   }
1229: #endif

1231:   /* slow search */
1232:   *flg = PETSC_FALSE;
1233:   PetscStrlen(tmp,&len);
1234:   for (i = 0; i < N; ++i) {
1235:     PetscStrncmp(names[i], tmp, len, &match);
1236:     if (match) {
1237:       if (value) *value = options->values[i];
1238:       options->used[i]  = PETSC_TRUE;
1239:       if (flg)   *flg   = PETSC_TRUE;
1240:       break;
1241:     }
1242:   }
1243:   return(0);
1244: }

1248: /*@C
1249:    PetscOptionsReject - Generates an error if a certain option is given.

1251:    Not Collective, but setting values on certain processors could cause problems
1252:    for parallel objects looking for options.

1254:    Input Parameters:
1255: +  name - the option one is seeking
1256: -  mess - error message (may be NULL)

1258:    Level: advanced

1260:    Concepts: options database^rejecting option

1262: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),OptionsHasName(),
1263:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1264:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1265:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1266:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1267:           PetscOptionsList(), PetscOptionsEList()
1268: @*/
1269: PetscErrorCode  PetscOptionsReject(const char name[],const char mess[])
1270: {
1272:   PetscBool      flag = PETSC_FALSE;

1275:   PetscOptionsHasName(NULL,name,&flag);
1276:   if (flag) {
1277:     if (mess) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Program has disabled option: %s with %s",name,mess);
1278:     else SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Program has disabled option: %s",name);
1279:   }
1280:   return(0);
1281: }

1285: /*@C
1286:    PetscOptionsHasName - Determines whether a certain option is given in the database. This returns true whether the option is a number, string or boolean, even
1287:                       its value is set to false.

1289:    Not Collective

1291:    Input Parameters:
1292: +  name - the option one is seeking
1293: -  pre - string to prepend to the name or NULL

1295:    Output Parameters:
1296: .  set - PETSC_TRUE if found else PETSC_FALSE.

1298:    Level: beginner

1300:    Concepts: options database^has option name

1302:    Notes: Name cannot be simply -h

1304:           In many cases you probably want to use PetscOptionsGetBool() instead of calling this, to allowing toggling values.

1306: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),
1307:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1308:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1309:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1310:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1311:           PetscOptionsList(), PetscOptionsEList()
1312: @*/
1313: PetscErrorCode  PetscOptionsHasName(const char pre[],const char name[],PetscBool  *set)
1314: {
1315:   char           *value;
1317:   PetscBool      flag;

1320:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1321:   if (set) *set = flag;
1322:   return(0);
1323: }

1327: /*@C
1328:    PetscOptionsGetInt - Gets the integer value for a particular option in the database.

1330:    Not Collective

1332:    Input Parameters:
1333: +  pre - the string to prepend to the name or NULL
1334: -  name - the option one is seeking

1336:    Output Parameter:
1337: +  ivalue - the integer value to return
1338: -  set - PETSC_TRUE if found, else PETSC_FALSE

1340:    Level: beginner

1342:    Concepts: options database^has int

1344: .seealso: PetscOptionsGetReal(), PetscOptionsHasName(), PetscOptionsGetString(),
1345:           PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool()
1346:           PetscOptionsInt(), PetscOptionsString(), PetscOptionsReal(), PetscOptionsBool(),
1347:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1348:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1349:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1350:           PetscOptionsList(), PetscOptionsEList()
1351: @*/
1352: PetscErrorCode  PetscOptionsGetInt(const char pre[],const char name[],PetscInt *ivalue,PetscBool  *set)
1353: {
1354:   char           *value;
1356:   PetscBool      flag;

1361:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1362:   if (flag) {
1363:     if (!value) {
1364:       if (set) *set = PETSC_FALSE;
1365:     } else {
1366:       if (set) *set = PETSC_TRUE;
1367:       PetscOptionsStringToInt(value,ivalue);
1368:     }
1369:   } else {
1370:     if (set) *set = PETSC_FALSE;
1371:   }
1372:   return(0);
1373: }

1377: /*@C
1378:      PetscOptionsGetEList - Puts a list of option values that a single one may be selected from

1380:    Not Collective

1382:    Input Parameters:
1383: +  pre - the string to prepend to the name or NULL
1384: .  opt - option name
1385: .  list - the possible choices
1386: .  ntext - number of choices

1388:    Output Parameter:
1389: +  value - the index of the value to return (defaults to zero if the option name is given but choice is listed)
1390: -  set - PETSC_TRUE if found, else PETSC_FALSE

1392:    Level: intermediate

1394:    See PetscOptionsList() for when the choices are given in a PetscFunctionList()

1396:    Concepts: options database^list

1398: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),
1399:            PetscOptionsHasName(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1400:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1401:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1402:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1403:           PetscOptionsList(), PetscOptionsEList()
1404: @*/
1405: PetscErrorCode  PetscOptionsGetEList(const char pre[],const char opt[],const char * const *list,PetscInt ntext,PetscInt *value,PetscBool  *set)
1406: {
1408:   size_t         alen,len = 0;
1409:   char           *svalue;
1410:   PetscBool      aset,flg = PETSC_FALSE;
1411:   PetscInt       i;

1414:   for (i=0; i<ntext; i++) {
1415:     PetscStrlen(list[i],&alen);
1416:     if (alen > len) len = alen;
1417:   }
1418:   len += 5; /* a little extra space for user mistypes */
1419:   PetscMalloc(len*sizeof(char),&svalue);
1420:   PetscOptionsGetString(pre,opt,svalue,len,&aset);
1421:   if (aset) {
1422:     PetscEListFind(ntext,list,svalue,value,&flg);
1423:     if (!flg) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_USER,"Unknown option %s for -%s%s",svalue,pre ? pre : "",opt+1);
1424:     if (set) *set = PETSC_TRUE;
1425:   } else if (set) *set = PETSC_FALSE;
1426:   PetscFree(svalue);
1427:   return(0);
1428: }

1432: /*@C
1433:    PetscOptionsGetEnum - Gets the enum value for a particular option in the database.

1435:    Not Collective

1437:    Input Parameters:
1438: +  pre - option prefix or NULL
1439: .  opt - option name
1440: .  list - array containing the list of choices, followed by the enum name, followed by the enum prefix, followed by a null
1441: -  defaultv - the default (current) value

1443:    Output Parameter:
1444: +  value - the  value to return
1445: -  set - PETSC_TRUE if found, else PETSC_FALSE

1447:    Level: beginner

1449:    Concepts: options database

1451:    Notes: Must be between a PetscOptionsBegin() and a PetscOptionsEnd()

1453:           list is usually something like PCASMTypes or some other predefined list of enum names

1455: .seealso: PetscOptionsGetReal(), PetscOptionsHasName(), PetscOptionsGetString(), PetscOptionsGetInt(),
1456:           PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool()
1457:           PetscOptionsInt(), PetscOptionsString(), PetscOptionsReal(), PetscOptionsBool(),
1458:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1459:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1460:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1461:           PetscOptionsList(), PetscOptionsEList(), PetscOptionsGetEList(), PetscOptionsEnum()
1462: @*/
1463: PetscErrorCode  PetscOptionsGetEnum(const char pre[],const char opt[],const char * const *list,PetscEnum *value,PetscBool  *set)
1464: {
1466:   PetscInt       ntext = 0,tval;
1467:   PetscBool      fset;

1470:   while (list[ntext++]) {
1471:     if (ntext > 50) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"List argument appears to be wrong or have more than 50 entries");
1472:   }
1473:   if (ntext < 3) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"List argument must have at least two entries: typename and type prefix");
1474:   ntext -= 3;
1475:   PetscOptionsGetEList(pre,opt,list,ntext,&tval,&fset);
1476:   /* with PETSC_USE_64BIT_INDICES sizeof(PetscInt) != sizeof(PetscEnum) */
1477:   if (fset) *value = (PetscEnum)tval;
1478:   if (set) *set = fset;
1479:   return(0);
1480: }

1484: /*@C
1485:    PetscOptionsGetBool - Gets the Logical (true or false) value for a particular
1486:             option in the database.

1488:    Not Collective

1490:    Input Parameters:
1491: +  pre - the string to prepend to the name or NULL
1492: -  name - the option one is seeking

1494:    Output Parameter:
1495: +  ivalue - the logical value to return
1496: -  set - PETSC_TRUE  if found, else PETSC_FALSE

1498:    Level: beginner

1500:    Notes:
1501:        TRUE, true, YES, yes, nostring, and 1 all translate to PETSC_TRUE
1502:        FALSE, false, NO, no, and 0 all translate to PETSC_FALSE

1504:        If the user does not supply the option (as either true or false) ivalue is NOT changed. Thus
1505:      you NEED TO ALWAYS initialize the ivalue.

1507:    Concepts: options database^has logical

1509: .seealso: PetscOptionsGetReal(), PetscOptionsHasName(), PetscOptionsGetString(),
1510:           PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsGetInt(), PetscOptionsBool(),
1511:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1512:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1513:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1514:           PetscOptionsList(), PetscOptionsEList()
1515: @*/
1516: PetscErrorCode  PetscOptionsGetBool(const char pre[],const char name[],PetscBool  *ivalue,PetscBool  *set)
1517: {
1518:   char           *value;
1519:   PetscBool      flag;

1525:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1526:   if (flag) {
1527:     if (set) *set = PETSC_TRUE;
1528:     if (!value) *ivalue = PETSC_TRUE;
1529:     else {
1530:       PetscOptionsStringToBool(value, ivalue);
1531:     }
1532:   } else {
1533:     if (set) *set = PETSC_FALSE;
1534:   }
1535:   return(0);
1536: }

1540: /*@C
1541:    PetscOptionsGetBoolArray - Gets an array of Logical (true or false) values for a particular
1542:    option in the database.  The values must be separated with commas with
1543:    no intervening spaces.

1545:    Not Collective

1547:    Input Parameters:
1548: +  pre - string to prepend to each name or NULL
1549: .  name - the option one is seeking
1550: -  nmax - maximum number of values to retrieve

1552:    Output Parameter:
1553: +  dvalue - the integer values to return
1554: .  nmax - actual number of values retreived
1555: -  set - PETSC_TRUE if found, else PETSC_FALSE

1557:    Level: beginner

1559:    Concepts: options database^array of ints

1561:    Notes:
1562:        TRUE, true, YES, yes, nostring, and 1 all translate to PETSC_TRUE
1563:        FALSE, false, NO, no, and 0 all translate to PETSC_FALSE

1565: .seealso: PetscOptionsGetInt(), PetscOptionsHasName(),
1566:            PetscOptionsGetString(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1567:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1568:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1569:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1570:           PetscOptionsList(), PetscOptionsEList()
1571: @*/
1572: PetscErrorCode  PetscOptionsGetBoolArray(const char pre[],const char name[],PetscBool dvalue[],PetscInt *nmax,PetscBool  *set)
1573: {
1574:   char           *value;
1576:   PetscInt       n = 0;
1577:   PetscBool      flag;
1578:   PetscToken     token;

1583:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1584:   if (!flag)  {if (set) *set = PETSC_FALSE; *nmax = 0; return(0);}
1585:   if (!value) {if (set) *set = PETSC_TRUE;  *nmax = 0; return(0);}

1587:   if (set) *set = PETSC_TRUE;

1589:   PetscTokenCreate(value,',',&token);
1590:   PetscTokenFind(token,&value);
1591:   while (n < *nmax) {
1592:     if (!value) break;
1593:     PetscOptionsStringToBool(value,dvalue);
1594:     PetscTokenFind(token,&value);
1595:     dvalue++;
1596:     n++;
1597:   }
1598:   PetscTokenDestroy(&token);
1599:   *nmax = n;
1600:   return(0);
1601: }

1605: /*@C
1606:    PetscOptionsGetReal - Gets the double precision value for a particular
1607:    option in the database.

1609:    Not Collective

1611:    Input Parameters:
1612: +  pre - string to prepend to each name or NULL
1613: -  name - the option one is seeking

1615:    Output Parameter:
1616: +  dvalue - the double value to return
1617: -  set - PETSC_TRUE if found, PETSC_FALSE if not found

1619:    Note: if the option is given but no value is provided then set is given the value PETSC_FALSE

1621:    Level: beginner

1623:    Concepts: options database^has double

1625: .seealso: PetscOptionsGetInt(), PetscOptionsHasName(),
1626:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(),PetscOptionsBool(),
1627:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1628:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1629:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1630:           PetscOptionsList(), PetscOptionsEList()
1631: @*/
1632: PetscErrorCode  PetscOptionsGetReal(const char pre[],const char name[],PetscReal *dvalue,PetscBool  *set)
1633: {
1634:   char           *value;
1636:   PetscBool      flag;

1641:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1642:   if (flag) {
1643:     if (!value) {
1644:       if (set) *set = PETSC_FALSE;
1645:     } else {
1646:       if (set) *set = PETSC_TRUE;
1647:       PetscOptionsStringToReal(value,dvalue);
1648:     }
1649:   } else {
1650:     if (set) *set = PETSC_FALSE;
1651:   }
1652:   return(0);
1653: }

1657: /*@C
1658:    PetscOptionsGetScalar - Gets the scalar value for a particular
1659:    option in the database.

1661:    Not Collective

1663:    Input Parameters:
1664: +  pre - string to prepend to each name or NULL
1665: -  name - the option one is seeking

1667:    Output Parameter:
1668: +  dvalue - the double value to return
1669: -  set - PETSC_TRUE if found, else PETSC_FALSE

1671:    Level: beginner

1673:    Usage:
1674:    A complex number 2+3i can be specified as 2,3 at the command line.
1675:    or a number 2.0e-10 - 3.3e-20 i  can be specified as 2.0e-10,-3.3e-20

1677:    Note: if the option is given but no value is provided then set is given the value PETSC_FALSE

1679:    Concepts: options database^has scalar

1681: .seealso: PetscOptionsGetInt(), PetscOptionsHasName(),
1682:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1683:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1684:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1685:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1686:           PetscOptionsList(), PetscOptionsEList()
1687: @*/
1688: PetscErrorCode  PetscOptionsGetScalar(const char pre[],const char name[],PetscScalar *dvalue,PetscBool  *set)
1689: {
1690:   char           *value;
1691:   PetscBool      flag;

1697:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1698:   if (flag) {
1699:     if (!value) {
1700:       if (set) *set = PETSC_FALSE;
1701:     } else {
1702: #if !defined(PETSC_USE_COMPLEX)
1703:       PetscOptionsStringToReal(value,dvalue);
1704: #else
1705:       PetscReal  re=0.0,im=0.0;
1706:       PetscToken token;
1707:       char       *tvalue = 0;

1709:       PetscTokenCreate(value,',',&token);
1710:       PetscTokenFind(token,&tvalue);
1711:       if (!tvalue) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"unknown string specified\n");
1712:       PetscOptionsStringToReal(tvalue,&re);
1713:       PetscTokenFind(token,&tvalue);
1714:       if (!tvalue) *dvalue = re; /* Unknown separator used. using only real value */
1715:       else {
1716:         PetscOptionsStringToReal(tvalue,&im);
1717:         *dvalue = re + PETSC_i*im;
1718:       }
1719:       PetscTokenDestroy(&token);
1720: #endif
1721:       if (set) *set = PETSC_TRUE;
1722:     }
1723:   } else { /* flag */
1724:     if (set) *set = PETSC_FALSE;
1725:   }
1726:   return(0);
1727: }

1731: /*@C
1732:    PetscOptionsGetRealArray - Gets an array of double precision values for a
1733:    particular option in the database.  The values must be separated with
1734:    commas with no intervening spaces.

1736:    Not Collective

1738:    Input Parameters:
1739: +  pre - string to prepend to each name or NULL
1740: .  name - the option one is seeking
1741: -  nmax - maximum number of values to retrieve

1743:    Output Parameters:
1744: +  dvalue - the double value to return
1745: .  nmax - actual number of values retreived
1746: -  set - PETSC_TRUE if found, else PETSC_FALSE

1748:    Level: beginner

1750:    Concepts: options database^array of doubles

1752: .seealso: PetscOptionsGetInt(), PetscOptionsHasName(),
1753:            PetscOptionsGetString(), PetscOptionsGetIntArray(), PetscOptionsBool(),
1754:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1755:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1756:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1757:           PetscOptionsList(), PetscOptionsEList()
1758: @*/
1759: PetscErrorCode  PetscOptionsGetRealArray(const char pre[],const char name[],PetscReal dvalue[],PetscInt *nmax,PetscBool  *set)
1760: {
1761:   char           *value;
1763:   PetscInt       n = 0;
1764:   PetscBool      flag;
1765:   PetscToken     token;

1770:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1771:   if (!flag) {
1772:     if (set) *set = PETSC_FALSE;
1773:     *nmax = 0;
1774:     return(0);
1775:   }
1776:   if (!value) {
1777:     if (set) *set = PETSC_TRUE;
1778:     *nmax = 0;
1779:     return(0);
1780:   }

1782:   if (set) *set = PETSC_TRUE;

1784:   PetscTokenCreate(value,',',&token);
1785:   PetscTokenFind(token,&value);
1786:   while (n < *nmax) {
1787:     if (!value) break;
1788:     PetscOptionsStringToReal(value,dvalue++);
1789:     PetscTokenFind(token,&value);
1790:     n++;
1791:   }
1792:   PetscTokenDestroy(&token);
1793:   *nmax = n;
1794:   return(0);
1795: }

1799: /*@C
1800:    PetscOptionsGetIntArray - Gets an array of integer values for a particular
1801:    option in the database.

1803:    Not Collective

1805:    Input Parameters:
1806: +  pre - string to prepend to each name or NULL
1807: .  name - the option one is seeking
1808: -  nmax - maximum number of values to retrieve

1810:    Output Parameter:
1811: +  dvalue - the integer values to return
1812: .  nmax - actual number of values retreived
1813: -  set - PETSC_TRUE if found, else PETSC_FALSE

1815:    Level: beginner

1817:    Notes:
1818:    The array can be passed as
1819:    a comma seperated list:                                 0,1,2,3,4,5,6,7
1820:    a range (start-end+1):                                  0-8
1821:    a range with given increment (start-end+1:inc):         0-7:2
1822:    a combination of values and ranges seperated by commas: 0,1-8,8-15:2

1824:    There must be no intervening spaces between the values.

1826:    Concepts: options database^array of ints

1828: .seealso: PetscOptionsGetInt(), PetscOptionsHasName(),
1829:            PetscOptionsGetString(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1830:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1831:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1832:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1833:           PetscOptionsList(), PetscOptionsEList()
1834: @*/
1835: PetscErrorCode  PetscOptionsGetIntArray(const char pre[],const char name[],PetscInt dvalue[],PetscInt *nmax,PetscBool  *set)
1836: {
1837:   char           *value;
1839:   PetscInt       n = 0,i,j,start,end,inc,nvalues;
1840:   size_t         len;
1841:   PetscBool      flag,foundrange;
1842:   PetscToken     token;

1847:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1848:   if (!flag) {
1849:     if (set) *set = PETSC_FALSE;
1850:     *nmax = 0;
1851:     return(0);
1852:   }
1853:   if (!value) {
1854:     if (set) *set = PETSC_TRUE;
1855:     *nmax = 0;
1856:     return(0);
1857:   }

1859:   if (set) *set = PETSC_TRUE;

1861:   PetscTokenCreate(value,',',&token);
1862:   PetscTokenFind(token,&value);
1863:   while (n < *nmax) {
1864:     if (!value) break;

1866:     /* look for form  d-D where d and D are integers */
1867:     foundrange = PETSC_FALSE;
1868:     PetscStrlen(value,&len);
1869:     if (value[0] == '-') i=2;
1870:     else i=1;
1871:     for (;i<(int)len; i++) {
1872:       if (value[i] == '-') {
1873:         if (i == (int)len-1) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_USER,"Error in %D-th array entry %s\n",n,value);
1874:         value[i] = 0;

1876:         PetscOptionsStringToInt(value,&start);
1877:         inc  = 1;
1878:         j    = i+1;
1879:         for (;j<(int)len; j++) {
1880:           if (value[j] == ':') {
1881:             value[j] = 0;

1883:             PetscOptionsStringToInt(value+j+1,&inc);
1884:             if (inc <= 0) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_USER,"Error in %D-th array entry,%s cannot have negative increment",n,value+j+1);
1885:             break;
1886:           }
1887:         }
1888:         PetscOptionsStringToInt(value+i+1,&end);
1889:         if (end <= start) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_USER,"Error in %D-th array entry, %s-%s cannot have decreasing list",n,value,value+i+1);
1890:         nvalues = (end-start)/inc + (end-start)%inc;
1891:         if (n + nvalues  > *nmax) SETERRQ4(PETSC_COMM_SELF,PETSC_ERR_USER,"Error in %D-th array entry, not enough space left in array (%D) to contain entire range from %D to %D",n,*nmax-n,start,end);
1892:         for (;start<end; start+=inc) {
1893:           *dvalue = start; dvalue++;n++;
1894:         }
1895:         foundrange = PETSC_TRUE;
1896:         break;
1897:       }
1898:     }
1899:     if (!foundrange) {
1900:       PetscOptionsStringToInt(value,dvalue);
1901:       dvalue++;
1902:       n++;
1903:     }
1904:     PetscTokenFind(token,&value);
1905:   }
1906:   PetscTokenDestroy(&token);
1907:   *nmax = n;
1908:   return(0);
1909: }

1913: /*@C
1914:    PetscOptionsGetString - Gets the string value for a particular option in
1915:    the database.

1917:    Not Collective

1919:    Input Parameters:
1920: +  pre - string to prepend to name or NULL
1921: .  name - the option one is seeking
1922: -  len - maximum length of the string including null termination

1924:    Output Parameters:
1925: +  string - location to copy string
1926: -  set - PETSC_TRUE if found, else PETSC_FALSE

1928:    Level: beginner

1930:    Fortran Note:
1931:    The Fortran interface is slightly different from the C/C++
1932:    interface (len is not used).  Sample usage in Fortran follows
1933: .vb
1934:       character *20 string
1935:       integer   flg, ierr
1936:       call PetscOptionsGetString(NULL_CHARACTER,'-s',string,flg,ierr)
1937: .ve

1939:    Notes: if the option is given but no string is provided then an empty string is returned and set is given the value of PETSC_TRUE

1941:    Concepts: options database^string

1943:     Note:
1944:       Even if the user provided no string (for example -optionname -someotheroption) the flag is set to PETSC_TRUE (and the string is fulled with nulls).

1946: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),
1947:            PetscOptionsHasName(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
1948:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
1949:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
1950:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
1951:           PetscOptionsList(), PetscOptionsEList()
1952: @*/
1953: PetscErrorCode  PetscOptionsGetString(const char pre[],const char name[],char string[],size_t len,PetscBool  *set)
1954: {
1955:   char           *value;
1957:   PetscBool      flag;

1962:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
1963:   if (!flag) {
1964:     if (set) *set = PETSC_FALSE;
1965:   } else {
1966:     if (set) *set = PETSC_TRUE;
1967:     if (value) {
1968:       PetscStrncpy(string,value,len);
1969:       string[len-1] = 0;        /* Ensure that the string is NULL terminated */
1970:     } else {
1971:       PetscMemzero(string,len);
1972:     }
1973:   }
1974:   return(0);
1975: }

1979: char *PetscOptionsGetStringMatlab(const char pre[],const char name[])
1980: {
1981:   char           *value;
1983:   PetscBool      flag;

1986:   PetscOptionsFindPair_Private(pre,name,&value,&flag);if (ierr) return(0);
1987:   if (flag) PetscFunctionReturn(value);
1988:   else return(0);
1989: }


1994: /*@C
1995:    PetscOptionsGetStringArray - Gets an array of string values for a particular
1996:    option in the database. The values must be separated with commas with
1997:    no intervening spaces.

1999:    Not Collective

2001:    Input Parameters:
2002: +  pre - string to prepend to name or NULL
2003: .  name - the option one is seeking
2004: -  nmax - maximum number of strings

2006:    Output Parameter:
2007: +  strings - location to copy strings
2008: -  set - PETSC_TRUE if found, else PETSC_FALSE

2010:    Level: beginner

2012:    Notes:
2013:    The user should pass in an array of pointers to char, to hold all the
2014:    strings returned by this function.

2016:    The user is responsible for deallocating the strings that are
2017:    returned. The Fortran interface for this routine is not supported.

2019:    Contributed by Matthew Knepley.

2021:    Concepts: options database^array of strings

2023: .seealso: PetscOptionsGetInt(), PetscOptionsGetReal(),
2024:            PetscOptionsHasName(), PetscOptionsGetIntArray(), PetscOptionsGetRealArray(), PetscOptionsBool(),
2025:           PetscOptionsName(), PetscOptionsBegin(), PetscOptionsEnd(), PetscOptionsHead(),
2026:           PetscOptionsStringArray(),PetscOptionsRealArray(), PetscOptionsScalar(),
2027:           PetscOptionsBoolGroupBegin(), PetscOptionsBoolGroup(), PetscOptionsBoolGroupEnd(),
2028:           PetscOptionsList(), PetscOptionsEList()
2029: @*/
2030: PetscErrorCode  PetscOptionsGetStringArray(const char pre[],const char name[],char *strings[],PetscInt *nmax,PetscBool  *set)
2031: {
2032:   char           *value;
2034:   PetscInt       n;
2035:   PetscBool      flag;
2036:   PetscToken     token;

2041:   PetscOptionsFindPair_Private(pre,name,&value,&flag);
2042:   if (!flag) {
2043:     *nmax = 0;
2044:     if (set) *set = PETSC_FALSE;
2045:     return(0);
2046:   }
2047:   if (!value) {
2048:     *nmax = 0;
2049:     if (set) *set = PETSC_FALSE;
2050:     return(0);
2051:   }
2052:   if (!*nmax) {
2053:     if (set) *set = PETSC_FALSE;
2054:     return(0);
2055:   }
2056:   if (set) *set = PETSC_TRUE;

2058:   PetscTokenCreate(value,',',&token);
2059:   PetscTokenFind(token,&value);
2060:   n    = 0;
2061:   while (n < *nmax) {
2062:     if (!value) break;
2063:     PetscStrallocpy(value,&strings[n]);
2064:     PetscTokenFind(token,&value);
2065:     n++;
2066:   }
2067:   PetscTokenDestroy(&token);
2068:   *nmax = n;
2069:   return(0);
2070: }

2074: /*@C
2075:    PetscOptionsUsed - Indicates if PETSc has used a particular option set in the database

2077:    Not Collective

2079:    Input Parameter:
2080: .    option - string name of option

2082:    Output Parameter:
2083: .   used - PETSC_TRUE if the option was used, otherwise false, including if option was not found in options database

2085:    Level: advanced

2087: .seealso: PetscOptionsView(), PetscOptionsLeft(), PetscOptionsAllUsed()
2088: @*/
2089: PetscErrorCode  PetscOptionsUsed(const char *option,PetscBool *used)
2090: {
2091:   PetscInt       i;

2095:   *used = PETSC_FALSE;
2096:   for (i=0; i<options->N; i++) {
2097:     PetscStrcmp(options->names[i],option,used);
2098:     if (*used) {
2099:       *used = options->used[i];
2100:       break;
2101:     }
2102:   }
2103:   return(0);
2104: }

2108: /*@C
2109:    PetscOptionsAllUsed - Returns a count of the number of options in the
2110:    database that have never been selected.

2112:    Not Collective

2114:    Output Parameter:
2115: .   N - count of options not used

2117:    Level: advanced

2119: .seealso: PetscOptionsView()
2120: @*/
2121: PetscErrorCode  PetscOptionsAllUsed(PetscInt *N)
2122: {
2123:   PetscInt i,n = 0;

2126:   for (i=0; i<options->N; i++) {
2127:     if (!options->used[i]) n++;
2128:   }
2129:   *N = n;
2130:   return(0);
2131: }

2135: /*@
2136:     PetscOptionsLeft - Prints to screen any options that were set and never used.

2138:   Not collective

2140:    Options Database Key:
2141: .  -options_left - Activates OptionsAllUsed() within PetscFinalize()

2143:   Level: advanced

2145: .seealso: PetscOptionsAllUsed()
2146: @*/
2147: PetscErrorCode  PetscOptionsLeft(void)
2148: {
2150:   PetscInt       i;

2153:   for (i=0; i<options->N; i++) {
2154:     if (!options->used[i]) {
2155:       if (options->values[i]) {
2156:         PetscPrintf(PETSC_COMM_WORLD,"Option left: name:-%s value: %s\n",options->names[i],options->values[i]);
2157:       } else {
2158:         PetscPrintf(PETSC_COMM_WORLD,"Option left: name:-%s (no value)\n",options->names[i]);
2159:       }
2160:     }
2161:   }
2162:   return(0);
2163: }


2168: /*
2169:     PetscOptionsCreate - Creates the empty options database.

2171: */
2172: PetscErrorCode  PetscOptionsCreate(void)
2173: {

2177:   options = (PetscOptionsTable*)malloc(sizeof(PetscOptionsTable));
2178:   PetscMemzero(options,sizeof(PetscOptionsTable));

2180:   options->namegiven      = PETSC_FALSE;
2181:   options->N              = 0;
2182:   options->Naliases       = 0;
2183:   options->numbermonitors = 0;

2185:   PetscOptionsObject.prefix = NULL;
2186:   PetscOptionsObject.title  = NULL;
2187:   return(0);
2188: }

2192: /*@
2193:    PetscOptionsSetFromOptions - Sets various SNES and KSP parameters from user options.

2195:    Collective on PETSC_COMM_WORLD

2197:    Options Database Keys:
2198: +  -options_monitor <optional filename> - prints the names and values of all runtime options as they are set. The monitor functionality is not
2199:                 available for options set through a file, environment variable, or on
2200:                 the command line. Only options set after PetscInitialize completes will
2201:                 be monitored.
2202: .  -options_monitor_cancel - cancel all options database monitors

2204:    Notes:
2205:    To see all options, run your program with the -help option or consult
2206:    the <A href="../../docs/manual.pdf">users manual</A>..

2208:    Level: intermediate

2210: .keywords: set, options, database
2211: @*/
2212: PetscErrorCode  PetscOptionsSetFromOptions(void)
2213: {
2214:   PetscBool      flgc,flgm;
2216:   char           monfilename[PETSC_MAX_PATH_LEN];
2217:   PetscViewer    monviewer;

2220:   PetscOptionsBegin(PETSC_COMM_WORLD,"","Options database options","PetscOptions");
2221:   PetscOptionsString("-options_monitor","Monitor options database","PetscOptionsMonitorSet","stdout",monfilename,PETSC_MAX_PATH_LEN,&flgm);
2222:   PetscOptionsBool("-options_monitor_cancel","Cancel all options database monitors","PetscOptionsMonitorCancel",PETSC_FALSE,&flgc,NULL);
2223:   PetscOptionsEnd();
2224:   if (flgm) {
2225:     PetscViewerASCIIOpen(PETSC_COMM_WORLD,monfilename,&monviewer);
2226:     PetscOptionsMonitorSet(PetscOptionsMonitorDefault,monviewer,(PetscErrorCode (*)(void**))PetscViewerDestroy);
2227:   }
2228:   if (flgc) { PetscOptionsMonitorCancel(); }
2229:   return(0);
2230: }


2235: /*@C
2236:    PetscOptionsMonitorDefault - Print all options set value events.

2238:    Logically Collective on PETSC_COMM_WORLD

2240:    Input Parameters:
2241: +  name  - option name string
2242: .  value - option value string
2243: -  dummy - unused monitor context

2245:    Level: intermediate

2247: .keywords: PetscOptions, default, monitor

2249: .seealso: PetscOptionsMonitorSet()
2250: @*/
2251: PetscErrorCode  PetscOptionsMonitorDefault(const char name[], const char value[], void *dummy)
2252: {
2254:   PetscViewer    viewer = (PetscViewer) dummy;

2257:   if (!viewer) {
2258:     PetscViewerASCIIGetStdout(PETSC_COMM_WORLD,&viewer);
2259:   }
2260:   PetscViewerASCIIPrintf(viewer,"Setting option: %s = %s\n",name,value);
2261:   return(0);
2262: }

2266: /*@C
2267:    PetscOptionsMonitorSet - Sets an ADDITIONAL function to be called at every method that
2268:    modified the PETSc options database.

2270:    Not collective

2272:    Input Parameters:
2273: +  monitor - pointer to function (if this is NULL, it turns off monitoring
2274: .  mctx    - [optional] context for private data for the
2275:              monitor routine (use NULL if no context is desired)
2276: -  monitordestroy - [optional] routine that frees monitor context
2277:           (may be NULL)

2279:    Calling Sequence of monitor:
2280: $     monitor (const char name[], const char value[], void *mctx)

2282: +  name - option name string
2283: .  value - option value string
2284: -  mctx  - optional monitoring context, as set by PetscOptionsMonitorSet()

2286:    Options Database Keys:
2287: +    -options_monitor    - sets PetscOptionsMonitorDefault()
2288: -    -options_monitor_cancel - cancels all monitors that have
2289:                           been hardwired into a code by
2290:                           calls to PetscOptionsMonitorSet(), but
2291:                           does not cancel those set via
2292:                           the options database.

2294:    Notes:
2295:    The default is to do nothing.  To print the name and value of options
2296:    being inserted into the database, use PetscOptionsMonitorDefault() as the monitoring routine,
2297:    with a null monitoring context.

2299:    Several different monitoring routines may be set by calling
2300:    PetscOptionsMonitorSet() multiple times; all will be called in the
2301:    order in which they were set.

2303:    Level: beginner

2305: .keywords: PetscOptions, set, monitor

2307: .seealso: PetscOptionsMonitorDefault(), PetscOptionsMonitorCancel()
2308: @*/
2309: PetscErrorCode  PetscOptionsMonitorSet(PetscErrorCode (*monitor)(const char name[], const char value[], void*),void *mctx,PetscErrorCode (*monitordestroy)(void**))
2310: {
2312:   if (options->numbermonitors >= MAXOPTIONSMONITORS) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Too many PetscOptions monitors set");
2313:   options->monitor[options->numbermonitors]          = monitor;
2314:   options->monitordestroy[options->numbermonitors]   = monitordestroy;
2315:   options->monitorcontext[options->numbermonitors++] = (void*)mctx;
2316:   return(0);
2317: }

2321: /*@
2322:    PetscOptionsMonitorCancel - Clears all monitors for a PetscOptions object.

2324:    Not collective

2326:    Options Database Key:
2327: .  -options_monitor_cancel - Cancels all monitors that have
2328:     been hardwired into a code by calls to PetscOptionsMonitorSet(),
2329:     but does not cancel those set via the options database.

2331:    Level: intermediate

2333: .keywords: PetscOptions, set, monitor

2335: .seealso: PetscOptionsMonitorDefault(), PetscOptionsMonitorSet()
2336: @*/
2337: PetscErrorCode  PetscOptionsMonitorCancel(void)
2338: {
2340:   PetscInt       i;

2343:   for (i=0; i<options->numbermonitors; i++) {
2344:     if (options->monitordestroy[i]) {
2345:       (*options->monitordestroy[i])(&options->monitorcontext[i]);
2346:     }
2347:   }
2348:   options->numbermonitors = 0;
2349:   return(0);
2350: }