Actual source code: tao_app.c
1: #include "tao_app_impl.h" /*I "tao.h" I*/
3: int Tao_ObjectiveEval=0, Tao_GradientEval=0, Tao_HessianEval=0,Tao_JacobianEval=0,Tao_FunctionEval=0;
4: int TAO_APP_COOKIE=0;
10: /*@C
11: TaoApplicationCreate - Creates a TaoApplication that
12: uses PETSc data structures. The vectors used for gradient
13: and other information can be a PETSc Vec. The routines
14: for function evaluation, and derivative information can
15: also used PETSc arguments.
17: Input Parameters:
18: . comm - an MPI communiicator
20: Output Parameters:
21: . newapp - the TaoApplication structure
23: .seealso TaoAppSetObjectiveAndGradientRoutine(), TaoSolveApplication(), TaoAppDestroy()
25: Level: beginner
27: .keywords: Application
28: @*/
29: int TaoApplicationCreate(MPI_Comm comm, TAO_APPLICATION* newapp){
30: int info;
31: TAO_APPLICATION taoapp;
35: if (TAO_APP_COOKIE==0){
36: info=PetscLogClassRegister(&TAO_APP_COOKIE,"TAO Application"); CHKERRQ(info);
37: }
39: // PetscHeaderCreate(taoapp,_p_PETSC_APPLICATION,int,TAO_APP_COOKIE,-1,"TAO DA APP",comm,TaoAppDestroy,0);
40: info = PetscHeaderCreate(taoapp,_p_TAOAPPLICATION,int,TAO_APP_COOKIE,-1,"TAO APP",comm,0,0); CHKERRQ(info);
41: info = PetscLogObjectCreate(taoapp); CHKERRQ(info);
42: info = PetscLogObjectMemory(taoapp, sizeof(struct _p_TAOAPPLICATION)); CHKERRQ(info);
43: // taoapp->taoappl = new TaoPetscApplication(comm);
46: /* This part works */
47: taoapp->computeumfunction=0; taoapp->computegradient=0;
48: taoapp->computefunctiongradient=0; taoapp->computehessian=0;
49: taoapp->computejacobian=0; taoapp->computevfunc=0;
50: taoapp->computebounds=0; taoapp->boundctx=0;
51: taoapp->grtol=0;
52: taoapp->usrfctx=0; taoapp->usrfgctx=0; taoapp->usrgctx=0; taoapp->usrhctx=0;
53: taoapp->V=0;
54: taoapp->G=0; taoapp->H=0; taoapp->HP=0;
55: taoapp->R=0; taoapp->J=0; taoapp->JP=0;
57: taoapp->numbermonitors = 0;
58: taoapp->numberdestroyers = 0;
59: taoapp->nAddOn = 0;
61: taoapp->numberoptioncheckers=0;
63: if (Tao_ObjectiveEval==0){
64: info = PetscLogEventRegister(&Tao_ObjectiveEval,"TaoAppObjective",TAO_APP_COOKIE); CHKERRQ(info);
65: info = PetscLogEventRegister(&Tao_GradientEval,"TaoAppGradient",TAO_APP_COOKIE); CHKERRQ(info);
66: info = PetscLogEventRegister(&Tao_HessianEval,"TaoAppHessian",TAO_APP_COOKIE); CHKERRQ(info);
67: info = PetscLogEventRegister(&Tao_JacobianEval,"TaoAppJacobian",TAO_APP_COOKIE); CHKERRQ(info);
68: info = PetscLogEventRegister(&Tao_FunctionEval,"TaoAppFunction",TAO_APP_COOKIE); CHKERRQ(info);
69: }
70: info = TaoAppAddFiniteDifferences(taoapp); CHKERRQ(info);
71: info = KSPCreate(comm,&taoapp->ksp); CHKERRQ(info);
72: info = KSPSetFromOptions(taoapp->ksp); CHKERRQ(info);
73: *newapp=taoapp;
74: return(0);
75: }
79: /*@
80: TaoAppDestroy - Destroy the PETSc application
81: and all of the vectors and matrices associated with it.
83: Input Parameters:
84: . taoapp - the TaoApplication structure
86: .seealso TaoApplicationCreate(), TaoDestroy()
88: Level: beginner
90: .keywords: Application, Destroy
91: @*/
92: int TaoAppDestroy(TAO_APPLICATION taoapp){
93: int i,info;
97: if (taoapp->V){ info = VecDestroy(taoapp->V); CHKERRQ(info); }
98: if (taoapp->G){ info = VecDestroy(taoapp->G); CHKERRQ(info); }
99: if (taoapp->H){ info = MatDestroy(taoapp->H); CHKERRQ(info); }
100: if (taoapp->HP){ info = MatDestroy(taoapp->HP); CHKERRQ(info); }
101: if (taoapp->R){ info = VecDestroy(taoapp->R); CHKERRQ(info); }
102: if (taoapp->J){ info = MatDestroy(taoapp->J); CHKERRQ(info); }
103: if (taoapp->JP){ info = MatDestroy(taoapp->JP); CHKERRQ(info); }
104:
105: if (taoapp->ksp) {
106: info = KSPDestroy(taoapp->ksp); CHKERRQ(info);
107: taoapp->ksp=0;
108: }
109: for (i=0; i< taoapp->numberdestroyers; i++){
110: info = (*taoapp->userdestroy[i])(taoapp->userctxdestroy[i]); CHKERRQ(info);
111: }
112:
113: // delete taoapp->taoappl;
114: PetscLogObjectDestroy(taoapp);
115: PetscHeaderDestroy(taoapp);
116: return(0);
117: }
122: /*@
123: TaoAppSetInitialSolutionVec - Sets the vector representing the variables
124: and an initial guess.
126: Collective on TAO_APPLICATION
128: Input Parameters:
129: + taoapp - the TAO_APPLICATION context
130: - xx - variable vector that stores the solution
132: Level: beginner
134: Note:
135: This vector will be used by the solver, so do not use it
136: for other purposes. The user should destroy this vector after
137: solving the application.
139: Note:
140: If the user is unaware of a decent initial solution,
141: the vector should be set to zero.
143: Note:
144: The TAO solvers will not use the contents of this
145: Vec until the TaoSolve() is called. Therefore the user
146: may compute an initial solution in this vector after this
147: routine -- but before TaoSolve().
149: .seealso: TaoAppGetSolutionVec(), TaoAppSetObjectiveRoutine()
150: @*/
151: int TaoAppSetInitialSolutionVec(TAO_APPLICATION taoapp, Vec xx){
152: int info;
155: if (xx){
157: PetscObjectReference((PetscObject)xx);
158: }
159: if (taoapp->V){
160: info=VecDestroy(taoapp->V);CHKERRQ(info);
161: }
162: taoapp->V=xx;
163: return(0);
164: }
168: /*@
169: TaoAppSetDefaultSolutionVec - Sets the vector representing the variables
170: and an initial guess.
172: Collective on TAO_APPLICATION
174: Input Parameters:
175: + taoapp - the TAO_APPLICATION context
176: - xx - variable vector that stores the solution
178: Level: beginner
180: Note:
181: This vector will be used by the solver, so do not use it
182: for other purposes. The user should destroy this vector after
183: solving the application.
185: .seealso: TaoAppGetSolutionVec(), TaoAppSetObjectiveRoutine(), TaoAppSetInitialSolutionVec()
186: @*/
187: int TaoAppSetDefaultSolutionVec(TAO_APPLICATION taoapp, Vec xx){
188: int info;
189: PetscScalar zero=0.0;
192: if (xx){
194: PetscObjectReference((PetscObject)xx);
195: }
196: if (taoapp->V){
197: info=VecDestroy(taoapp->V);CHKERRQ(info);
198: }
199: taoapp->V=xx;
200: info = VecSet(xx, zero); CHKERRQ(info);
201: return(0);
202: }
206: /*@
207: TaoAppGetSolutionVec - Get the vector with the
208: solution in the current application.
210: Input Parameters:
211: . taoapp - the application
213: Output Parameter:
214: . X - the solution vector
216: Note:
217: This vector should not be destroyed.
219: Level: intermediate
222: .keywords: Application, variables
223: @*/
224: int TaoAppGetSolutionVec(TAO_APPLICATION taoapp, Vec *X){
227: if (X){
228: *X=taoapp->V;
229: }
230: return(0);
231: }
234: /* ------------ Routines to set performance monitoring options ----------- */
238: /*@C
239: TaoAppSetMonitor - Sets an ADDITIONAL function that is to be used at every
240: iteration of the solver to display the iteration's
241: progress.
243: Collective on TAO_APPLICATION
245: Input Parameters:
246: + taoapp - the TAO_APPLICATION solver context
247: . mymonitor - monitoring routine
248: - mctx - [optional] user-defined context for private data for the
249: monitor routine (may be TAO_NULL)
251: Calling sequence of mymonitor:
252: $ int mymonitor(TAO_APPLICATION taoapp,void *mctx)
254: + taoapp - the TAO_APPLICATION solver context
255: - mctx - [optional] monitoring context
258: Note:
259: Several different monitoring routines may be set by calling
260: TaoAppSetMonitor() multiple times; all will be called in the
261: order in which they were set.
263: Level: intermediate
265: .keywords: options, monitor, View
267: .seealso: TaoSetMonitor(), TaoAppSetDestroyRoutine()
268: @*/
269: int TaoAppSetMonitor(TAO_APPLICATION taoapp,int (*mymonitor)(TAO_APPLICATION,void*),void *mctx)
270: {
273: if (mymonitor){
274: if (taoapp->numbermonitors >= MAX_TAO_MONITORS) {
275: SETERRQ(1,"Too many monitors set");
276: }
277: taoapp->monitor[taoapp->numbermonitors] = mymonitor;
278: taoapp->monitorcontext[taoapp->numbermonitors++] = (void*)mctx;
279: }
280: return(0);
281: }
285: /*@
286: TaoAppMonitor - Apply the monitor functions for a TAO_APPLICATION object.
288: Collective on TAO_APPLICATION
290: Input Parameters:
291: . taoapp - the TAO_APPLICATION structure
293: Level: developer
295: .keywords: options, monitor, View
297: .seealso: TaoAppSetMonitor()
298: @*/
299: int TaoAppMonitor(TAO_APPLICATION taoapp){
300: int i,info;
303: for ( i=0; i<taoapp->numbermonitors; i++ ) {
304: info = (*taoapp->monitor[i])(taoapp,taoapp->monitorcontext[i]);CHKERRQ(info);
305: }
306: return(0);
307: }
310: /* ------------ Routines to called when destroying this application ----------- */
313: /*@C
314: TaoAppSetDestroyRoutine - Sets an ADDITIONAL function that will be called when
315: this application is destroyed.
317: Collective on TAO_APPLICATION
319: Input Parameters:
320: + taoapp - the TAO_APPLICATION solver context
321: . destroy - function pointer
322: - ctx - [optional] user-defined context for private data for the
323: destroy routine (may be TAO_NULL)
325: Calling sequence of destroy:
326: $ int mydestroy(void *ctx)
328: . ctx - [optional] destroy context
331: Level: intermediate
333: Note:
334: This routine is often used to destroy structures used by monitors and
335: function evaluations. This routine may also be used to shut down other packages
336: such as ADIC.
338: .keywords: destroy
340: .seealso: TaoAppSetMonitor(), TaoAppSetHessianRoutine(), TaoAppDestroy()
341: @*/
342: int TaoAppSetDestroyRoutine(TAO_APPLICATION taoapp,int (*destroy)(void*),void *ctx)
343: {
346: if (destroy){
347: if (taoapp->numberdestroyers >= MAX_TAO_USER_DESTROY) {
348: SETERRQ(1,"TAO ERRROR: Too many TAO APPLICATION destroy routines set");
349: }
350:
351: taoapp->userdestroy[taoapp->numberdestroyers] = destroy;
352: taoapp->userctxdestroy[taoapp->numberdestroyers++] = ctx;
353: }
354: return(0);
355: }
357: /* ------------ Routines to extend TaoApp ----------- */
361: /*@
362: TaoAppAddObject - add an object from to the Tao Application.
364: Collective on TAO_APPLICATION
366: Input Parameters:
367: + taoapp - the TAO_APPLICATION solver context
368: . key - string used to ID this object
369: - ctx - user-defined context for private data
371: Output Paramter:
372: . id - ignored
373:
375: Note:
376: This routine can be used to extend the functionality of this object
378: Level: advanced
380: .keywords: extensions
382: .seealso: TaoAppQueryForObject()
383: @*/
384: int TaoAppAddObject(TAO_APPLICATION taoapp, char *key, void *ctx, int *id)
385: {
386: int info;
389: if (ctx){
390: if (taoapp->nAddOn >= MAX_TAOAPP_ADDON) {
391: SETERRQ(1,"Too many TaoObject added on");
392: }
393: taoapp->TaoAppCtx[taoapp->nAddOn].ctx = ctx;
394: info=PetscStrncpy(taoapp->TaoAppCtx[taoapp->nAddOn].key , key, MAX_TAO_KEY_LENGTH); CHKERRQ(info);
395: taoapp->TaoAppCtx[taoapp->nAddOn].id = taoapp->nAddOn;
396: *id=taoapp->TaoAppCtx[taoapp->nAddOn].id;
397: taoapp->nAddOn++;
398: }
399: return(0);
400: }
405: /*@
406: TaoAppQueryForObject - query the TAO Application for an object
408: Collective on TAO_APPLICATION
410: Input Parameters:
411: + taoapp - the TAO_APPLICATION solver context
412: . key - string used to ID this object
413: - ctx - user-defined context for private data
415: Output Parameter:
416:
418: Note:
419: This routine can be used to extend the functionality of this object
421: Level: advanced
423: .keywords: extensions
425: .seealso: TaoAppAddObject()
426: @*/
427: int TaoAppQueryForObject(TAO_APPLICATION taoapp, char *key, void **ctx)
428: {
429: int i,n,info;
430: PetscTruth flag=PETSC_FALSE;
434: n=taoapp->nAddOn;
435: *ctx=0;
436: for (i=0;i<n;i++){
437: info=PetscStrncmp(taoapp->TaoAppCtx[i].key,key,MAX_TAOAPP_ADDON,&flag); CHKERRQ(info);
438: if (flag==PETSC_TRUE){
439: *ctx=taoapp->TaoAppCtx[i].ctx;
440: break;
441: }
442: }
443: return(0);
444: }
449: /*@
450: TaoAppQueryRemoveObject - add an object from to the Tao Application.
452: Collective on TAO_APPLICATION
454: Input Parameters:
455: + taoapp - the TAO_APPLICATION solver context
456: - key - string used to ID this object
458: Note:
459: This routine can be used to extend the functionality of this object
461: Level: advanced
463: .keywords: extensions
465: .seealso: TaoAppQueryForObject()
466: @*/
467: int TaoAppQueryRemoveObject(TAO_APPLICATION taoapp, char *key)
468: {
469: int i,n,info;
470: PetscTruth flag;
473: n=taoapp->nAddOn;
474: for (i=0;i<n;i++){
475: info=PetscStrncmp(taoapp->TaoAppCtx[i].key,key,MAX_TAO_KEY_LENGTH,&flag); CHKERRQ(info);
476: if (flag==PETSC_TRUE){
477: if (n>0){
478: taoapp->TaoAppCtx[i].ctx=taoapp->TaoAppCtx[n-1].ctx;
479: taoapp->TaoAppCtx[i].id=taoapp->TaoAppCtx[n-1].id;
480: info=PetscStrncpy(taoapp->TaoAppCtx[i].key,taoapp->TaoAppCtx[n-1].key,MAX_TAO_KEY_LENGTH);
481: CHKERRQ(info);
482: }
483: taoapp->nAddOn--;
484: break;
485: }
486: }
487: return(0);
488: }
492: /*@C
493: TaoAppSetOptionsRoutine - Sets an ADDITIONAL function that is to be called
494: during TaoSetFromOptions().
496: Collective on TAO_APPLICATION
498: Input Parameters:
499: + tao - the TAO_APPLICATION solver context
500: - options - routine the checks options
502: Calling sequence of options:
503: $ int myoptions(TAO_APPLICATION taoapp)
505: . taoapp - the TAO_APPLICATION solver context
508: Note:
509: Several different options routines may be set by calling
510: this routine.
512: Level: advanced
514: .keywords: options, monitor, View
516: .seealso: TaoAppSetFromOptions()
517: @*/
518: int TaoAppSetOptionsRoutine(TAO_APPLICATION taoapp,int (*options)(TAO_APPLICATION) )
519: {
522: if (options){
523: if (taoapp->numberoptioncheckers >= MAX_TAO_MONITORS) {
524: SETERRQ(1,"Too many options checkers set");
525: }
526: taoapp->checkoptions[taoapp->numberoptioncheckers++] = options;
527: }
528: return(0);
529: }
533: /*@
534: TaoAppSetFromOptions - Sets various TAO parameters from user options
536: Collective on TAO_APPLICATION
538: Input Parameters:
539: . taoapp - the TAO Application
541: Level: beginner
543: .keywords: options
545: .seealso: TaoSetFromOptions()
547: @*/
548: int TaoAppSetFromOptions(TAO_APPLICATION taoapp){
549: int i,info;
550: const char *prefix=0;
551: MPI_Comm comm;
552: PetscTruth flg1;
556: info = PetscObjectGetOptionsPrefix((PetscObject)taoapp,&prefix); CHKERRQ(info);
557: info = PetscObjectGetComm((PetscObject)taoapp,&comm);CHKERRQ(info);
558: info = PetscOptionsBegin(comm,prefix,"TAO PETSC APPLICATIONS ","solver");CHKERRQ(info);
559: info = PetscOptionsReal("-taoapp_grtol","the relative tolerance","TaoAppSetRelativeTolerance",
560: taoapp->grtol,&taoapp->grtol,&flg1);CHKERRQ(info);
561: for (i=0;i<taoapp->numberoptioncheckers;i++){
562: info = (*taoapp->checkoptions[i])(taoapp);CHKERRQ(info);
563: }
564: info = KSPSetFromOptions(taoapp->ksp);CHKERRQ(info);
565: info = PetscOptionsEnd(); CHKERRQ(info);
566: return(0);
567: }
571: int TaoAppGetKSP(TAO_APPLICATION taoapp, KSP *ksp){
572: /*@C
573: TaoAppGetKSP - Gets the linear solver used by the optimization application
575: Collective on TAO_APPLICATION
577: Input Parameters:
578: . taoapp - the TAO Application
580: Level: intermediate
582: .keywords: options
584: .seealso: TaoSetFromOptions()
586: @*/
589: if (ksp){
590: *ksp=taoapp->ksp;
591: }
592: return(0);
593: }