xref: /petsc/src/ts/trajectory/interface/traj.c (revision 84a458341578b7b1a1d4862485e24f22f28d0b03)
1 
2 #include <petsc/private/tsimpl.h>        /*I "petscts.h"  I*/
3 
4 PetscFunctionList TSTrajectoryList              = NULL;
5 PetscBool         TSTrajectoryRegisterAllCalled = PETSC_FALSE;
6 PetscClassId      TSTRAJECTORY_CLASSID;
7 PetscLogEvent     TSTrajectory_Set, TSTrajectory_Get;
8 
9 /*@C
10   TSTrajectoryRegister - Adds a way of storing trajectories to the TS package
11 
12   Not Collective
13 
14   Input Parameters:
15 + name        - the name of a new user-defined creation routine
16 - create_func - the creation routine itself
17 
18   Notes:
19   TSTrajectoryRegister() may be called multiple times to add several user-defined tses.
20 
21   Level: developer
22 
23 .keywords: TS, trajectory, timestep, register
24 
25 .seealso: TSTrajectoryRegisterAll()
26 @*/
27 PetscErrorCode TSTrajectoryRegister(const char sname[],PetscErrorCode (*function)(TSTrajectory,TS))
28 {
29   PetscErrorCode ierr;
30 
31   PetscFunctionBegin;
32   ierr = PetscFunctionListAdd(&TSTrajectoryList,sname,function);CHKERRQ(ierr);
33   PetscFunctionReturn(0);
34 }
35 
36 PetscErrorCode TSTrajectorySet(TSTrajectory tj,TS ts,PetscInt stepnum,PetscReal time,Vec X)
37 {
38   PetscErrorCode ierr;
39 
40   PetscFunctionBegin;
41   if (!tj) PetscFunctionReturn(0);
42   ierr = PetscLogEventBegin(TSTrajectory_Set,tj,ts,0,0);CHKERRQ(ierr);
43   ierr = (*tj->ops->set)(tj,ts,stepnum,time,X);CHKERRQ(ierr);
44   ierr = PetscLogEventEnd(TSTrajectory_Set,tj,ts,0,0);CHKERRQ(ierr);
45   PetscFunctionReturn(0);
46 }
47 
48 PetscErrorCode TSTrajectoryGet(TSTrajectory tj,TS ts,PetscInt stepnum,PetscReal *time)
49 {
50   PetscErrorCode ierr;
51 
52   PetscFunctionBegin;
53   if (!tj) SETERRQ(PetscObjectComm((PetscObject)ts),PETSC_ERR_ARG_WRONGSTATE,"TS solver did not save trajectory");
54   ierr = PetscLogEventBegin(TSTrajectory_Get,tj,ts,0,0);CHKERRQ(ierr);
55   ierr = (*tj->ops->get)(tj,ts,stepnum,time);CHKERRQ(ierr);
56   ierr = PetscLogEventEnd(TSTrajectory_Get,tj,ts,0,0);CHKERRQ(ierr);
57   PetscFunctionReturn(0);
58 }
59 
60 /*@C
61     TSTrajectoryView - Prints information about the trajectory object
62 
63     Collective on TSTrajectory
64 
65     Input Parameters:
66 +   tj - the TSTrajectory context obtained from TSTrajectoryCreate()
67 -   viewer - visualization context
68 
69     Options Database Key:
70 .   -ts_trajectory_view - calls TSTrajectoryView() at end of TSAdjointStep()
71 
72     Notes:
73     The available visualization contexts include
74 +     PETSC_VIEWER_STDOUT_SELF - standard output (default)
75 -     PETSC_VIEWER_STDOUT_WORLD - synchronized standard
76          output where only the first processor opens
77          the file.  All other processors send their
78          data to the first processor to print.
79 
80     The user can open an alternative visualization context with
81     PetscViewerASCIIOpen() - output to a specified file.
82 
83     Level: developer
84 
85 .keywords: TS, trajectory, timestep, view
86 
87 .seealso: PetscViewerASCIIOpen()
88 @*/
89 PetscErrorCode  TSTrajectoryView(TSTrajectory tj,PetscViewer viewer)
90 {
91   PetscErrorCode ierr;
92   PetscBool      iascii;
93 
94   PetscFunctionBegin;
95   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
96   if (!viewer) {
97     ierr = PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)tj),&viewer);CHKERRQ(ierr);
98   }
99   PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2);
100   PetscCheckSameComm(tj,1,viewer,2);
101 
102   ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr);
103   if (iascii) {
104     ierr = PetscObjectPrintClassNamePrefixType((PetscObject)tj,viewer);CHKERRQ(ierr);
105     ierr = PetscViewerASCIIPrintf(viewer,"  total number of recomputations for adjoint calculation = %D\n",tj->recomps);CHKERRQ(ierr);
106     ierr = PetscViewerASCIIPrintf(viewer,"  disk checkpoint reads = %D\n",tj->diskreads);CHKERRQ(ierr);
107     ierr = PetscViewerASCIIPrintf(viewer,"  disk checkpoint writes = %D\n",tj->diskwrites);CHKERRQ(ierr);
108     if (tj->ops->view) {
109       ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr);
110       ierr = (*tj->ops->view)(tj,viewer);CHKERRQ(ierr);
111       ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr);
112     }
113   }
114   PetscFunctionReturn(0);
115 }
116 
117 /*@C
118    TSTrajectorySetVariableNames - Sets the name of each component in the solution vector so that it may be saved with the trajectory
119 
120    Collective on TSTrajectory
121 
122    Input Parameters:
123 +  tr - the trajectory context
124 -  names - the names of the components, final string must be NULL
125 
126    Level: intermediate
127 
128    Note: Fortran interface is not possible because of the string array argument
129 
130 .keywords: TS, TSTrajectory, vector, monitor, view
131 
132 .seealso: TSTrajectory, TSGetTrajectory()
133 @*/
134 PetscErrorCode  TSTrajectorySetVariableNames(TSTrajectory ctx,const char * const *names)
135 {
136   PetscErrorCode    ierr;
137 
138   PetscFunctionBegin;
139   ierr = PetscStrArrayDestroy(&ctx->names);CHKERRQ(ierr);
140   ierr = PetscStrArrayallocpy(names,&ctx->names);CHKERRQ(ierr);
141   PetscFunctionReturn(0);
142 }
143 
144 /*@C
145    TSTrjactorySetTransform - Solution vector will be transformed by provided function before being saved to disk
146 
147    Collective on TSLGCtx
148 
149    Input Parameters:
150 +  tj - the TSTrajectory context
151 .  transform - the transform function
152 .  destroy - function to destroy the optional context
153 -  ctx - optional context used by transform function
154 
155    Level: intermediate
156 
157 .keywords: TSTrajectory,  vector, monitor, view
158 
159 .seealso:  TSTrajectorySetVariableNames(), TSTrajectory, TSMonitorLGSetTransform()
160 @*/
161 PetscErrorCode  TSTrajectorySetTransform(TSTrajectory tj,PetscErrorCode (*transform)(void*,Vec,Vec*),PetscErrorCode (*destroy)(void*),void *tctx)
162 {
163   PetscFunctionBegin;
164   tj->transform        = transform;
165   tj->transformdestroy = destroy;
166   tj->transformctx     = tctx;
167   PetscFunctionReturn(0);
168 }
169 
170 
171 /*@
172   TSTrajectoryCreate - This function creates an empty trajectory object used to store the time dependent solution of an ODE/DAE
173 
174   Collective on MPI_Comm
175 
176   Input Parameter:
177 . comm - the communicator
178 
179   Output Parameter:
180 . tj   - the trajectory object
181 
182   Level: developer
183 
184   Notes: Usually one does not call this routine, it is called automatically when one calls TSSetSaveTrajectory().
185 
186 .keywords: TS, trajectory, create
187 
188 .seealso: TSTrajectorySetUp(), TSTrajectoryDestroy(), TSTrajectorySetType(), TSTrajectorySetVariableNames(), TSGetTrajectory(), TSTrajectorySetKeepFiles()
189 @*/
190 PetscErrorCode  TSTrajectoryCreate(MPI_Comm comm,TSTrajectory *tj)
191 {
192   TSTrajectory   t;
193   PetscErrorCode ierr;
194 
195   PetscFunctionBegin;
196   PetscValidPointer(tj,2);
197   *tj = NULL;
198   ierr = TSInitializePackage();CHKERRQ(ierr);
199 
200   ierr = PetscHeaderCreate(t,TSTRAJECTORY_CLASSID,"TSTrajectory","Time stepping","TS",comm,TSTrajectoryDestroy,TSTrajectoryView);CHKERRQ(ierr);
201   t->setupcalled = PETSC_FALSE;
202   t->keepfiles   = PETSC_TRUE;
203   *tj  = t;
204   ierr = TSTrajectorySetDirname(t,"SA-data");CHKERRQ(ierr);
205   ierr = TSTrajectorySetFiletemplate(t,"/SA-%06D.bin");CHKERRQ(ierr);
206   PetscFunctionReturn(0);
207 }
208 
209 /*@C
210   TSTrajectorySetType - Sets the storage method to be used as in a trajectory
211 
212   Collective on TS
213 
214   Input Parameters:
215 + tj   - the TSTrajectory context
216 . ts   - the TS context
217 - type - a known method
218 
219   Options Database Command:
220 . -ts_trajectory_type <type> - Sets the method; use -help for a list of available methods (for instance, basic)
221 
222    Level: developer
223 
224 .keywords: TS, trajectory, timestep, set, type
225 
226 .seealso: TS, TSTrajectoryCreate(), TSTrajectorySetFromOptions(), TSTrajectoryDestroy()
227 
228 @*/
229 PetscErrorCode  TSTrajectorySetType(TSTrajectory tj,TS ts,const TSTrajectoryType type)
230 {
231   PetscErrorCode (*r)(TSTrajectory,TS);
232   PetscBool      match;
233   PetscErrorCode ierr;
234 
235   PetscFunctionBegin;
236   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
237   ierr = PetscObjectTypeCompare((PetscObject)tj,type,&match);CHKERRQ(ierr);
238   if (match) PetscFunctionReturn(0);
239 
240   ierr = PetscFunctionListFind(TSTrajectoryList,type,&r);CHKERRQ(ierr);
241   if (!r) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_UNKNOWN_TYPE,"Unknown TSTrajectory type: %s",type);
242   if (tj->ops->destroy) {
243     ierr = (*(tj)->ops->destroy)(tj);CHKERRQ(ierr);
244 
245     tj->ops->destroy = NULL;
246   }
247   ierr = PetscMemzero(tj->ops,sizeof(*tj->ops));CHKERRQ(ierr);
248 
249   ierr = PetscObjectChangeTypeName((PetscObject)tj,type);CHKERRQ(ierr);
250   ierr = (*r)(tj,ts);CHKERRQ(ierr);
251   PetscFunctionReturn(0);
252 }
253 
254 PETSC_EXTERN PetscErrorCode TSTrajectoryCreate_Basic(TSTrajectory,TS);
255 PETSC_EXTERN PetscErrorCode TSTrajectoryCreate_Singlefile(TSTrajectory,TS);
256 PETSC_EXTERN PetscErrorCode TSTrajectoryCreate_Memory(TSTrajectory,TS);
257 PETSC_EXTERN PetscErrorCode TSTrajectoryCreate_Visualization(TSTrajectory,TS);
258 
259 /*@C
260   TSTrajectoryRegisterAll - Registers all of the trajectory storage schecmes in the TS package.
261 
262   Not Collective
263 
264   Level: developer
265 
266 .keywords: TS, trajectory, register, all
267 
268 .seealso: TSTrajectoryRegister()
269 @*/
270 PetscErrorCode  TSTrajectoryRegisterAll(void)
271 {
272   PetscErrorCode ierr;
273 
274   PetscFunctionBegin;
275   if (TSTrajectoryRegisterAllCalled) PetscFunctionReturn(0);
276   TSTrajectoryRegisterAllCalled = PETSC_TRUE;
277 
278   ierr = TSTrajectoryRegister(TSTRAJECTORYBASIC,TSTrajectoryCreate_Basic);CHKERRQ(ierr);
279   ierr = TSTrajectoryRegister(TSTRAJECTORYSINGLEFILE,TSTrajectoryCreate_Singlefile);CHKERRQ(ierr);
280   ierr = TSTrajectoryRegister(TSTRAJECTORYMEMORY,TSTrajectoryCreate_Memory);CHKERRQ(ierr);
281   ierr = TSTrajectoryRegister(TSTRAJECTORYVISUALIZATION,TSTrajectoryCreate_Visualization);CHKERRQ(ierr);
282   PetscFunctionReturn(0);
283 }
284 
285 /*@
286    TSTrajectoryDestroy - Destroys a trajectory context
287 
288    Collective on TSTrajectory
289 
290    Input Parameter:
291 .  tj - the TSTrajectory context obtained from TSTrajectoryCreate()
292 
293    Level: developer
294 
295 .keywords: TS, trajectory, timestep, destroy
296 
297 .seealso: TSTrajectoryCreate(), TSTrajectorySetUp()
298 @*/
299 PetscErrorCode  TSTrajectoryDestroy(TSTrajectory *tj)
300 {
301   PetscErrorCode ierr;
302 
303   PetscFunctionBegin;
304   if (!*tj) PetscFunctionReturn(0);
305   PetscValidHeaderSpecific((*tj),TSTRAJECTORY_CLASSID,1);
306   if (--((PetscObject)(*tj))->refct > 0) {*tj = 0; PetscFunctionReturn(0);}
307 
308   if ((*tj)->transformdestroy) {ierr = (*(*tj)->transformdestroy)((*tj)->transformctx);CHKERRQ(ierr);}
309   if ((*tj)->ops->destroy) {ierr = (*(*tj)->ops->destroy)((*tj));CHKERRQ(ierr);}
310   ierr = PetscViewerDestroy(&(*tj)->monitor);CHKERRQ(ierr);
311   ierr = PetscStrArrayDestroy(&(*tj)->names);CHKERRQ(ierr);
312   ierr = PetscFree((*tj)->dirname);CHKERRQ(ierr);
313   ierr = PetscFree((*tj)->filetemplate);CHKERRQ(ierr);
314   ierr = PetscHeaderDestroy(tj);CHKERRQ(ierr);
315   PetscFunctionReturn(0);
316 }
317 
318 /*
319   TSTrajectorySetTypeFromOptions_Private - Sets the type of ts from user options.
320 
321   Collective on TSTrajectory
322 
323   Input Parameter:
324 + tj - the TSTrajectory context
325 - ts - the TS context
326 
327   Options Database Keys:
328 . -ts_trajectory_type <type> - TSTRAJECTORYBASIC, TSTRAJECTORYMEMORY, TSTRAJECTORYSINGLEFILE, TSTRAJECTORYVISUALIZATION
329 
330   Level: developer
331 
332 .keywords: TS, trajectory, set, options, type
333 
334 .seealso: TSTrajectorySetFromOptions(), TSTrajectorySetType()
335 */
336 static PetscErrorCode TSTrajectorySetTypeFromOptions_Private(PetscOptionItems *PetscOptionsObject,TSTrajectory tj,TS ts)
337 {
338   PetscBool      opt;
339   const char     *defaultType;
340   char           typeName[256];
341   PetscBool      flg;
342   PetscErrorCode ierr;
343 
344   PetscFunctionBegin;
345   if (((PetscObject)tj)->type_name) defaultType = ((PetscObject)tj)->type_name;
346   else defaultType = TSTRAJECTORYBASIC;
347 
348   ierr = TSTrajectoryRegisterAll();CHKERRQ(ierr);
349   ierr = PetscOptionsFList("-ts_trajectory_type","TSTrajectory method","TSTrajectorySetType",TSTrajectoryList,defaultType,typeName,256,&opt);CHKERRQ(ierr);
350   if (opt) {
351     ierr = PetscStrcmp(typeName,TSTRAJECTORYMEMORY,&flg);CHKERRQ(ierr);
352     ierr = TSTrajectorySetType(tj,ts,typeName);CHKERRQ(ierr);
353   } else {
354     ierr = TSTrajectorySetType(tj,ts,defaultType);CHKERRQ(ierr);
355   }
356   PetscFunctionReturn(0);
357 }
358 
359 /*@
360    TSTrajectorySetMonitor - Monitor the schedules generated by the checkpointing controller
361 
362    Collective on TSTrajectory
363 
364    Input Arguments:
365 +  tj - the TSTrajectory context
366 -  flg - PETSC_TRUE to active a monitor, PETSC_FALSE to disable
367 
368    Options Database Keys:
369 .  -ts_trajectory_monitor - print TSTrajectory information
370 
371    Level: developer
372 
373 .keywords: TS, trajectory, set, monitor
374 
375 .seealso: TSTrajectoryCreate(), TSTrajectoryDestroy(), TSTrajectorySetUp()
376 @*/
377 PetscErrorCode TSTrajectorySetMonitor(TSTrajectory tj,PetscBool flg)
378 {
379   PetscErrorCode ierr;
380 
381   PetscFunctionBegin;
382   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
383   PetscValidLogicalCollectiveBool(tj,flg,2);
384   if (flg) {
385     if (!tj->monitor) {ierr = PetscViewerASCIIOpen(PetscObjectComm((PetscObject)tj),"stdout",&tj->monitor);CHKERRQ(ierr);}
386   } else {
387     ierr = PetscViewerDestroy(&tj->monitor);CHKERRQ(ierr);
388   }
389   PetscFunctionReturn(0);
390 }
391 
392 /*@
393    TSTrajectorySetKeepFiles - Keep the files generated by the TSTrajectory
394 
395    Collective on TSTrajectory
396 
397    Input Arguments:
398 +  tj - the TSTrajectory context
399 -  flg - PETSC_TRUE to save, PETSC_FALSE to disable
400 
401    Options Database Keys:
402 .  -ts_trajectory_keep_files - have it keep the files
403 
404    Notes: By default the TSTrajectory used for adjoint computations, TSTRAJECTORYBASIC, removes the files it generates at the end of the run. This causes the files to be kept.
405 
406    Level: advanced
407 
408 .keywords: TS, trajectory, set, monitor
409 
410 .seealso: TSTrajectoryCreate(), TSTrajectoryDestroy(), TSTrajectorySetUp(), TSTrajectorySetMonitor()
411 @*/
412 PetscErrorCode TSTrajectorySetKeepFiles(TSTrajectory tj,PetscBool flg)
413 {
414   PetscFunctionBegin;
415   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
416   PetscValidLogicalCollectiveBool(tj,flg,2);
417   tj->keepfiles = flg;
418   PetscFunctionReturn(0);
419 }
420 
421 /*@C
422    TSTrajectorySetDirname - Specify the name of the directory where disk checkpoints are stored.
423 
424    Collective on TSTrajectory
425 
426    Input Arguments:
427 +  tj      - the TSTrajectory context
428 -  dirname - the directory name
429 
430    Options Database Keys:
431 .  -ts_trajectory_dirname - set the directory name
432 
433    Level: developer
434 
435 .keywords: TS, trajectory, set
436 
437 .seealso: TSTrajectorySetFiletemplate(),TSTrajectorySetUp()
438 @*/
439 PetscErrorCode TSTrajectorySetDirname(TSTrajectory tj,const char dirname[])
440 {
441   PetscErrorCode ierr;
442   PetscFunctionBegin;
443   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
444   ierr = PetscFree(tj->dirname);CHKERRQ(ierr);
445   ierr = PetscStrallocpy(dirname,&tj->dirname);CHKERRQ(ierr);
446   PetscFunctionReturn(0);
447 }
448 
449 /*@C
450    TSTrajectorySetFiletemplate - Specify the name template for the files storing checkpoints.
451 
452    Collective on TSTrajectory
453 
454    Input Arguments:
455 +  tj      - the TSTrajectory context
456 -  filetemplate - the directory name
457 
458    Options Database Keys:
459 .  -ts_trajectory_file - set the file name template
460 
461    Level: developer
462 
463 .keywords: TS, trajectory, set
464 
465 .seealso: TSTrajectorySetFiletemplate(),TSTrajectorySetUp()
466 @*/
467 PetscErrorCode TSTrajectorySetFiletemplate(TSTrajectory tj,const char filetemplate[])
468 {
469   PetscErrorCode ierr;
470   PetscFunctionBegin;
471   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
472   ierr = PetscFree(tj->filetemplate);CHKERRQ(ierr);
473   ierr = PetscStrallocpy(filetemplate,&tj->filetemplate);CHKERRQ(ierr);
474   PetscFunctionReturn(0);
475 }
476 
477 /*@
478    TSTrajectorySetFromOptions - Sets various TSTrajectory parameters from user options.
479 
480    Collective on TSTrajectory
481 
482    Input Parameter:
483 +  tj - the TSTrajectory context obtained from TSTrajectoryCreate()
484 -  ts - the TS context
485 
486    Options Database Keys:
487 +  -ts_trajectory_type <type> - TSTRAJECTORYBASIC, TSTRAJECTORYMEMORY, TSTRAJECTORYSINGLEFILE, TSTRAJECTORYVISUALIZATION
488 .  -ts_trajectory_keep_files <true,false> - keep the files generated by the code after the program ends. This is true by default for TSTRAJECTORYSINGLEFILE, TSTRAJECTORYVISUALIZATION
489 -  -ts_trajectory_monitor - print TSTrajectory information
490 
491    Level: developer
492 
493    Notes: This is not normally called directly by users
494 
495 .keywords: TS, trajectory, timestep, set, options, database
496 
497 .seealso: TSSetSaveTrajectory(), TSTrajectorySetUp()
498 @*/
499 PetscErrorCode  TSTrajectorySetFromOptions(TSTrajectory tj,TS ts)
500 {
501   PetscBool      set,flg;
502   char           dirname[PETSC_MAX_PATH_LEN],filetemplate[PETSC_MAX_PATH_LEN];
503   PetscErrorCode ierr;
504 
505   PetscFunctionBegin;
506   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
507   PetscValidHeaderSpecific(ts,TS_CLASSID,2);
508   ierr = PetscObjectOptionsBegin((PetscObject)tj);CHKERRQ(ierr);
509   ierr = TSTrajectorySetTypeFromOptions_Private(PetscOptionsObject,tj,ts);CHKERRQ(ierr);
510   ierr = PetscOptionsBool("-ts_trajectory_monitor","Print checkpointing schedules","TSTrajectorySetMonitor",tj->monitor ? PETSC_TRUE:PETSC_FALSE,&flg,&set);CHKERRQ(ierr);
511   if (set) {ierr = TSTrajectorySetMonitor(tj,flg);CHKERRQ(ierr);}
512 
513   ierr = PetscOptionsBool("-ts_trajectory_keep_files","Keep any trajectory files generated during the run","TSTrajectorySetKeepFiles",tj->keepfiles,&flg,&set);CHKERRQ(ierr);
514   if (set) {ierr = TSTrajectorySetKeepFiles(tj,flg);CHKERRQ(ierr);}
515 
516   ierr = PetscOptionsString("-ts_trajectory_dirname","Directory name for TSTrajectory file","TSTrajectorySetDirname",0,dirname,PETSC_MAX_PATH_LEN-14,&set);CHKERRQ(ierr);
517   if (set) {
518     ierr = TSTrajectorySetDirname(tj,dirname);CHKERRQ(ierr);
519   }
520 
521   ierr = PetscOptionsString("-ts_trajectory_file","Template for TSTrajectory file name, use filename-%06D.bin","TSTrajectorySetFiletemplate",0,filetemplate,PETSC_MAX_PATH_LEN,&set);CHKERRQ(ierr);
522   if (set) {
523     size_t     len;
524     const char *ptr,*ptr2;
525 
526     if (!filetemplate[0]) SETERRQ(PetscObjectComm((PetscObject)ts),PETSC_ERR_USER,"-ts_trajectory_file requires a file name template, e.g. filename-%%06D.bin");
527     /* Do some cursory validation of the input. */
528     ierr = PetscStrstr(filetemplate,"%",(char**)&ptr);CHKERRQ(ierr);
529     if (!ptr) SETERRQ(PetscObjectComm((PetscObject)ts),PETSC_ERR_USER,"-ts_trajectory_file requires a file name template, e.g. filename-%%06D.bin");
530     for (ptr++; ptr && *ptr; ptr++) {
531       ierr = PetscStrchr("DdiouxX",*ptr,(char**)&ptr2);CHKERRQ(ierr);
532       if (!ptr2 && (*ptr < '0' || '9' < *ptr)) SETERRQ(PetscObjectComm((PetscObject)ts),PETSC_ERR_USER,"Invalid file template argument to -ts_trajectory_file, should look like filename-%%06D.bin");
533       if (ptr2) break;
534     }
535     ierr = PetscStrcat(dirname,"/");CHKERRQ(ierr);
536     ierr = PetscStrlen(filetemplate,&len);CHKERRQ(ierr);
537     ierr = PetscStrncat(dirname,filetemplate,PETSC_MAX_PATH_LEN-len-1);CHKERRQ(ierr);
538     ierr = TSTrajectorySetFiletemplate(tj,dirname);CHKERRQ(ierr);
539   }
540 
541   /* Handle specific TSTrajectory options */
542   if (tj->ops->setfromoptions) {
543     ierr = (*tj->ops->setfromoptions)(PetscOptionsObject,tj);CHKERRQ(ierr);
544   }
545   ierr = PetscOptionsEnd();CHKERRQ(ierr);
546   PetscFunctionReturn(0);
547 }
548 
549 /*@
550    TSTrajectorySetUp - Sets up the internal data structures, e.g. stacks, for the later use
551    of a TS trajectory.
552 
553    Collective on TS
554 
555    Input Parameter:
556 +  ts - the TS context obtained from TSCreate()
557 -  tj - the TS trajectory context
558 
559    Level: developer
560 
561 .keywords: TS, trajectory, setup
562 
563 .seealso: TSSetSaveTrajectory(), TSTrajectoryCreate(), TSTrajectoryDestroy()
564 @*/
565 PetscErrorCode  TSTrajectorySetUp(TSTrajectory tj,TS ts)
566 {
567   PetscErrorCode ierr;
568 
569   PetscFunctionBegin;
570   if (!tj) PetscFunctionReturn(0);
571   PetscValidHeaderSpecific(tj,TSTRAJECTORY_CLASSID,1);
572   PetscValidHeaderSpecific(ts,TS_CLASSID,2);
573   if (tj->setupcalled) PetscFunctionReturn(0);
574 
575   if (!((PetscObject)tj)->type_name) {
576     ierr = TSTrajectorySetType(tj,ts,TSTRAJECTORYBASIC);CHKERRQ(ierr);
577   }
578   if (tj->ops->setup) {
579     ierr = (*tj->ops->setup)(tj,ts);CHKERRQ(ierr);
580   }
581 
582   tj->setupcalled = PETSC_TRUE;
583 
584   /* Set the counters to zero */
585   tj->recomps    = 0;
586   tj->diskreads  = 0;
587   tj->diskwrites = 0;
588   PetscFunctionReturn(0);
589 }
590