1 #include <petsc/private/tsimpl.h> /*I "petscts.h" I*/ 2 #include <petscsys.h> 3 #ifdef PETSC_HAVE_REVOLVE 4 #include <revolve_c.h> 5 #endif 6 7 PetscLogEvent Disk_Write, Disk_Read; 8 9 typedef enum {NONE,TWO_LEVEL_NOREVOLVE,TWO_LEVEL_REVOLVE,TWO_LEVEL_TWO_REVOLVE,REVOLVE_OFFLINE,REVOLVE_ONLINE,REVOLVE_MULTISTAGE} SchedulerType; 10 11 typedef struct _StackElement { 12 PetscInt stepnum; 13 Vec X; 14 Vec *Y; 15 PetscReal time; 16 PetscReal timeprev; 17 } *StackElement; 18 19 #ifdef PETSC_HAVE_REVOLVE 20 typedef struct _RevolveCTX { 21 PetscBool reverseonestep; 22 PetscInt where; 23 PetscInt snaps_in; 24 PetscInt stepsleft; 25 PetscInt check; 26 PetscInt oldcapo; 27 PetscInt capo; 28 PetscInt fine; 29 PetscInt info; 30 } RevolveCTX; 31 #endif 32 33 typedef struct _Stack { 34 PetscInt stacksize; 35 PetscInt top; 36 StackElement *container; 37 PetscInt numY; 38 PetscBool solution_only; 39 } Stack; 40 41 typedef struct _DiskStack { 42 PetscInt stacksize; 43 PetscInt top; 44 PetscInt *container; 45 } DiskStack; 46 47 typedef struct _TJScheduler { 48 SchedulerType stype; 49 #ifdef PETSC_HAVE_REVOLVE 50 RevolveCTX *rctx,*rctx2; 51 PetscBool use_online; 52 PetscInt store_stride; 53 #endif 54 PetscBool recompute; 55 PetscBool skip_trajectory; 56 PetscBool save_stack; 57 MPI_Comm comm; 58 PetscInt max_cps_ram; /* maximum checkpoints in RAM */ 59 PetscInt max_cps_disk; /* maximum checkpoints on disk */ 60 PetscInt stride; 61 PetscInt total_steps; /* total number of steps */ 62 Stack stack; 63 DiskStack diskstack; 64 } TJScheduler; 65 66 #undef __FUNCT__ 67 #define __FUNCT__ "StackCreate" 68 static PetscErrorCode StackCreate(Stack *stack,PetscInt size,PetscInt ny) 69 { 70 PetscErrorCode ierr; 71 72 PetscFunctionBegin; 73 stack->top = -1; 74 stack->numY = ny; 75 76 ierr = PetscMalloc1(size*sizeof(StackElement),&stack->container);CHKERRQ(ierr); 77 PetscFunctionReturn(0); 78 } 79 80 #undef __FUNCT__ 81 #define __FUNCT__ "StackDestroy" 82 static PetscErrorCode StackDestroy(Stack *stack) 83 { 84 PetscInt i; 85 PetscErrorCode ierr; 86 87 PetscFunctionBegin; 88 if (stack->top > -1) { 89 for (i=0;i<=stack->top;i++) { 90 ierr = VecDestroy(&stack->container[i]->X);CHKERRQ(ierr); 91 if (!stack->solution_only) { 92 ierr = VecDestroyVecs(stack->numY,&stack->container[i]->Y);CHKERRQ(ierr); 93 } 94 ierr = PetscFree(stack->container[i]);CHKERRQ(ierr); 95 } 96 } 97 ierr = PetscFree(stack->container);CHKERRQ(ierr); 98 PetscFunctionReturn(0); 99 } 100 101 #undef __FUNCT__ 102 #define __FUNCT__ "StackPush" 103 static PetscErrorCode StackPush(Stack *stack,StackElement e) 104 { 105 PetscFunctionBegin; 106 if (stack->top+1 >= stack->stacksize) SETERRQ1(PETSC_COMM_WORLD,PETSC_ERR_MEMC,"Maximum stack size (%D) exceeded",stack->stacksize); 107 stack->container[++stack->top] = e; 108 PetscFunctionReturn(0); 109 } 110 111 #undef __FUNCT__ 112 #define __FUNCT__ "StackPop" 113 static PetscErrorCode StackPop(Stack *stack,StackElement *e) 114 { 115 PetscFunctionBegin; 116 if (stack->top == -1) SETERRQ(PETSC_COMM_WORLD,PETSC_ERR_MEMC,"Empty stack"); 117 *e = stack->container[stack->top--]; 118 PetscFunctionReturn(0); 119 } 120 121 #undef __FUNCT__ 122 #define __FUNCT__ "StackTop" 123 static PetscErrorCode StackTop(Stack *stack,StackElement *e) 124 { 125 PetscFunctionBegin; 126 *e = stack->container[stack->top]; 127 PetscFunctionReturn(0); 128 } 129 130 #ifdef PETSC_HAVE_REVOLVE 131 #undef __FUNCT__ 132 #define __FUNCT__ "StackFind" 133 static PetscErrorCode StackFind(Stack *stack,StackElement *e,PetscInt index) 134 { 135 PetscFunctionBegin; 136 *e = stack->container[index]; 137 PetscFunctionReturn(0); 138 } 139 #endif 140 141 #undef __FUNCT__ 142 #define __FUNCT__ "OutputBIN" 143 static PetscErrorCode OutputBIN(const char *filename,PetscViewer *viewer) 144 { 145 PetscErrorCode ierr; 146 147 PetscFunctionBegin; 148 ierr = PetscViewerCreate(PETSC_COMM_WORLD,viewer);CHKERRQ(ierr); 149 ierr = PetscViewerSetType(*viewer,PETSCVIEWERBINARY);CHKERRQ(ierr); 150 ierr = PetscViewerFileSetMode(*viewer,FILE_MODE_WRITE);CHKERRQ(ierr); 151 ierr = PetscViewerFileSetName(*viewer,filename);CHKERRQ(ierr); 152 PetscFunctionReturn(0); 153 } 154 155 #undef __FUNCT__ 156 #define __FUNCT__ "WriteToDisk" 157 static PetscErrorCode WriteToDisk(PetscInt stepnum,PetscReal time,PetscReal timeprev,Vec X,Vec *Y,PetscInt numY,PetscBool solution_only,PetscViewer viewer) 158 { 159 PetscInt i; 160 PetscErrorCode ierr; 161 162 PetscFunctionBegin; 163 ierr = PetscViewerBinaryWrite(viewer,&stepnum,1,PETSC_INT,PETSC_FALSE);CHKERRQ(ierr); 164 ierr = VecView(X,viewer);CHKERRQ(ierr); 165 for (i=0;!solution_only && i<numY;i++) { 166 ierr = VecView(Y[i],viewer);CHKERRQ(ierr); 167 } 168 ierr = PetscViewerBinaryWrite(viewer,&time,1,PETSC_REAL,PETSC_FALSE);CHKERRQ(ierr); 169 ierr = PetscViewerBinaryWrite(viewer,&timeprev,1,PETSC_REAL,PETSC_FALSE);CHKERRQ(ierr); 170 PetscFunctionReturn(0); 171 } 172 173 #undef __FUNCT__ 174 #define __FUNCT__ "ReadFromDisk" 175 static PetscErrorCode ReadFromDisk(PetscInt *stepnum,PetscReal *time,PetscReal *timeprev,Vec X,Vec *Y,PetscInt numY,PetscBool solution_only,PetscViewer viewer) 176 { 177 PetscInt i; 178 PetscErrorCode ierr; 179 180 PetscFunctionBegin; 181 ierr = PetscViewerBinaryRead(viewer,stepnum,1,NULL,PETSC_INT);CHKERRQ(ierr); 182 ierr = VecLoad(X,viewer);CHKERRQ(ierr); 183 for (i=0;!solution_only && i<numY;i++) { 184 ierr = VecLoad(Y[i],viewer);CHKERRQ(ierr); 185 } 186 ierr = PetscViewerBinaryRead(viewer,time,1,NULL,PETSC_REAL);CHKERRQ(ierr); 187 ierr = PetscViewerBinaryRead(viewer,timeprev,1,NULL,PETSC_REAL);CHKERRQ(ierr); 188 PetscFunctionReturn(0); 189 } 190 191 #undef __FUNCT__ 192 #define __FUNCT__ "StackDumpAll" 193 static PetscErrorCode StackDumpAll(TS ts,Stack *stack,PetscInt id) 194 { 195 Vec *Y; 196 PetscInt i; 197 StackElement e; 198 PetscViewer viewer; 199 char filename[PETSC_MAX_PATH_LEN]; 200 PetscErrorCode ierr; 201 202 PetscFunctionBegin; 203 if (id == 1) { 204 PetscMPIInt rank; 205 ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)ts),&rank);CHKERRQ(ierr); 206 if (!rank) { 207 ierr = PetscRMTree("SA-data");CHKERRQ(ierr); 208 ierr = PetscMkdir("SA-data");CHKERRQ(ierr); 209 } 210 } 211 ierr = PetscSNPrintf(filename,sizeof(filename),"SA-data/SA-STACK%06d.bin",id);CHKERRQ(ierr); 212 ierr = OutputBIN(filename,&viewer);CHKERRQ(ierr); 213 for (i=0;i<stack->stacksize;i++) { 214 e = stack->container[i]; 215 ierr = WriteToDisk(e->stepnum,e->time,e->timeprev,e->X,e->Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 216 } 217 /* save the last step for restart, the last step is in memory when using single level schemes, but not necessarily the case for multi level schemes */ 218 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 219 ierr = WriteToDisk(ts->total_steps,ts->ptime,ts->ptime_prev,ts->vec_sol,Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 220 for (i=0;i<stack->stacksize;i++) { 221 ierr = StackPop(stack,&e);CHKERRQ(ierr); 222 ierr = VecDestroy(&e->X);CHKERRQ(ierr); 223 if (!stack->solution_only) { 224 ierr = VecDestroyVecs(stack->numY,&e->Y);CHKERRQ(ierr); 225 } 226 ierr = PetscFree(e);CHKERRQ(ierr); 227 } 228 ierr = PetscViewerDestroy(&viewer);CHKERRQ(ierr); 229 PetscFunctionReturn(0); 230 } 231 232 #undef __FUNCT__ 233 #define __FUNCT__ "StackLoadAll" 234 static PetscErrorCode StackLoadAll(TS ts,Stack *stack,PetscInt id) 235 { 236 Vec *Y; 237 PetscInt i; 238 StackElement e; 239 PetscViewer viewer; 240 char filename[PETSC_MAX_PATH_LEN]; 241 PetscErrorCode ierr; 242 243 PetscFunctionBegin; 244 ierr = PetscSNPrintf(filename,sizeof filename,"SA-data/SA-STACK%06d.bin",id);CHKERRQ(ierr); 245 ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,filename,FILE_MODE_READ,&viewer);CHKERRQ(ierr); 246 for (i=0;i<stack->stacksize;i++) { 247 ierr = PetscCalloc1(1,&e); 248 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 249 ierr = VecDuplicate(Y[0],&e->X);CHKERRQ(ierr); 250 if (!stack->solution_only && stack->numY>0) { 251 ierr = VecDuplicateVecs(Y[0],stack->numY,&e->Y);CHKERRQ(ierr); 252 } 253 ierr = StackPush(stack,e);CHKERRQ(ierr); 254 } 255 for (i=0;i<stack->stacksize;i++) { 256 e = stack->container[i]; 257 ierr = ReadFromDisk(&e->stepnum,&e->time,&e->timeprev,e->X,e->Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 258 } 259 /* load the last step into TS */ 260 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 261 ierr = ReadFromDisk(&ts->total_steps,&ts->ptime,&ts->ptime_prev,ts->vec_sol,Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 262 ierr = TSSetTimeStep(ts,ts->ptime_prev-ts->ptime);CHKERRQ(ierr); 263 ierr = PetscViewerDestroy(&viewer);CHKERRQ(ierr); 264 PetscFunctionReturn(0); 265 } 266 267 #undef __FUNCT__ 268 #define __FUNCT__ "DumpSingle" 269 static PetscErrorCode DumpSingle(TS ts,Stack *stack,PetscInt id) 270 { 271 Vec *Y; 272 PetscInt stepnum; 273 PetscViewer viewer; 274 char filename[PETSC_MAX_PATH_LEN]; 275 PetscErrorCode ierr; 276 277 PetscFunctionBegin; 278 ierr = TSGetTotalSteps(ts,&stepnum);CHKERRQ(ierr); 279 if (id == 1) { 280 PetscMPIInt rank; 281 ierr = MPI_Comm_rank(PetscObjectComm((PetscObject)ts),&rank);CHKERRQ(ierr); 282 if (!rank) { 283 ierr = PetscRMTree("SA-data");CHKERRQ(ierr); 284 ierr = PetscMkdir("SA-data");CHKERRQ(ierr); 285 } 286 } 287 ierr = PetscSNPrintf(filename,sizeof(filename),"SA-data/SA-CPS%06d.bin",id);CHKERRQ(ierr); 288 ierr = OutputBIN(filename,&viewer);CHKERRQ(ierr); 289 290 ierr = PetscLogEventBegin(Disk_Write,ts,0,0,0);CHKERRQ(ierr); 291 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 292 ierr = WriteToDisk(stepnum,ts->ptime,ts->ptime_prev,ts->vec_sol,Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 293 ierr = PetscLogEventEnd(Disk_Write,ts,0,0,0);CHKERRQ(ierr); 294 295 ierr = PetscViewerDestroy(&viewer);CHKERRQ(ierr); 296 PetscFunctionReturn(0); 297 } 298 299 #undef __FUNCT__ 300 #define __FUNCT__ "LoadSingle" 301 static PetscErrorCode LoadSingle(TS ts,Stack *stack,PetscInt id) 302 { 303 Vec *Y; 304 PetscViewer viewer; 305 char filename[PETSC_MAX_PATH_LEN]; 306 PetscErrorCode ierr; 307 308 PetscFunctionBegin; 309 ierr = PetscSNPrintf(filename,sizeof filename,"SA-data/SA-CPS%06d.bin",id);CHKERRQ(ierr); 310 ierr = PetscViewerBinaryOpen(PETSC_COMM_WORLD,filename,FILE_MODE_READ,&viewer);CHKERRQ(ierr); 311 312 ierr = PetscLogEventBegin(Disk_Read,ts,0,0,0);CHKERRQ(ierr); 313 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 314 ierr = ReadFromDisk(&ts->total_steps,&ts->ptime,&ts->ptime_prev,ts->vec_sol,Y,stack->numY,stack->solution_only,viewer);CHKERRQ(ierr); 315 ierr = PetscLogEventEnd(Disk_Read,ts,0,0,0);CHKERRQ(ierr); 316 317 ierr = PetscViewerDestroy(&viewer);CHKERRQ(ierr); 318 PetscFunctionReturn(0); 319 } 320 321 #undef __FUNCT__ 322 #define __FUNCT__ "ElementCreate" 323 static PetscErrorCode ElementCreate(TS ts,Stack *stack,StackElement *e,PetscInt stepnum,PetscReal time,Vec X) 324 { 325 Vec *Y; 326 PetscInt i; 327 PetscReal timeprev; 328 PetscErrorCode ierr; 329 330 PetscFunctionBegin; 331 ierr = PetscCalloc1(1,e);CHKERRQ(ierr); 332 ierr = VecDuplicate(X,&(*e)->X);CHKERRQ(ierr); 333 ierr = VecCopy(X,(*e)->X);CHKERRQ(ierr); 334 if (stack->numY > 0 && !stack->solution_only) { 335 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 336 ierr = VecDuplicateVecs(Y[0],stack->numY,&(*e)->Y);CHKERRQ(ierr); 337 for (i=0;i<stack->numY;i++) { 338 ierr = VecCopy(Y[i],(*e)->Y[i]);CHKERRQ(ierr); 339 } 340 } 341 (*e)->stepnum = stepnum; 342 (*e)->time = time; 343 /* for consistency */ 344 if (stepnum == 0) { 345 (*e)->timeprev = (*e)->time - ts->time_step; 346 } else { 347 ierr = TSGetPrevTime(ts,&timeprev);CHKERRQ(ierr); 348 (*e)->timeprev = timeprev; 349 } 350 PetscFunctionReturn(0); 351 } 352 353 #undef __FUNCT__ 354 #define __FUNCT__ "ElementDestroy" 355 static PetscErrorCode ElementDestroy(Stack *stack,StackElement e) 356 { 357 PetscErrorCode ierr; 358 359 PetscFunctionBegin; 360 ierr = VecDestroy(&e->X);CHKERRQ(ierr); 361 if (!stack->solution_only) { 362 ierr = VecDestroyVecs(stack->numY,&e->Y);CHKERRQ(ierr); 363 } 364 ierr = PetscFree(e);CHKERRQ(ierr); 365 PetscFunctionReturn(0); 366 } 367 368 #undef __FUNCT__ 369 #define __FUNCT__ "UpdateTS" 370 static PetscErrorCode UpdateTS(TS ts,Stack *stack,StackElement e) 371 { 372 Vec *Y; 373 PetscInt i; 374 PetscErrorCode ierr; 375 376 PetscFunctionBegin; 377 ierr = VecCopy(e->X,ts->vec_sol);CHKERRQ(ierr); 378 if (!stack->solution_only) { 379 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 380 for (i=0;i<stack->numY;i++) { 381 ierr = VecCopy(e->Y[i],Y[i]);CHKERRQ(ierr); 382 } 383 } 384 ierr = TSSetTimeStep(ts,e->timeprev-e->time);CHKERRQ(ierr); /* stepsize will be negative */ 385 ts->ptime = e->time; 386 ts->ptime_prev = e->timeprev; 387 PetscFunctionReturn(0); 388 } 389 390 #undef __FUNCT__ 391 #define __FUNCT__ "ReCompute" 392 static PetscErrorCode ReCompute(TS ts,TJScheduler *tjsch,PetscInt stepnumbegin,PetscInt stepnumend) 393 { 394 Stack *stack = &tjsch->stack; 395 PetscInt i,adjsteps; 396 PetscReal stepsize; 397 PetscErrorCode ierr; 398 399 PetscFunctionBegin; 400 adjsteps = ts->steps; 401 /* reset ts context */ 402 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 403 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 404 ts->steps = stepnumbegin; /* global step number */ 405 for (i=ts->steps;i<stepnumend;i++) { /* assume fixed step size */ 406 if (stack->solution_only && !tjsch->skip_trajectory) { /* revolve online need this */ 407 ierr = TSTrajectorySet(ts->trajectory,ts,ts->steps,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 408 } 409 ierr = TSMonitor(ts,ts->steps,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 410 ierr = TSStep(ts);CHKERRQ(ierr); 411 if (!stack->solution_only && !tjsch->skip_trajectory) { 412 ierr = TSTrajectorySet(ts->trajectory,ts,ts->steps,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 413 } 414 if (ts->event) { 415 ierr = TSEventMonitor(ts);CHKERRQ(ierr); 416 } 417 if (!ts->steprollback) { 418 ierr = TSPostStep(ts);CHKERRQ(ierr); 419 } 420 } 421 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 422 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 423 ts->steps = adjsteps; 424 ts->total_steps = stepnumend; 425 PetscFunctionReturn(0); 426 } 427 428 #undef __FUNCT__ 429 #define __FUNCT__ "TopLevelStore" 430 static PetscErrorCode TopLevelStore(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscInt localstepnum,PetscInt laststridesize,PetscBool *done) 431 { 432 Stack *stack = &tjsch->stack; 433 DiskStack *diskstack = &tjsch->diskstack; 434 PetscInt stridenum; 435 PetscErrorCode ierr; 436 437 PetscFunctionBegin; 438 *done = PETSC_FALSE; 439 stridenum = stepnum/tjsch->stride; 440 /* make sure saved checkpoint id starts from 1 441 skip last stride when using stridenum+1 442 skip first stride when using stridenum */ 443 if (stack->solution_only) { 444 if (tjsch->save_stack) { 445 if (localstepnum == tjsch->stride-1 && stepnum < tjsch->total_steps-laststridesize) { /* current step will be saved without going through stack */ 446 ierr = StackDumpAll(ts,stack,stridenum+1);CHKERRQ(ierr); 447 if (diskstack) diskstack->container[++diskstack->top] = stridenum+1; 448 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mDump stack to file\033[0m\n"); 449 *done = PETSC_TRUE; 450 } 451 } else { 452 if (!tjsch->recompute && localstepnum == 0 && stepnum < tjsch->total_steps-laststridesize) { 453 ierr = DumpSingle(ts,stack,stridenum+1);CHKERRQ(ierr); 454 if (diskstack) diskstack->container[++diskstack->top] = stridenum+1; 455 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mDump a single point (solution) to file\033[0m\n"); 456 *done = PETSC_TRUE; 457 } 458 } 459 } else { 460 if (tjsch->save_stack) { 461 if (localstepnum == 0 && stepnum < tjsch->total_steps && stepnum != 0) { /* skip the first stride */ 462 ierr = StackDumpAll(ts,stack,stridenum);CHKERRQ(ierr); 463 if (diskstack) diskstack->container[++diskstack->top] = stridenum; 464 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mDump stack to file\033[0m\n"); 465 *done = PETSC_TRUE; 466 } 467 } else { 468 if (!tjsch->recompute && localstepnum == 1 && stepnum < tjsch->total_steps-laststridesize) { 469 ierr = DumpSingle(ts,stack,stridenum+1);CHKERRQ(ierr); 470 if (diskstack) diskstack->container[++diskstack->top] = stridenum+1; 471 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mDump a single point (solution+stages) to file\033[0m\n"); 472 *done = PETSC_TRUE; 473 } 474 } 475 } 476 PetscFunctionReturn(0); 477 } 478 479 #undef __FUNCT__ 480 #define __FUNCT__ "SetTrajN" 481 static PetscErrorCode SetTrajN(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 482 { 483 Stack *stack = &tjsch->stack; 484 StackElement e; 485 PetscErrorCode ierr; 486 487 PetscFunctionBegin; 488 /* skip the last two steps of each stride or the whole interval */ 489 if (stack->solution_only && (stepnum >= tjsch->total_steps-1 || tjsch->recompute)) PetscFunctionReturn(0); //? 490 /* skip the first and the last steps of each stride or the whole interval */ 491 if (!stack->solution_only && (stepnum == 0 || stepnum == tjsch->total_steps)) PetscFunctionReturn(0); 492 493 if (stepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 494 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 495 ierr = StackPush(stack,e);CHKERRQ(ierr); 496 PetscFunctionReturn(0); 497 } 498 499 #undef __FUNCT__ 500 #define __FUNCT__ "GetTrajN" 501 static PetscErrorCode GetTrajN(TS ts,TJScheduler *tjsch,PetscInt stepnum) 502 { 503 Stack *stack = &tjsch->stack; 504 PetscReal stepsize; 505 StackElement e; 506 PetscErrorCode ierr; 507 508 PetscFunctionBegin; 509 if (stepnum == tjsch->total_steps) { 510 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 511 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 512 PetscFunctionReturn(0); 513 } 514 /* restore a checkpoint */ 515 ierr = StackTop(stack,&e);CHKERRQ(ierr); 516 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 517 if (stack->solution_only) {/* recompute one step */ 518 tjsch->recompute = PETSC_TRUE; 519 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 520 } 521 ierr = StackPop(stack,&e);CHKERRQ(ierr); 522 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 523 PetscFunctionReturn(0); 524 } 525 526 #undef __FUNCT__ 527 #define __FUNCT__ "SetTrajTLNR" 528 static PetscErrorCode SetTrajTLNR(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 529 { 530 Stack *stack = &tjsch->stack; 531 PetscInt localstepnum,laststridesize; 532 StackElement e; 533 PetscBool done; 534 PetscErrorCode ierr; 535 536 PetscFunctionBegin; 537 if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 538 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 539 if (tjsch->save_stack && tjsch->recompute) PetscFunctionReturn(0); 540 541 localstepnum = stepnum%tjsch->stride; 542 /* (stride size-1) checkpoints are saved in each stride; an extra point is added by StackDumpAll() */ 543 laststridesize = tjsch->total_steps%tjsch->stride; 544 if (!laststridesize) laststridesize = tjsch->stride; 545 546 if (!tjsch->recompute) { 547 ierr = TopLevelStore(ts,tjsch,stepnum,localstepnum,laststridesize,&done);CHKERRQ(ierr); 548 if (!tjsch->save_stack && stepnum < tjsch->total_steps-laststridesize) PetscFunctionReturn(0); 549 } 550 if (!stack->solution_only && localstepnum == 0) PetscFunctionReturn(0); /* skip last point in each stride at recompute stage or last stride */ 551 if (stack->solution_only && localstepnum == tjsch->stride-1) PetscFunctionReturn(0); /* skip last step in each stride at recompute stage or last stride */ 552 553 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 554 ierr = StackPush(stack,e);CHKERRQ(ierr); 555 PetscFunctionReturn(0); 556 } 557 558 #undef __FUNCT__ 559 #define __FUNCT__ "GetTrajTLNR" 560 static PetscErrorCode GetTrajTLNR(TS ts,TJScheduler *tjsch,PetscInt stepnum) 561 { 562 Stack *stack = &tjsch->stack; 563 PetscInt id,localstepnum,laststridesize; 564 PetscReal stepsize; 565 StackElement e; 566 PetscErrorCode ierr; 567 568 PetscFunctionBegin; 569 if (stepnum == tjsch->total_steps) { 570 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 571 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 572 PetscFunctionReturn(0); 573 } 574 575 localstepnum = stepnum%tjsch->stride; 576 laststridesize = tjsch->total_steps%tjsch->stride; 577 if (!laststridesize) laststridesize = tjsch->stride; 578 if (stack->solution_only) { 579 /* fill stack with info */ 580 if (localstepnum == 0 && tjsch->total_steps-stepnum >= laststridesize) { 581 id = stepnum/tjsch->stride; 582 if (tjsch->save_stack) { 583 ierr = StackLoadAll(ts,stack,id);CHKERRQ(ierr); 584 tjsch->recompute = PETSC_TRUE; 585 tjsch->skip_trajectory = PETSC_TRUE; 586 ierr = ReCompute(ts,tjsch,id*tjsch->stride-1,id*tjsch->stride);CHKERRQ(ierr); 587 tjsch->skip_trajectory = PETSC_FALSE; 588 } else { 589 ierr = LoadSingle(ts,stack,id);CHKERRQ(ierr); 590 tjsch->recompute = PETSC_TRUE; 591 ierr = ReCompute(ts,tjsch,(id-1)*tjsch->stride,id*tjsch->stride);CHKERRQ(ierr); 592 } 593 PetscFunctionReturn(0); 594 } 595 /* restore a checkpoint */ 596 ierr = StackPop(stack,&e);CHKERRQ(ierr); 597 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 598 tjsch->recompute = PETSC_TRUE; 599 tjsch->skip_trajectory = PETSC_TRUE; 600 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 601 tjsch->skip_trajectory = PETSC_FALSE; 602 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 603 } else { 604 /* fill stack with info */ 605 if (localstepnum == 0 && tjsch->total_steps-stepnum >= laststridesize) { 606 id = stepnum/tjsch->stride; 607 if (tjsch->save_stack) { 608 ierr = StackLoadAll(ts,stack,id);CHKERRQ(ierr); 609 } else { 610 ierr = LoadSingle(ts,stack,id);CHKERRQ(ierr); 611 ierr = ElementCreate(ts,stack,&e,(id-1)*tjsch->stride+1,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 612 ierr = StackPush(stack,e);CHKERRQ(ierr); 613 tjsch->recompute = PETSC_TRUE; 614 ierr = ReCompute(ts,tjsch,e->stepnum,id*tjsch->stride);CHKERRQ(ierr); 615 } 616 PetscFunctionReturn(0); 617 } 618 /* restore a checkpoint */ 619 ierr = StackPop(stack,&e);CHKERRQ(ierr); 620 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 621 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 622 } 623 PetscFunctionReturn(0); 624 } 625 626 #ifdef PETSC_HAVE_REVOLVE 627 static void printwhattodo(PetscInt whattodo,RevolveCTX *rctx,PetscInt shift) 628 { 629 switch(whattodo) { 630 case 1: 631 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mAdvance from %D to %D\033[0m\n",rctx->oldcapo+shift,rctx->capo+shift); 632 break; 633 case 2: 634 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mStore in checkpoint number %D (located in RAM)\033[0m\n",rctx->check); 635 break; 636 case 3: 637 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mFirst turn: Initialize adjoints and reverse first step\033[0m\n"); 638 break; 639 case 4: 640 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mForward and reverse one step\033[0m\n"); 641 break; 642 case 5: 643 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mRestore in checkpoint number %D (located in RAM)\033[0m\n",rctx->check); 644 break; 645 case 7: 646 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mStore in checkpoint number %D (located on disk)\033[0m\n",rctx->check); 647 break; 648 case 8: 649 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mRestore in checkpoint number %D (located on disk)\033[0m\n",rctx->check); 650 break; 651 case -1: 652 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mError!"); 653 break; 654 } 655 } 656 657 static void printwhattodo2(PetscInt whattodo,RevolveCTX *rctx,PetscInt shift) 658 { 659 switch(whattodo) { 660 case 1: 661 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Advance from stride %D to stride %D\033[0m\n",rctx->oldcapo+shift,rctx->capo+shift); 662 break; 663 case 2: 664 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Store in checkpoint number %D\033[0m\n",rctx->check); 665 break; 666 case 3: 667 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] First turn: Initialize adjoints and reverse first stride\033[0m\n"); 668 break; 669 case 4: 670 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Forward and reverse one stride\033[0m\n"); 671 break; 672 case 5: 673 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Restore in checkpoint number %D\033[0m\n",rctx->check); 674 break; 675 case 7: 676 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Store in top-level checkpoint number %D\033[0m\n",rctx->check); 677 break; 678 case 8: 679 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Restore in top-level checkpoint number %D\033[0m\n",rctx->check); 680 break; 681 case -1: 682 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Error!"); 683 break; 684 } 685 } 686 687 #undef __FUNCT__ 688 #define __FUNCT__ "ApplyRevolve" 689 static PetscErrorCode ApplyRevolve(SchedulerType stype,RevolveCTX *rctx,PetscInt total_steps,PetscInt stepnum,PetscInt localstepnum,PetscBool toplevel,PetscInt *store) 690 { 691 PetscInt shift,whattodo; 692 693 PetscFunctionBegin; 694 *store = 0; 695 // if (rctx->reverseonestep && stepnum == total_steps) { /* intermediate information is ready inside TS, this happens at last time step */ 696 // rctx->reverseonestep = PETSC_FALSE; 697 // PetscFunctionReturn(0); 698 // } 699 if (rctx->stepsleft > 0) { /* advance the solution without checkpointing anything as Revolve requires */ 700 rctx->stepsleft--; 701 PetscFunctionReturn(0); 702 } 703 /* let Revolve determine what to do next */ 704 shift = stepnum-localstepnum; 705 rctx->oldcapo = rctx->capo; 706 rctx->capo = localstepnum; 707 708 if (!toplevel) whattodo = revolve_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); 709 else whattodo = revolve2_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); 710 if (stype == REVOLVE_ONLINE && whattodo == 8) whattodo = 5; 711 if (stype == REVOLVE_ONLINE && whattodo == 7) whattodo = 2; 712 if (!toplevel) printwhattodo(whattodo,rctx,shift); 713 else printwhattodo2(whattodo,rctx,shift); 714 if (whattodo == -1) SETERRQ(PETSC_COMM_WORLD,PETSC_ERR_LIB,"Error in the Revolve library"); 715 if (whattodo == 1) { /* advance some time steps */ 716 if (stype == REVOLVE_ONLINE && rctx->capo >= total_steps-1) { 717 revolve_turn(total_steps,&rctx->capo,&rctx->fine); 718 if (!toplevel) printwhattodo(whattodo,rctx,shift); 719 else printwhattodo2(whattodo,rctx,shift); 720 } 721 rctx->stepsleft = rctx->capo-rctx->oldcapo-1; 722 } 723 if (whattodo == 3 || whattodo == 4) { /* ready for a reverse step */ 724 rctx->reverseonestep = PETSC_TRUE; 725 } 726 if (whattodo == 5) { /* restore a checkpoint and ask Revolve what to do next */ 727 rctx->oldcapo = rctx->capo; 728 if (!toplevel) whattodo = revolve_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); /* must return 1 or 3 or 4*/ 729 else whattodo = revolve2_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); 730 if (!toplevel) printwhattodo(whattodo,rctx,shift); 731 else printwhattodo2(whattodo,rctx,shift); 732 if (whattodo == 3 || whattodo == 4) rctx->reverseonestep = PETSC_TRUE; 733 if (whattodo == 1) rctx->stepsleft = rctx->capo-rctx->oldcapo; 734 } 735 if (whattodo == 7) { /* save the checkpoint to disk */ 736 *store = 2; 737 rctx->oldcapo = rctx->capo; 738 whattodo = revolve_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); /* must return 1 */ 739 printwhattodo(whattodo,rctx,shift); 740 rctx->stepsleft = rctx->capo-rctx->oldcapo-1; 741 } 742 if (whattodo == 2) { /* store a checkpoint to RAM and ask Revolve how many time steps to advance next */ 743 *store = 1; 744 rctx->oldcapo = rctx->capo; 745 if (!toplevel) whattodo = revolve_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); /* must return 1 */ 746 else whattodo = revolve2_action(&rctx->check,&rctx->capo,&rctx->fine,rctx->snaps_in,&rctx->info,&rctx->where); 747 if (!toplevel) printwhattodo(whattodo,rctx,shift); 748 else printwhattodo2(whattodo,rctx,shift); 749 if (stype == REVOLVE_ONLINE && rctx->capo >= total_steps-1) { 750 revolve_turn(total_steps,&rctx->capo,&rctx->fine); 751 printwhattodo(whattodo,rctx,shift); 752 } 753 rctx->stepsleft = rctx->capo-rctx->oldcapo-1; 754 } 755 PetscFunctionReturn(0); 756 } 757 758 #undef __FUNCT__ 759 #define __FUNCT__ "SetTrajROF" 760 static PetscErrorCode SetTrajROF(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 761 { 762 Stack *stack = &tjsch->stack; 763 PetscInt store; 764 StackElement e; 765 PetscErrorCode ierr; 766 767 PetscFunctionBegin; 768 if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 769 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 770 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,stepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 771 if (store == 1) { 772 if (stepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 773 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 774 ierr = StackPush(stack,e);CHKERRQ(ierr); 775 } 776 PetscFunctionReturn(0); 777 } 778 779 #undef __FUNCT__ 780 #define __FUNCT__ "GetTrajROF" 781 static PetscErrorCode GetTrajROF(TS ts,TJScheduler *tjsch,PetscInt stepnum) 782 { 783 Stack *stack = &tjsch->stack; 784 PetscInt whattodo,shift,store; 785 PetscReal stepsize; 786 StackElement e; 787 PetscErrorCode ierr; 788 789 PetscFunctionBegin; 790 if (stepnum == 0 || stepnum == tjsch->total_steps) { 791 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 792 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 793 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 794 PetscFunctionReturn(0); 795 } 796 /* restore a checkpoint */ 797 ierr = StackTop(stack,&e);CHKERRQ(ierr); 798 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 799 if (stack->solution_only) { /* start with restoring a checkpoint */ 800 tjsch->rctx->capo = stepnum; 801 tjsch->rctx->oldcapo = tjsch->rctx->capo; 802 shift = 0; 803 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 804 printwhattodo(whattodo,tjsch->rctx,shift); 805 } else { /* 2 revolve actions: restore a checkpoint and then advance */ 806 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,stepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 807 if (!tjsch->rctx->reverseonestep && tjsch->rctx->stepsleft > 0) { 808 tjsch->rctx->stepsleft--; 809 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mSkip the step from %D to %D (already checkpointed)\033[0m\n",tjsch->rctx->oldcapo,tjsch->rctx->oldcapo+1); 810 } 811 } 812 if (stack->solution_only || (!stack->solution_only && e->stepnum < stepnum)) { 813 tjsch->recompute = PETSC_TRUE; 814 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 815 } 816 if ((stack->solution_only && e->stepnum+1 == stepnum) || (!stack->solution_only && e->stepnum == stepnum)) { 817 ierr = StackPop(stack,&e);CHKERRQ(ierr); 818 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 819 } 820 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 821 PetscFunctionReturn(0); 822 } 823 824 #undef __FUNCT__ 825 #define __FUNCT__ "SetTrajRON" 826 static PetscErrorCode SetTrajRON(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 827 { 828 Stack *stack = &tjsch->stack; 829 Vec *Y; 830 PetscInt i,store; 831 PetscReal timeprev; 832 StackElement e; 833 RevolveCTX *rctx = tjsch->rctx; 834 PetscErrorCode ierr; 835 836 PetscFunctionBegin; 837 if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 838 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 839 ierr = ApplyRevolve(tjsch->stype,rctx,tjsch->total_steps,stepnum,stepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 840 if (store == 1) { 841 if (rctx->check != stack->top+1) { /* overwrite some non-top checkpoint in the stack */ 842 ierr = StackFind(stack,&e,rctx->check);CHKERRQ(ierr); 843 ierr = VecCopy(X,e->X);CHKERRQ(ierr); 844 if (stack->numY > 0 && !stack->solution_only) { 845 ierr = TSGetStages(ts,&stack->numY,&Y);CHKERRQ(ierr); 846 for (i=0;i<stack->numY;i++) { 847 ierr = VecCopy(Y[i],e->Y[i]);CHKERRQ(ierr); 848 } 849 } 850 e->stepnum = stepnum; 851 e->time = time; 852 ierr = TSGetPrevTime(ts,&timeprev);CHKERRQ(ierr); 853 e->timeprev = timeprev; 854 } else { 855 if (stepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 856 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 857 ierr = StackPush(stack,e);CHKERRQ(ierr); 858 } 859 } 860 PetscFunctionReturn(0); 861 } 862 863 #undef __FUNCT__ 864 #define __FUNCT__ "GetTrajRON" 865 static PetscErrorCode GetTrajRON(TS ts,TJScheduler *tjsch,PetscInt stepnum) 866 { 867 Stack *stack = &tjsch->stack; 868 PetscInt whattodo,shift; 869 PetscReal stepsize; 870 StackElement e; 871 PetscErrorCode ierr; 872 873 PetscFunctionBegin; 874 if (stepnum == 0 || stepnum == tjsch->total_steps) { 875 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 876 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 877 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 878 PetscFunctionReturn(0); 879 } 880 tjsch->rctx->capo = stepnum; 881 tjsch->rctx->oldcapo = tjsch->rctx->capo; 882 shift = 0; 883 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); /* whattodo=restore */ 884 if (whattodo == 8) whattodo = 5; 885 printwhattodo(whattodo,tjsch->rctx,shift); 886 /* restore a checkpoint */ 887 ierr = StackFind(stack,&e,tjsch->rctx->check);CHKERRQ(ierr); 888 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 889 if (!stack->solution_only) { /* whattodo must be 5 */ 890 /* ask Revolve what to do next */ 891 tjsch->rctx->oldcapo = tjsch->rctx->capo; 892 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); /* must return 1 or 3 or 4*/ 893 printwhattodo(whattodo,tjsch->rctx,shift); 894 if (whattodo == 3 || whattodo == 4) tjsch->rctx->reverseonestep = PETSC_TRUE; 895 if (whattodo == 1) tjsch->rctx->stepsleft = tjsch->rctx->capo-tjsch->rctx->oldcapo; 896 if (!tjsch->rctx->reverseonestep && tjsch->rctx->stepsleft > 0) { 897 tjsch->rctx->stepsleft--; 898 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mSkip the step from %D to %D (already checkpointed)\033[0m\n",tjsch->rctx->oldcapo,tjsch->rctx->oldcapo+1); 899 } 900 } 901 if (stack->solution_only || (!stack->solution_only && e->stepnum < stepnum)) { 902 tjsch->recompute = PETSC_TRUE; 903 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 904 } 905 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 906 PetscFunctionReturn(0); 907 } 908 909 #undef __FUNCT__ 910 #define __FUNCT__ "SetTrajTLR" 911 static PetscErrorCode SetTrajTLR(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 912 { 913 Stack *stack = &tjsch->stack; 914 PetscInt store,localstepnum,laststridesize; 915 StackElement e; 916 RevolveCTX *rctx = tjsch->rctx; 917 PetscBool done = PETSC_FALSE; 918 PetscErrorCode ierr; 919 920 PetscFunctionBegin; 921 if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 922 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 923 924 localstepnum = stepnum%tjsch->stride; 925 laststridesize = tjsch->total_steps%tjsch->stride; 926 if (!laststridesize) laststridesize = tjsch->stride; 927 928 if (!tjsch->recompute) { /* skip last stride */ 929 ierr = TopLevelStore(ts,tjsch,stepnum,localstepnum,laststridesize,&done);CHKERRQ(ierr); 930 /* different starting points for last stride between solutin_only and !solutin_only */ 931 if (!stack->solution_only && !tjsch->save_stack && stepnum <= tjsch->total_steps-laststridesize) PetscFunctionReturn(0); 932 if (stack->solution_only && !tjsch->save_stack && stepnum < tjsch->total_steps-laststridesize) PetscFunctionReturn(0); 933 } 934 935 if (tjsch->save_stack && done) { 936 revolve_reset(); 937 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 938 rctx = tjsch->rctx; 939 rctx->check = 0; 940 rctx->capo = 0; 941 rctx->fine = tjsch->stride; 942 tjsch->rctx->reverseonestep = PETSC_FALSE; 943 PetscFunctionReturn(0); 944 } 945 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,localstepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 946 if (store == 1) { 947 if (localstepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 948 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 949 ierr = StackPush(stack,e);CHKERRQ(ierr); 950 } 951 952 PetscFunctionReturn(0); 953 } 954 955 #undef __FUNCT__ 956 #define __FUNCT__ "GetTrajTLR" 957 static PetscErrorCode GetTrajTLR(TS ts,TJScheduler *tjsch,PetscInt stepnum) 958 { 959 Stack *stack = &tjsch->stack; 960 PetscInt whattodo,shift; 961 PetscInt localstepnum,stridenum,laststridesize,store; 962 PetscReal stepsize; 963 StackElement e; 964 PetscErrorCode ierr; 965 966 PetscFunctionBegin; 967 localstepnum = stepnum%tjsch->stride; 968 stridenum = stepnum/tjsch->stride; 969 if (stepnum == tjsch->total_steps) { 970 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 971 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 972 if ( tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 973 PetscFunctionReturn(0); 974 } 975 laststridesize = tjsch->total_steps%tjsch->stride; 976 if (!laststridesize) laststridesize = tjsch->stride; 977 if (stack->solution_only) { 978 /* fill stack */ 979 if (localstepnum == 0 && stepnum <= tjsch->total_steps-laststridesize) { 980 if (tjsch->save_stack) { 981 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad stack from file\033[0m\n"); 982 ierr = StackLoadAll(ts,stack,stridenum);CHKERRQ(ierr); 983 revolve_reset(); 984 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 985 tjsch->rctx->check = 0; 986 tjsch->rctx->capo = 0; 987 tjsch->rctx->fine = tjsch->stride; 988 whattodo = 0; 989 while(whattodo!=3) { /* stupid revolve */ 990 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 991 } 992 tjsch->recompute = PETSC_TRUE; 993 tjsch->skip_trajectory = PETSC_TRUE; 994 ierr = ReCompute(ts,tjsch,stridenum*tjsch->stride-1,stridenum*tjsch->stride);CHKERRQ(ierr); 995 tjsch->skip_trajectory = PETSC_FALSE; 996 } else { 997 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad a single point from file\033[0m\n"); 998 ierr = LoadSingle(ts,stack,stridenum);CHKERRQ(ierr); 999 revolve_reset(); 1000 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1001 tjsch->rctx->check = 0; 1002 tjsch->rctx->capo = 0; 1003 tjsch->rctx->fine = tjsch->stride; 1004 tjsch->recompute = PETSC_TRUE; 1005 ierr = ReCompute(ts,tjsch,(stridenum-1)*tjsch->stride,stridenum*tjsch->stride);CHKERRQ(ierr); 1006 } 1007 PetscFunctionReturn(0); 1008 } 1009 /* restore a checkpoint */ 1010 ierr = StackTop(stack,&e);CHKERRQ(ierr); 1011 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 1012 /* start with restoring a checkpoint */ 1013 tjsch->rctx->capo = stepnum; 1014 tjsch->rctx->oldcapo = tjsch->rctx->capo; 1015 shift = stepnum-localstepnum; 1016 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1017 printwhattodo(whattodo,tjsch->rctx,shift); 1018 tjsch->recompute = PETSC_TRUE; 1019 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 1020 if (e->stepnum+1 == stepnum) { 1021 ierr = StackPop(stack,&e);CHKERRQ(ierr); 1022 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 1023 } 1024 } else { 1025 /* fill stack with info */ 1026 if (localstepnum == 0 && tjsch->total_steps-stepnum >= laststridesize) { 1027 if (tjsch->save_stack) { 1028 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad stack from file\033[0m\n"); 1029 ierr = StackLoadAll(ts,stack,stridenum);CHKERRQ(ierr); 1030 revolve_reset(); 1031 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1032 tjsch->rctx->check = 0; 1033 tjsch->rctx->capo = 0; 1034 tjsch->rctx->fine = tjsch->stride; 1035 whattodo = 0; 1036 while(whattodo!=3) { /* stupid revolve */ 1037 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1038 } 1039 } else { 1040 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad a single point from file\033[0m\n"); 1041 ierr = LoadSingle(ts,stack,stridenum);CHKERRQ(ierr); 1042 revolve_reset(); 1043 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1044 tjsch->rctx->check = 0; 1045 tjsch->rctx->capo = 0; 1046 tjsch->rctx->fine = tjsch->stride; 1047 shift = stepnum-localstepnum; 1048 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1049 printwhattodo(whattodo,tjsch->rctx,shift); 1050 ierr = ElementCreate(ts,stack,&e,(stridenum-1)*tjsch->stride+1,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 1051 ierr = StackPush(stack,e);CHKERRQ(ierr); 1052 tjsch->recompute = PETSC_TRUE; 1053 ierr = ReCompute(ts,tjsch,e->stepnum,stridenum*tjsch->stride);CHKERRQ(ierr); 1054 if ( tjsch->rctx->reverseonestep) { /* ready for the reverse step */ 1055 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 1056 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 1057 tjsch->rctx->reverseonestep = PETSC_FALSE; 1058 } 1059 } 1060 PetscFunctionReturn(0); 1061 } 1062 /* restore a checkpoint */ 1063 ierr = StackTop(stack,&e);CHKERRQ(ierr); 1064 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 1065 /* 2 revolve actions: restore a checkpoint and then advance */ 1066 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,localstepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 1067 if (!tjsch->rctx->reverseonestep && tjsch->rctx->stepsleft > 0) { 1068 tjsch->rctx->stepsleft--; 1069 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mSkip the step from %D to %D (already checkpointed)\033[0m\n",stepnum-localstepnum+tjsch->rctx->oldcapo,stepnum-localstepnum+tjsch->rctx->oldcapo+1); 1070 } 1071 if (e->stepnum < stepnum) { 1072 tjsch->recompute = PETSC_TRUE; 1073 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 1074 } 1075 if (e->stepnum == stepnum) { 1076 ierr = StackPop(stack,&e);CHKERRQ(ierr); 1077 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 1078 } 1079 } 1080 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 1081 PetscFunctionReturn(0); 1082 } 1083 1084 #undef __FUNCT__ 1085 #define __FUNCT__ "SetTrajTLTR" 1086 static PetscErrorCode SetTrajTLTR(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 1087 { 1088 Stack *stack = &tjsch->stack; 1089 PetscInt store,localstepnum,stridenum,laststridesize; 1090 StackElement e; 1091 RevolveCTX *rctx = tjsch->rctx; 1092 PetscBool done = PETSC_FALSE; 1093 PetscErrorCode ierr; 1094 1095 PetscFunctionBegin; 1096 //if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 1097 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 1098 1099 localstepnum = stepnum%tjsch->stride; /* index at the bottom level (inside a stride) */ 1100 stridenum = stepnum/tjsch->stride; /* index at the top level */ 1101 laststridesize = tjsch->total_steps%tjsch->stride; 1102 if (!laststridesize) laststridesize = tjsch->stride; 1103 if (stack->solution_only && localstepnum == 0 && !tjsch->rctx2->reverseonestep) { 1104 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx2,(tjsch->total_steps+tjsch->stride-1)/tjsch->stride,stridenum,stridenum,PETSC_TRUE,&tjsch->store_stride);CHKERRQ(ierr); 1105 } 1106 if (!stack->solution_only && localstepnum == 1 && !tjsch->rctx2->reverseonestep) { 1107 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx2,(tjsch->total_steps+tjsch->stride-1)/tjsch->stride,stridenum,stridenum,PETSC_TRUE,&tjsch->store_stride);CHKERRQ(ierr); 1108 } 1109 if (tjsch->store_stride) { 1110 ierr = TopLevelStore(ts,tjsch,stepnum,localstepnum,laststridesize,&done);CHKERRQ(ierr); 1111 if (tjsch->save_stack && done) { 1112 revolve_reset(); 1113 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1114 rctx = tjsch->rctx; 1115 rctx->check = 0; 1116 rctx->capo = 0; 1117 rctx->fine = tjsch->stride; 1118 tjsch->rctx->reverseonestep = PETSC_FALSE; 1119 PetscFunctionReturn(0); 1120 } 1121 } 1122 if (stepnum < tjsch->total_steps-laststridesize) { 1123 if (tjsch->save_stack && !tjsch->store_stride && !tjsch->rctx2->reverseonestep) PetscFunctionReturn(0); 1124 if (!tjsch->save_stack && !tjsch->rctx2->reverseonestep) PetscFunctionReturn(0); 1125 } 1126 if (!stack->solution_only && localstepnum == 0 && stepnum != tjsch->total_steps) PetscFunctionReturn(0); 1127 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,localstepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 1128 if (store == 1) { 1129 if (localstepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 1130 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 1131 ierr = StackPush(stack,e);CHKERRQ(ierr); 1132 } 1133 PetscFunctionReturn(0); 1134 } 1135 1136 #undef __FUNCT__ 1137 #define __FUNCT__ "GetTrajTLTR" 1138 static PetscErrorCode GetTrajTLTR(TS ts,TJScheduler *tjsch,PetscInt stepnum) 1139 { 1140 Stack *stack = &tjsch->stack; 1141 DiskStack *diskstack = &tjsch->diskstack; 1142 PetscInt i,whattodo,shift; 1143 PetscInt localstepnum,stridenum,restoredstridenum,laststridesize,store; 1144 PetscReal stepsize; 1145 StackElement e; 1146 PetscErrorCode ierr; 1147 1148 PetscFunctionBegin; 1149 localstepnum = stepnum%tjsch->stride; 1150 stridenum = stepnum/tjsch->stride; 1151 if (stepnum == tjsch->total_steps) { 1152 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 1153 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 1154 if ( tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 1155 PetscFunctionReturn(0); 1156 } 1157 laststridesize = tjsch->total_steps%tjsch->stride; 1158 if (!laststridesize) laststridesize = tjsch->stride; 1159 /* 1160 Last stride can be adjoined directly. All the other strides require that the stack in memory be ready before an adjoint step is taken (at the end of each stride). The following two cases need to be addressed differently: 1161 Case 1 (save_stack) 1162 Restore a disk checkpoint; update TS with the last element in the restored data; recompute to the current point. 1163 Case 2 (!save_stack) 1164 Restore a disk checkpoint; update TS with the restored point; recompute to the current point. 1165 */ 1166 if (localstepnum == 0 && stepnum <= tjsch->total_steps-laststridesize) { 1167 /* restore the top element in the stack for disk checkpoints */ 1168 restoredstridenum = diskstack->container[diskstack->top]; 1169 if (tjsch->rctx2->reverseonestep) tjsch->rctx2->reverseonestep = PETSC_FALSE; 1170 if (!tjsch->save_stack) { /* start with restoring a checkpoint */ 1171 tjsch->rctx2->capo = stridenum; 1172 tjsch->rctx2->oldcapo = tjsch->rctx2->capo; 1173 shift = 0; 1174 whattodo = revolve2_action(&tjsch->rctx2->check,&tjsch->rctx2->capo,&tjsch->rctx2->fine,tjsch->rctx2->snaps_in,&tjsch->rctx2->info,&tjsch->rctx2->where); 1175 printwhattodo2(whattodo,tjsch->rctx2,shift); 1176 } else { /* 2 revolve actions: restore a checkpoint and then advance */ 1177 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx2,(tjsch->total_steps+tjsch->stride-1)/tjsch->stride,stridenum,stridenum,PETSC_TRUE,&tjsch->store_stride);CHKERRQ(ierr); 1178 if (!tjsch->rctx2->reverseonestep && tjsch->rctx2->stepsleft > 0) { 1179 tjsch->rctx2->stepsleft--; 1180 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35m[Top Level] Skip the stride from %D to %D (already checkpointed)\033[0m\n",tjsch->rctx2->oldcapo,tjsch->rctx2->oldcapo+1); 1181 } 1182 } 1183 /* fill stack */ 1184 if (stack->solution_only) { 1185 if (tjsch->save_stack) { 1186 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad stack from file\033[0m\n"); 1187 ierr = StackLoadAll(ts,stack,restoredstridenum);CHKERRQ(ierr); 1188 /* recompute one step ahead */ 1189 tjsch->recompute = PETSC_TRUE; 1190 tjsch->skip_trajectory = PETSC_TRUE; 1191 ierr = ReCompute(ts,tjsch,stridenum*tjsch->stride-1,stridenum*tjsch->stride);CHKERRQ(ierr); 1192 tjsch->skip_trajectory = PETSC_FALSE; 1193 if (restoredstridenum < stridenum) { 1194 /* clear the stack */ 1195 if (stack->top > -1) { 1196 for (i=0;i<=stack->top;i++) { 1197 ierr = VecDestroy(&stack->container[i]->X);CHKERRQ(ierr); 1198 ierr = PetscFree(stack->container[i]);CHKERRQ(ierr); 1199 } 1200 stack->top = -1; 1201 } 1202 tjsch->recompute = PETSC_TRUE; 1203 ierr = ReCompute(ts,tjsch,restoredstridenum*tjsch->stride,stepnum);CHKERRQ(ierr); 1204 } else { /* stack ready, fast forward revolve status */ 1205 revolve_reset(); 1206 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1207 tjsch->rctx->check = 0; 1208 tjsch->rctx->capo = 0; 1209 tjsch->rctx->fine = tjsch->stride; 1210 whattodo = 0; 1211 while(whattodo!=3) { /* stupid revolve */ 1212 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1213 } 1214 } 1215 } else { 1216 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad a single point from file\033[0m\n"); 1217 ierr = LoadSingle(ts,stack,restoredstridenum);CHKERRQ(ierr); 1218 revolve_reset(); 1219 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1220 tjsch->rctx->check = 0; 1221 tjsch->rctx->capo = 0; 1222 tjsch->rctx->fine = tjsch->stride; 1223 tjsch->recompute = PETSC_TRUE; 1224 ierr = ReCompute(ts,tjsch,(stridenum-1)*tjsch->stride,stepnum);CHKERRQ(ierr); 1225 } 1226 } else { 1227 if (tjsch->save_stack) { 1228 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad stack from file\033[0m\n"); 1229 ierr = StackLoadAll(ts,stack,restoredstridenum);CHKERRQ(ierr); 1230 if (restoredstridenum < stridenum) { 1231 /* clear the stack */ 1232 if (stack->top > -1) { 1233 for (i=0;i<=stack->top;i++) { 1234 ierr = VecDestroy(&stack->container[i]->X);CHKERRQ(ierr); 1235 ierr = VecDestroyVecs(stack->numY,&stack->container[i]->Y);CHKERRQ(ierr); 1236 ierr = PetscFree(stack->container[i]);CHKERRQ(ierr); 1237 } 1238 stack->top = -1; 1239 } 1240 tjsch->recompute = PETSC_TRUE; 1241 ierr = ReCompute(ts,tjsch,restoredstridenum*tjsch->stride,stepnum);CHKERRQ(ierr); 1242 } else { /* stack ready, fast forward revolve status */ 1243 revolve_reset(); 1244 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1245 tjsch->rctx->check = 0; 1246 tjsch->rctx->capo = 0; 1247 tjsch->rctx->fine = tjsch->stride; 1248 whattodo = 0; 1249 while(whattodo!=3) { /* stupid revolve */ 1250 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1251 } 1252 } 1253 } else { 1254 PetscPrintf(PETSC_COMM_WORLD,"\x1B[33mLoad a single point from file\033[0m\n"); 1255 ierr = LoadSingle(ts,stack,restoredstridenum);CHKERRQ(ierr); 1256 revolve_reset(); 1257 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1258 tjsch->rctx->check = 0; 1259 tjsch->rctx->capo = 0; 1260 tjsch->rctx->fine = tjsch->stride; 1261 /* push first element to stack */ 1262 shift = stepnum-localstepnum; 1263 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1264 printwhattodo(whattodo,tjsch->rctx,shift); 1265 ierr = ElementCreate(ts,stack,&e,(stridenum-1)*tjsch->stride+1,ts->ptime,ts->vec_sol);CHKERRQ(ierr); 1266 ierr = StackPush(stack,e);CHKERRQ(ierr); 1267 tjsch->recompute = PETSC_TRUE; 1268 ierr = ReCompute(ts,tjsch,(stridenum-1)*tjsch->stride+1,stepnum);CHKERRQ(ierr); 1269 1270 if ( tjsch->rctx->reverseonestep) { /* ready for the reverse step */ 1271 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 1272 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 1273 tjsch->rctx->reverseonestep = PETSC_FALSE; 1274 } 1275 } 1276 } 1277 if (restoredstridenum == stridenum) diskstack->top--; 1278 PetscFunctionReturn(0); 1279 } 1280 1281 if (stack->solution_only) { 1282 /* restore a checkpoint */ 1283 ierr = StackTop(stack,&e);CHKERRQ(ierr); 1284 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 1285 /* start with restoring a checkpoint */ 1286 tjsch->rctx->capo = stepnum; 1287 tjsch->rctx->oldcapo = tjsch->rctx->capo; 1288 shift = stepnum-localstepnum; 1289 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); 1290 printwhattodo(whattodo,tjsch->rctx,shift); 1291 tjsch->recompute = PETSC_TRUE; 1292 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 1293 if (e->stepnum+1 == stepnum) { 1294 ierr = StackPop(stack,&e);CHKERRQ(ierr); 1295 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 1296 } 1297 } else { 1298 /* restore a checkpoint */ 1299 ierr = StackTop(stack,&e);CHKERRQ(ierr); 1300 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 1301 /* 2 revolve actions: restore a checkpoint and then advance */ 1302 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,localstepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 1303 if (!tjsch->rctx->reverseonestep && tjsch->rctx->stepsleft > 0) { 1304 tjsch->rctx->stepsleft--; 1305 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mSkip the step from %D to %D (already checkpointed)\033[0m\n",stepnum-localstepnum+tjsch->rctx->oldcapo,stepnum-localstepnum+tjsch->rctx->oldcapo+1); 1306 } 1307 if (e->stepnum < stepnum) { 1308 tjsch->recompute = PETSC_TRUE; 1309 ierr = ReCompute(ts,tjsch,e->stepnum,stepnum);CHKERRQ(ierr); 1310 } 1311 if (e->stepnum == stepnum) { 1312 ierr = StackPop(stack,&e);CHKERRQ(ierr); 1313 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 1314 } 1315 } 1316 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 1317 PetscFunctionReturn(0); 1318 } 1319 1320 #undef __FUNCT__ 1321 #define __FUNCT__ "SetTrajRMS" 1322 static PetscErrorCode SetTrajRMS(TS ts,TJScheduler *tjsch,PetscInt stepnum,PetscReal time,Vec X) 1323 { 1324 Stack *stack = &tjsch->stack; 1325 PetscInt store; 1326 StackElement e; 1327 PetscErrorCode ierr; 1328 1329 PetscFunctionBegin; 1330 if (!stack->solution_only && stepnum == 0) PetscFunctionReturn(0); 1331 if (stack->solution_only && stepnum == tjsch->total_steps) PetscFunctionReturn(0); 1332 ierr = ApplyRevolve(tjsch->stype,tjsch->rctx,tjsch->total_steps,stepnum,stepnum,PETSC_FALSE,&store);CHKERRQ(ierr); 1333 if (store == 1){ 1334 if (stepnum < stack->top) SETERRQ(tjsch->comm,PETSC_ERR_MEMC,"Illegal modification of a non-top stack element"); 1335 ierr = ElementCreate(ts,stack,&e,stepnum,time,X);CHKERRQ(ierr); 1336 ierr = StackPush(stack,e);CHKERRQ(ierr); 1337 } else if (store == 2) { 1338 ierr = DumpSingle(ts,stack,tjsch->rctx->check+1);CHKERRQ(ierr); 1339 } 1340 PetscFunctionReturn(0); 1341 } 1342 1343 #undef __FUNCT__ 1344 #define __FUNCT__ "GetTrajRMS" 1345 static PetscErrorCode GetTrajRMS(TS ts,TJScheduler *tjsch,PetscInt stepnum) 1346 { 1347 Stack *stack = &tjsch->stack; 1348 PetscInt whattodo,shift; 1349 PetscInt restart; 1350 PetscBool ondisk; 1351 PetscReal stepsize; 1352 StackElement e; 1353 PetscErrorCode ierr; 1354 1355 PetscFunctionBegin; 1356 if (stepnum == 0 || stepnum == tjsch->total_steps) { 1357 ierr = TSGetTimeStep(ts,&stepsize);CHKERRQ(ierr); 1358 ierr = TSSetTimeStep(ts,-stepsize);CHKERRQ(ierr); 1359 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 1360 PetscFunctionReturn(0); 1361 } 1362 tjsch->rctx->capo = stepnum; 1363 tjsch->rctx->oldcapo = tjsch->rctx->capo; 1364 shift = 0; 1365 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); /* whattodo=restore */ 1366 printwhattodo(whattodo,tjsch->rctx,shift); 1367 /* restore a checkpoint */ 1368 restart = tjsch->rctx->capo; 1369 if (!tjsch->rctx->where) { 1370 ondisk = PETSC_TRUE; 1371 ierr = LoadSingle(ts,stack,tjsch->rctx->check+1);CHKERRQ(ierr); 1372 ierr = TSSetTimeStep(ts,ts->ptime_prev-ts->ptime);CHKERRQ(ierr); 1373 } else { 1374 ondisk = PETSC_FALSE; 1375 ierr = StackTop(stack,&e);CHKERRQ(ierr); 1376 ierr = UpdateTS(ts,stack,e);CHKERRQ(ierr); 1377 } 1378 if (!stack->solution_only) { /* whattodo must be 5 or 8 */ 1379 /* ask Revolve what to do next */ 1380 tjsch->rctx->oldcapo = tjsch->rctx->capo; 1381 whattodo = revolve_action(&tjsch->rctx->check,&tjsch->rctx->capo,&tjsch->rctx->fine,tjsch->rctx->snaps_in,&tjsch->rctx->info,&tjsch->rctx->where); /* must return 1 or 3 or 4*/ 1382 printwhattodo(whattodo,tjsch->rctx,shift); 1383 if (whattodo == 3 || whattodo == 4) tjsch->rctx->reverseonestep = PETSC_TRUE; 1384 if (whattodo == 1) tjsch->rctx->stepsleft = tjsch->rctx->capo-tjsch->rctx->oldcapo; 1385 if (!tjsch->rctx->reverseonestep && tjsch->rctx->stepsleft > 0) { 1386 tjsch->rctx->stepsleft--; 1387 PetscPrintf(PETSC_COMM_WORLD,"\x1B[35mSkip the step from %D to %D (already checkpointed)\033[0m\n",tjsch->rctx->oldcapo,tjsch->rctx->oldcapo+1); 1388 } 1389 restart++; /* skip one step */ 1390 } 1391 if (stack->solution_only || (!stack->solution_only && restart < stepnum)) { 1392 tjsch->recompute = PETSC_TRUE; 1393 ierr = ReCompute(ts,tjsch,restart,stepnum);CHKERRQ(ierr); 1394 } 1395 if (!ondisk && ( (stack->solution_only && e->stepnum+1 == stepnum) || (!stack->solution_only && e->stepnum == stepnum) )) { 1396 ierr = StackPop(stack,&e);CHKERRQ(ierr); 1397 ierr = ElementDestroy(stack,e);CHKERRQ(ierr); 1398 } 1399 if (tjsch->rctx->reverseonestep) tjsch->rctx->reverseonestep = PETSC_FALSE; 1400 PetscFunctionReturn(0); 1401 } 1402 #endif 1403 1404 #undef __FUNCT__ 1405 #define __FUNCT__ "TSTrajectorySet_Memory" 1406 PetscErrorCode TSTrajectorySet_Memory(TSTrajectory tj,TS ts,PetscInt stepnum,PetscReal time,Vec X) 1407 { 1408 TJScheduler *tjsch = (TJScheduler*)tj->data; 1409 PetscErrorCode ierr; 1410 1411 PetscFunctionBegin; 1412 if (!tjsch->recompute) { /* use global stepnum in the forward sweep */ 1413 ierr = TSGetTotalSteps(ts,&stepnum);CHKERRQ(ierr); 1414 } 1415 /* for consistency */ 1416 if (!tjsch->recompute && stepnum == 0) ts->ptime_prev = ts->ptime-ts->time_step; 1417 switch (tjsch->stype) { 1418 case NONE: 1419 ierr = SetTrajN(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1420 break; 1421 case TWO_LEVEL_NOREVOLVE: 1422 ierr = SetTrajTLNR(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1423 break; 1424 #ifdef PETSC_HAVE_REVOLVE 1425 case TWO_LEVEL_REVOLVE: 1426 ierr = SetTrajTLR(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1427 break; 1428 case TWO_LEVEL_TWO_REVOLVE: 1429 ierr = SetTrajTLTR(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1430 break; 1431 case REVOLVE_OFFLINE: 1432 ierr = SetTrajROF(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1433 break; 1434 case REVOLVE_ONLINE: 1435 ierr = SetTrajRON(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1436 break; 1437 case REVOLVE_MULTISTAGE: 1438 ierr = SetTrajRMS(ts,tjsch,stepnum,time,X);CHKERRQ(ierr); 1439 break; 1440 #endif 1441 default: 1442 break; 1443 } 1444 PetscFunctionReturn(0); 1445 } 1446 1447 #undef __FUNCT__ 1448 #define __FUNCT__ "TSTrajectoryGet_Memory" 1449 PetscErrorCode TSTrajectoryGet_Memory(TSTrajectory tj,TS ts,PetscInt stepnum,PetscReal *t) 1450 { 1451 TJScheduler *tjsch = (TJScheduler*)tj->data; 1452 PetscErrorCode ierr; 1453 1454 PetscFunctionBegin; 1455 ierr = TSGetTotalSteps(ts,&stepnum);CHKERRQ(ierr); 1456 if (stepnum == 0) PetscFunctionReturn(0); 1457 switch (tjsch->stype) { 1458 case NONE: 1459 ierr = GetTrajN(ts,tjsch,stepnum);CHKERRQ(ierr); 1460 break; 1461 case TWO_LEVEL_NOREVOLVE: 1462 ierr = GetTrajTLNR(ts,tjsch,stepnum);CHKERRQ(ierr); 1463 break; 1464 #ifdef PETSC_HAVE_REVOLVE 1465 case TWO_LEVEL_REVOLVE: 1466 ierr = GetTrajTLR(ts,tjsch,stepnum);CHKERRQ(ierr); 1467 break; 1468 case TWO_LEVEL_TWO_REVOLVE: 1469 ierr = GetTrajTLTR(ts,tjsch,stepnum);CHKERRQ(ierr); 1470 break; 1471 case REVOLVE_OFFLINE: 1472 ierr = GetTrajROF(ts,tjsch,stepnum);CHKERRQ(ierr); 1473 break; 1474 case REVOLVE_ONLINE: 1475 ierr = GetTrajRON(ts,tjsch,stepnum);CHKERRQ(ierr); 1476 break; 1477 case REVOLVE_MULTISTAGE: 1478 ierr = GetTrajRMS(ts,tjsch,stepnum);CHKERRQ(ierr); 1479 break; 1480 #endif 1481 default: 1482 break; 1483 } 1484 PetscFunctionReturn(0); 1485 } 1486 1487 #undef __FUNCT__ 1488 #define __FUNCT__ "TSTrajectorySetStride_Memory" 1489 PetscErrorCode TSTrajectorySetStride_Memory(TSTrajectory tj,TS ts,PetscInt stride) 1490 { 1491 TJScheduler *tjsch = (TJScheduler*)tj->data; 1492 1493 PetscFunctionBegin; 1494 tjsch->stride = stride; 1495 PetscFunctionReturn(0); 1496 } 1497 1498 #undef __FUNCT__ 1499 #define __FUNCT__ "TSTrajectorySetMaxCpsRAM_Memory" 1500 PetscErrorCode TSTrajectorySetMaxCpsRAM_Memory(TSTrajectory tj,TS ts,PetscInt max_cps_ram) 1501 { 1502 TJScheduler *tjsch = (TJScheduler*)tj->data; 1503 1504 PetscFunctionBegin; 1505 tjsch->max_cps_ram = max_cps_ram; 1506 PetscFunctionReturn(0); 1507 } 1508 1509 #undef __FUNCT__ 1510 #define __FUNCT__ "TSTrajectorySetMaxCpsDisk_Memory" 1511 PetscErrorCode TSTrajectorySetMaxCpsDisk_Memory(TSTrajectory tj,TS ts,PetscInt max_cps_disk) 1512 { 1513 TJScheduler *tjsch = (TJScheduler*)tj->data; 1514 1515 PetscFunctionBegin; 1516 tjsch->max_cps_disk = max_cps_disk; 1517 PetscFunctionReturn(0); 1518 } 1519 1520 #ifdef PETSC_HAVE_REVOLVE 1521 #undef __FUNCT__ 1522 #define __FUNCT__ "TSTrajectorySetRevolveOnline" 1523 PetscErrorCode TSTrajectorySetRevolveOnline(TSTrajectory tj,PetscBool use_online) 1524 { 1525 TJScheduler *tjsch = (TJScheduler*)tj->data; 1526 1527 PetscFunctionBegin; 1528 tjsch->use_online = use_online; 1529 PetscFunctionReturn(0); 1530 } 1531 #endif 1532 1533 #undef __FUNCT__ 1534 #define __FUNCT__ "TSTrajectorySetSaveStack" 1535 PetscErrorCode TSTrajectorySetSaveStack(TSTrajectory tj,PetscBool save_stack) 1536 { 1537 TJScheduler *tjsch = (TJScheduler*)tj->data; 1538 1539 PetscFunctionBegin; 1540 tjsch->save_stack = save_stack; 1541 PetscFunctionReturn(0); 1542 } 1543 1544 #undef __FUNCT__ 1545 #define __FUNCT__ "TSTrajectorySetSolutionOnly" 1546 PetscErrorCode TSTrajectorySetSolutionOnly(TSTrajectory tj,PetscBool solution_only) 1547 { 1548 TJScheduler *tjsch = (TJScheduler*)tj->data; 1549 Stack *stack = &tjsch->stack; 1550 1551 PetscFunctionBegin; 1552 stack->solution_only = solution_only; 1553 PetscFunctionReturn(0); 1554 } 1555 1556 #undef __FUNCT__ 1557 #define __FUNCT__ "TSTrajectorySetFromOptions_Memory" 1558 PetscErrorCode TSTrajectorySetFromOptions_Memory(PetscOptions *PetscOptionsObject,TSTrajectory tj) 1559 { 1560 TJScheduler *tjsch = (TJScheduler*)tj->data; 1561 PetscErrorCode ierr; 1562 1563 PetscFunctionBegin; 1564 ierr = PetscOptionsHead(PetscOptionsObject,"Memory based TS trajectory options");CHKERRQ(ierr); 1565 { 1566 ierr = PetscOptionsInt("-tstrajectory_max_cps_ram","Maximum number of checkpoints in RAM","TSTrajectorySetMaxCpsRAM_Memory",tjsch->max_cps_ram,&tjsch->max_cps_ram,NULL);CHKERRQ(ierr); 1567 ierr = PetscOptionsInt("-tstrajectory_max_cps_disk","Maximum number of checkpoints on disk","TSTrajectorySetMaxCpsDisk_Memory",tjsch->max_cps_disk,&tjsch->max_cps_disk,NULL);CHKERRQ(ierr); 1568 ierr = PetscOptionsInt("-tstrajectory_stride","Stride to save checkpoints to file","TSTrajectorySetStride_Memory",tjsch->stride,&tjsch->stride,NULL);CHKERRQ(ierr); 1569 #ifdef PETSC_HAVE_REVOLVE 1570 ierr = PetscOptionsBool("-tstrajectory_revolve_online","Trick TS trajectory into using online mode of revolve","TSTrajectorySetRevolveOnline",tjsch->use_online,&tjsch->use_online,NULL);CHKERRQ(ierr); 1571 #endif 1572 ierr = PetscOptionsBool("-tstrajectory_save_stack","Save all stack to disk","TSTrajectorySetSaveStack",tjsch->save_stack,&tjsch->save_stack,NULL);CHKERRQ(ierr); 1573 ierr = PetscOptionsBool("-tstrajectory_solution_only","Checkpoint solution only","TSTrajectorySetSolutionOnly",tjsch->stack.solution_only,&tjsch->stack.solution_only,NULL);CHKERRQ(ierr); 1574 } 1575 ierr = PetscOptionsTail();CHKERRQ(ierr); 1576 PetscFunctionReturn(0); 1577 } 1578 1579 #undef __FUNCT__ 1580 #define __FUNCT__ "TSTrajectorySetUp_Memory" 1581 PetscErrorCode TSTrajectorySetUp_Memory(TSTrajectory tj,TS ts) 1582 { 1583 TJScheduler *tjsch = (TJScheduler*)tj->data; 1584 Stack *stack = &tjsch->stack; 1585 DiskStack *diskstack = &tjsch->diskstack; 1586 #ifdef PETSC_HAVE_REVOLVE 1587 RevolveCTX *rctx,*rctx2; 1588 #endif 1589 PetscInt numY; 1590 PetscBool flg; 1591 PetscErrorCode ierr; 1592 1593 PetscFunctionBegin; 1594 PetscStrcmp(((PetscObject)ts->adapt)->type_name,TSADAPTNONE,&flg); 1595 if (flg) { /* fixed time step */ 1596 tjsch->total_steps = PetscMin(ts->max_steps,(PetscInt)(ceil(ts->max_time/ts->time_step))); 1597 } 1598 if (tjsch->max_cps_ram > 1) stack->stacksize = tjsch->max_cps_ram; 1599 if (tjsch->stride > 1) { /* two level mode works for both fixed time step and adaptive time step */ 1600 if (tjsch->max_cps_disk <= 1 && tjsch->max_cps_ram > 1 && tjsch->max_cps_ram < tjsch->stride-1) { /* use revolve_offline for each stride */ 1601 tjsch->stype = TWO_LEVEL_REVOLVE; 1602 } 1603 if (tjsch->max_cps_disk > 1 && tjsch->max_cps_ram > 1 && tjsch->max_cps_ram <= tjsch->stride-1) { /* use revolve_offline for each stride */ 1604 tjsch->stype = TWO_LEVEL_TWO_REVOLVE; 1605 diskstack->stacksize = tjsch->max_cps_disk; 1606 } 1607 if (tjsch->max_cps_disk <= 1 && (tjsch->max_cps_ram >= tjsch->stride || tjsch->max_cps_ram == -1)) { /* checkpoint all for each stride */ 1608 tjsch->stype = TWO_LEVEL_NOREVOLVE; /* can also be handled by TWO_LEVEL_REVOLVE */ 1609 stack->stacksize = tjsch->stride-1; /* need tjsch->stride-1 at most */ 1610 } 1611 } else { 1612 if (flg) { /* fixed time step */ 1613 if (tjsch->max_cps_ram >= tjsch->total_steps-1 || tjsch->max_cps_ram < 1) { /* checkpoint all */ 1614 tjsch->stype = NONE; 1615 stack->stacksize = stack->solution_only ? tjsch->total_steps : tjsch->total_steps-1; 1616 } else { 1617 if (tjsch->max_cps_disk > 1) { /* disk can be used */ 1618 tjsch->stype = REVOLVE_MULTISTAGE; 1619 } else { /* memory only */ 1620 tjsch->stype = REVOLVE_OFFLINE; 1621 } 1622 } 1623 } else { /* adaptive time step */ 1624 tjsch->stype = REVOLVE_ONLINE; 1625 } 1626 #ifdef PETSC_HAVE_REVOLVE 1627 if (tjsch->use_online) { /* trick into online */ 1628 tjsch->stype = REVOLVE_ONLINE; 1629 stack->stacksize = tjsch->max_cps_ram; 1630 } 1631 #endif 1632 } 1633 1634 if (tjsch->stype > TWO_LEVEL_NOREVOLVE) { 1635 #ifndef PETSC_HAVE_REVOLVE 1636 SETERRQ(tjsch->comm,PETSC_ERR_SUP,"revolve is needed when there is not enough memory to checkpoint all time steps according to the user's settings, please reconfigure with the additional option --download-revolve."); 1637 #else 1638 if (tjsch->stype == TWO_LEVEL_REVOLVE) revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1639 else if (tjsch->stype == TWO_LEVEL_TWO_REVOLVE) { 1640 revolve_create_offline(tjsch->stride,tjsch->max_cps_ram); 1641 revolve2_create_offline((tjsch->total_steps+tjsch->stride-1)/tjsch->stride,tjsch->max_cps_disk); 1642 ierr = PetscCalloc1(1,&rctx2);CHKERRQ(ierr); 1643 rctx2->snaps_in = tjsch->max_cps_disk; 1644 rctx2->reverseonestep = PETSC_FALSE; 1645 rctx2->check = 0; 1646 rctx2->oldcapo = 0; 1647 rctx2->capo = 0; 1648 rctx2->info = 2; 1649 rctx2->fine = (tjsch->total_steps+tjsch->stride-1)/tjsch->stride; 1650 tjsch->rctx2 = rctx2; 1651 diskstack->top = -1; 1652 ierr = PetscMalloc1(diskstack->stacksize*sizeof(PetscInt),&diskstack->container);CHKERRQ(ierr); 1653 } else if (tjsch->stype == REVOLVE_OFFLINE) revolve_create_offline(tjsch->total_steps,tjsch->max_cps_ram); 1654 else if (tjsch->stype == REVOLVE_ONLINE) revolve_create_online(tjsch->max_cps_ram); 1655 else if (tjsch->stype == REVOLVE_MULTISTAGE) revolve_create_multistage(tjsch->total_steps,tjsch->max_cps_ram+tjsch->max_cps_disk,tjsch->max_cps_ram); 1656 1657 ierr = PetscCalloc1(1,&rctx);CHKERRQ(ierr); 1658 rctx->snaps_in = tjsch->max_cps_ram; /* for theta methods snaps_in=2*max_cps_ram */ 1659 rctx->reverseonestep = PETSC_FALSE; 1660 rctx->check = 0; 1661 rctx->oldcapo = 0; 1662 rctx->capo = 0; 1663 rctx->info = 2; 1664 rctx->fine = (tjsch->stride > 1) ? tjsch->stride : tjsch->total_steps; 1665 tjsch->rctx = rctx; 1666 if (tjsch->stype == REVOLVE_ONLINE) rctx->fine = -1; 1667 #endif 1668 } 1669 1670 tjsch->recompute = PETSC_FALSE; 1671 tjsch->comm = PetscObjectComm((PetscObject)ts); 1672 ierr = TSGetStages(ts,&numY,PETSC_IGNORE);CHKERRQ(ierr); 1673 ierr = StackCreate(stack,stack->stacksize,numY);CHKERRQ(ierr); 1674 PetscFunctionReturn(0); 1675 } 1676 1677 #undef __FUNCT__ 1678 #define __FUNCT__ "TSTrajectoryDestroy_Memory" 1679 PETSC_EXTERN PetscErrorCode TSTrajectoryDestroy_Memory(TSTrajectory tj) 1680 { 1681 TJScheduler *tjsch = (TJScheduler*)tj->data; 1682 PetscErrorCode ierr; 1683 1684 PetscFunctionBegin; 1685 if (tjsch->stype > TWO_LEVEL_NOREVOLVE) { 1686 #ifdef PETSC_HAVE_REVOLVE 1687 revolve_reset(); 1688 if (tjsch->stype == TWO_LEVEL_TWO_REVOLVE) { 1689 revolve2_reset(); 1690 ierr = PetscFree(tjsch->diskstack.container);CHKERRQ(ierr); 1691 } 1692 #endif 1693 } 1694 ierr = StackDestroy(&tjsch->stack);CHKERRQ(ierr); 1695 #ifdef PETSC_HAVE_REVOLVE 1696 if (tjsch->stype > TWO_LEVEL_NOREVOLVE) { 1697 ierr = PetscFree(tjsch->rctx);CHKERRQ(ierr); 1698 ierr = PetscFree(tjsch->rctx2);CHKERRQ(ierr); 1699 } 1700 #endif 1701 ierr = PetscFree(tjsch);CHKERRQ(ierr); 1702 PetscFunctionReturn(0); 1703 } 1704 1705 /*MC 1706 TSTRAJECTORYMEMORY - Stores each solution of the ODE/ADE in memory 1707 1708 Level: intermediate 1709 1710 .seealso: TSTrajectoryCreate(), TS, TSTrajectorySetType() 1711 1712 M*/ 1713 #undef __FUNCT__ 1714 #define __FUNCT__ "TSTrajectoryCreate_Memory" 1715 PETSC_EXTERN PetscErrorCode TSTrajectoryCreate_Memory(TSTrajectory tj,TS ts) 1716 { 1717 TJScheduler *tjsch; 1718 PetscErrorCode ierr; 1719 1720 PetscFunctionBegin; 1721 tj->ops->set = TSTrajectorySet_Memory; 1722 tj->ops->get = TSTrajectoryGet_Memory; 1723 tj->ops->setup = TSTrajectorySetUp_Memory; 1724 tj->ops->destroy = TSTrajectoryDestroy_Memory; 1725 tj->ops->setfromoptions = TSTrajectorySetFromOptions_Memory; 1726 1727 ierr = PetscCalloc1(1,&tjsch);CHKERRQ(ierr); 1728 tjsch->stype = NONE; 1729 tjsch->max_cps_ram = -1; /* -1 indicates that it is not set */ 1730 tjsch->max_cps_disk = -1; /* -1 indicates that it is not set */ 1731 tjsch->stride = 0; /* if not zero, two-level checkpointing will be used */ 1732 #ifdef PETSC_HAVE_REVOLVE 1733 tjsch->use_online = PETSC_FALSE; 1734 #endif 1735 tjsch->save_stack = PETSC_TRUE; 1736 1737 tjsch->stack.solution_only = PETSC_TRUE; 1738 1739 tj->data = tjsch; 1740 1741 PetscFunctionReturn(0); 1742 } 1743