Actual source code: plog.c
1: /*$Id: plog.c,v 1.262 2001/08/22 17:59:37 balay Exp $*/
2: /*
3: PETSc code to log object creation and destruction and PETSc events.
4: */
5: #include petsc.h
6: #include "petscmachineinfo.h"
7: #if defined(PETSC_HAVE_MPE)
8: #include "mpe.h"
9: #endif
10: #include <stdarg.h>
11: #include <sys/types.h>
12: #include petscsys.h
13: #if defined(PETSC_HAVE_STDLIB_H)
14: #include <stdlib.h>
15: #endif
16: #if defined(PETSC_HAVE_MALLOC_H) && !defined(__cplusplus)
17: #include <malloc.h>
18: #endif
19: #include "petscfix.h"
20: #include src/sys/src/plog/ptime.h
21: #include plog.h
23: int PETSC_LARGEST_COOKIE = PETSC_COOKIE;
24: int PETSC_LARGEST_EVENT = PETSC_EVENT;
26: #if defined(PETSC_USE_LOG)
28: /* used in the MPI_XXX() count macros in petsclog.h */
29: int PETSC_DUMMY,PETSC_DUMMY_SIZE;
31: /* Action and object logging variables */
32: Action *actions = PETSC_NULL;
33: Object *objects = PETSC_NULL;
34: PetscTruth logActions = PETSC_FALSE;
35: PetscTruth logObjects = PETSC_FALSE;
36: int numActions = 0, maxActions = 100;
37: int numObjects = 0, maxObjects = 100;
38: int numObjectsDestroyed = 0;
40: /* Global counters */
41: PetscLogDouble BaseTime;
42: PetscLogDouble _TotalFlops = 0.0; /* The number of flops */
43: PetscLogDouble send_ct = 0.0; /* The number of sends */
44: PetscLogDouble recv_ct = 0.0; /* The number of receives */
45: PetscLogDouble send_len = 0.0; /* The total length of all sent messages */
46: PetscLogDouble recv_len = 0.0; /* The total length of all received messages */
47: PetscLogDouble isend_ct = 0.0; /* The number of immediate sends */
48: PetscLogDouble irecv_ct = 0.0; /* The number of immediate receives */
49: PetscLogDouble isend_len = 0.0; /* The total length of all immediate send messages */
50: PetscLogDouble irecv_len = 0.0; /* The total length of all immediate receive messages */
51: PetscLogDouble wait_ct = 0.0; /* The number of waits */
52: PetscLogDouble wait_any_ct = 0.0; /* The number of anywaits */
53: PetscLogDouble wait_all_ct = 0.0; /* The number of waitalls */
54: PetscLogDouble sum_of_waits_ct = 0.0; /* The total number of waits */
55: PetscLogDouble allreduce_ct = 0.0; /* The number of reductions */
57: /* Logging functions */
58: int (*_PetscLogPHC)(PetscObject) = PETSC_NULL;
59: int (*_PetscLogPHD)(PetscObject) = PETSC_NULL;
60: int (*_PetscLogPLB)(int, int, PetscObject, PetscObject, PetscObject, PetscObject) = PETSC_NULL;
61: int (*_PetscLogPLE)(int, int, PetscObject, PetscObject, PetscObject, PetscObject) = PETSC_NULL;
63: /* Tracing event logging variables */
64: FILE *tracefile = PETSC_NULL;
65: int tracelevel = 0;
66: char *traceblanks = " ";
67: char tracespace[128];
68: PetscLogDouble tracetime = 0.0;
70: /*---------------------------------------------- General Functions --------------------------------------------------*/
71: #undef __FUNCT__
73: /*@C
74: PetscLogDestroy - Destroys the object and event logging data and resets the global counters.
76: Not Collective
78: Notes:
79: This routine should not usually be used by programmers. Instead employ
80: PetscLogStagePush() and PetscLogStagePop().
82: Level: developer
84: .keywords: log, destroy
85: .seealso: PetscLogDump(), PetscLogAllBegin(), PetscLogPrintSummary(), PetscLogStagePush(), PlogStagePop()
86: @*/
87: int PetscLogDestroy(void) {
88: StageLog stageLog;
89: int ierr;
92: if (actions != PETSC_NULL) {
93: PetscFree(actions);
94: actions = PETSC_NULL;
95: }
96: if (objects != PETSC_NULL) {
97: PetscFree(objects);
98: objects = PETSC_NULL;
99: }
100: PetscLogSet(PETSC_NULL, PETSC_NULL);
102: /* Resetting phase */
103: PetscLogGetStageLog(&stageLog);
104: StageLogDestroy(stageLog);
105: _TotalFlops = 0.0;
106: numActions = 0;
107: numObjects = 0;
108: numObjectsDestroyed = 0;
109: return(0);
110: }
112: #undef __FUNCT__
114: /*@C
115: PetscLogSet - Sets the logging functions called at the beginning and ending of every event.
117: Not Collective
119: Input Parameters:
120: + b - The function called at beginning of event
121: - e - The function called at end of event
123: Level: developer
125: .seealso: PetscLogDump(), PetscLogBegin(), PetscLogAllBegin(), PetscLogTraceBegin()
126: @*/
127: int PetscLogSet(int (*b)(int, int, PetscObject, PetscObject, PetscObject, PetscObject),
128: int (*e)(int, int, PetscObject, PetscObject, PetscObject, PetscObject))
129: {
131: _PetscLogPLB = b;
132: _PetscLogPLE = e;
133: return(0);
134: }
136: /*------------------------------------------- Initialization Functions ----------------------------------------------*/
137: #undef __FUNCT__
139: int PetscLogBegin_Private(void) {
140: static int initialized = 0;
141: int stage;
142: PetscTruth opt;
143: int ierr;
146: if (initialized) return(0);
147: initialized = 1;
148: PetscOptionsHasName(PETSC_NULL, "-log_exclude_actions", &opt);
149: if (opt == PETSC_TRUE) {
150: logActions = PETSC_FALSE;
151: }
152: PetscOptionsHasName(PETSC_NULL, "-log_exclude_objects", &opt);
153: if (opt == PETSC_TRUE) {
154: logObjects = PETSC_FALSE;
155: }
156: if (logActions == PETSC_TRUE) {
157: PetscMalloc(maxActions * sizeof(Action), &actions);
158: }
159: if (logObjects == PETSC_TRUE) {
160: PetscMalloc(maxObjects * sizeof(Object), &objects);
161: }
162: _PetscLogPHC = PetscLogObjCreateDefault;
163: _PetscLogPHD = PetscLogObjDestroyDefault;
164: /* Setup default logging structures */
165: StageLogCreate(&_stageLog);
166: StageLogRegister(_stageLog, "Main Stage", &stage);
167: /* All processors sync here for more consistent logging */
168: MPI_Barrier(PETSC_COMM_WORLD);
169: PetscTime(BaseTime);
170: PetscLogStagePush(stage);
171: return(0);
172: }
174: #undef __FUNCT__
176: /*@C
177: PetscLogBegin - Turns on logging of objects and events. This logs flop
178: rates and object creation and should not slow programs down too much.
179: This routine may be called more than once.
181: Collective over PETSC_COMM_WORLD
183: Options Database Keys:
184: + -log_summary - Prints summary of flop and timing information to the
185: screen (for code compiled with PETSC_USE_LOG)
186: - -log - Prints detailed log information (for code compiled with PETSC_USE_LOG)
188: Usage:
189: .vb
190: PetscInitialize(...);
191: PetscLogBegin();
192: ... code ...
193: PetscLogPrintSummary(MPI_Comm,filename); or PetscLogDump();
194: PetscFinalize();
195: .ve
197: Notes:
198: PetscLogPrintSummary(MPI_Comm,filename) or PetscLogDump() actually cause the printing of
199: the logging information.
201: Level: advanced
203: .keywords: log, begin
204: .seealso: PetscLogDump(), PetscLogAllBegin(), PetscLogPrintSummary(), PetscLogTraceBegin()
205: @*/
206: int PetscLogBegin(void)
207: {
211: PetscLogSet(PetscLogEventBeginDefault, PetscLogEventEndDefault);
212: PetscLogBegin_Private();
213: return(0);
214: }
216: #undef __FUNCT__
218: /*@C
219: PetscLogAllBegin - Turns on extensive logging of objects and events. Logs
220: all events. This creates large log files and slows the program down.
222: Collective on PETSC_COMM_WORLD
224: Options Database Keys:
225: . -log_all - Prints extensive log information (for code compiled with PETSC_USE_LOG)
227: Usage:
228: .vb
229: PetscInitialize(...);
230: PetscLogAllBegin();
231: ... code ...
232: PetscLogDump(filename);
233: PetscFinalize();
234: .ve
236: Notes:
237: A related routine is PetscLogBegin (with the options key -log), which is
238: intended for production runs since it logs only flop rates and object
239: creation (and shouldn't significantly slow the programs).
241: Level: advanced
243: .keywords: log, all, begin
244: .seealso: PetscLogDump(), PetscLogBegin(), PetscLogTraceBegin()
245: @*/
246: int PetscLogAllBegin(void)
247: {
251: PetscLogSet(PetscLogEventBeginComplete, PetscLogEventEndComplete);
252: PetscLogBegin_Private();
253: return(0);
254: }
256: #undef __FUNCT__
258: /*@
259: PetscLogTraceBegin - Activates trace logging. Every time a PETSc event
260: begins or ends, the event name is printed.
262: Collective on PETSC_COMM_WORLD
264: Input Parameter:
265: . file - The file to print trace in (e.g. stdout)
267: Options Database Key:
268: . -log_trace [filename] - Activates PetscLogTraceBegin()
270: Notes:
271: PetscLogTraceBegin() prints the processor number, the execution time (sec),
272: then "Event begin:" or "Event end:" followed by the event name.
274: PetscLogTraceBegin() allows tracing of all PETSc calls, which is useful
275: to determine where a program is hanging without running in the
276: debugger. Can be used in conjunction with the -log_info option.
278: Level: intermediate
280: .seealso: PetscLogDump(), PetscLogAllBegin(), PetscLogPrintSummary(), PetscLogBegin()
281: @*/
282: int PetscLogTraceBegin(FILE *file)
283: {
287: tracefile = file;
288: PetscLogSet(PetscLogEventBeginTrace, PetscLogEventEndTrace);
289: PetscLogBegin_Private();
290: return(0);
291: }
293: #undef __FUNCT__
295: /*@
296: PetscLogActions - Determines whether actions are logged for the graphical viewer.
298: Not Collective
300: Input Parameter:
301: . flag - PETSC_TRUE if actions are to be logged
303: Level: intermediate
305: Note: Logging of actions continues to consume more memory as the program
306: runs. Long running programs should consider turning this feature off.
308: Options Database Keys:
309: . -log_exclude_actions - Turns off actions logging
311: .keywords: log, stage, register
312: .seealso: PetscLogStagePush(), PetscLogStagePop()
313: @*/
314: int PetscLogActions(PetscTruth flag) {
316: logActions = flag;
317: return(0);
318: }
320: #undef __FUNCT__
322: /*@
323: PetscLogObjects - Determines whether objects are logged for the graphical viewer.
325: Not Collective
327: Input Parameter:
328: . flag - PETSC_TRUE if objects are to be logged
330: Level: intermediate
332: Note: Logging of objects continues to consume more memory as the program
333: runs. Long running programs should consider turning this feature off.
335: Options Database Keys:
336: . -log_exclude_objects - Turns off objects logging
338: .keywords: log, stage, register
339: .seealso: PetscLogStagePush(), PetscLogStagePop()
340: @*/
341: int PetscLogObjects(PetscTruth flag) {
343: logObjects = flag;
344: return(0);
345: }
347: /*------------------------------------------------ Stage Functions --------------------------------------------------*/
348: #undef __FUNCT__
350: /*@C
351: PetscLogStageRegister - Attaches a charactor string name to a logging stage.
353: Not Collective
355: Input Parameter:
356: . sname - The name to associate with that stage
358: Output Parameter:
359: . stage - The stage number
361: Level: intermediate
363: .keywords: log, stage, register
364: .seealso: PetscLogStagePush(), PetscLogStagePop()
365: @*/
366: int PetscLogStageRegister(int *stage, const char sname[]) {
367: StageLog stageLog;
368: int event;
369: int ierr;
372: PetscLogGetStageLog(&stageLog);
373: StageLogRegister(stageLog, sname, stage);
374: /* Copy events already changed in the main stage, this sucks */
375: EventPerfLogEnsureSize(stageLog->stageInfo[*stage].eventLog, stageLog->eventLog->numEvents);
376: for(event = 0; event < stageLog->eventLog->numEvents; event++) {
377: EventPerfInfoCopy(&stageLog->stageInfo[0].eventLog->eventInfo[event],
378: &stageLog->stageInfo[*stage].eventLog->eventInfo[event]);
379:
380: }
381: ClassPerfLogEnsureSize(stageLog->stageInfo[*stage].classLog, stageLog->classLog->numClasses);
382: return(0);
383: }
385: #undef __FUNCT__
387: /*@C
388: PetscLogStagePush - This function pushes a stage on the stack.
390: Not Collective
392: Input Parameter:
393: . stage - The stage on which to log
395: Usage:
396: If the option -log_sumary is used to run the program containing the
397: following code, then 2 sets of summary data will be printed during
398: PetscFinalize().
399: .vb
400: PetscInitialize(int *argc,char ***args,0,0);
401: [stage 0 of code]
402: PetscLogStagePush(1);
403: [stage 1 of code]
404: PetscLogStagePop();
405: PetscBarrier(...);
406: [more stage 0 of code]
407: PetscFinalize();
408: .ve
409:
410: Notes:
411: Use PetscLogStageRegister() to register a stage.
413: Level: intermediate
415: .keywords: log, push, stage
416: .seealso: PetscLogStagePop(), PetscLogStageRegister(), PetscBarrier()
417: @*/
418: int PetscLogStagePush(int stage)
419: {
420: StageLog stageLog;
421: int ierr;
424: PetscLogGetStageLog(&stageLog);
425: StageLogPush(stageLog, stage);
426: return(0);
427: }
429: #undef __FUNCT__
431: /*@C
432: PetscLogStagePop - This function pops a stage from the stack.
434: Not Collective
436: Usage:
437: If the option -log_sumary is used to run the program containing the
438: following code, then 2 sets of summary data will be printed during
439: PetscFinalize().
440: .vb
441: PetscInitialize(int *argc,char ***args,0,0);
442: [stage 0 of code]
443: PetscLogStagePush(1);
444: [stage 1 of code]
445: PetscLogStagePop();
446: PetscBarrier(...);
447: [more stage 0 of code]
448: PetscFinalize();
449: .ve
451: Notes:
452: Use PetscLogStageRegister() to register a stage.
454: Level: intermediate
456: .keywords: log, pop, stage
457: .seealso: PetscLogStagePush(), PetscLogStageRegister(), PetscBarrier()
458: @*/
459: int PetscLogStagePop(void)
460: {
461: StageLog stageLog;
462: int ierr;
465: PetscLogGetStageLog(&stageLog);
466: StageLogPop(stageLog);
467: return(0);
468: }
470: #undef __FUNCT__
472: /*@
473: PetscLogStageSetActive - Determines stage activity for PetscLogEventBegin() and PetscLogEventEnd().
475: Not Collective
477: Input Parameters:
478: + stage - The stage
479: - isActive - The activity flag, PETSC_TRUE for logging, else PETSC_FALSE (defaults to PETSC_TRUE)
481: Level: intermediate
483: .seealso: PetscLogStagePush(), PetscLogStagePop(), PetscLogEventBegin(), PetscLogEventEnd(), PreLoadBegin(), PreLoadEnd(), PreLoadStage()
484: @*/
485: int PetscLogStageSetActive(int stage, PetscTruth isActive) {
486: StageLog stageLog;
487: int ierr;
490: PetscLogGetStageLog(&stageLog);
491: StageLogSetActive(stageLog, stage, isActive);
492: return(0);
493: }
495: #undef __FUNCT__
497: /*@
498: PetscLogStageGetActive - Returns stage activity for PetscLogEventBegin() and PetscLogEventEnd().
500: Not Collective
502: Input Parameter:
503: . stage - The stage
505: Output Parameter:
506: . isActive - The activity flag, PETSC_TRUE for logging, else PETSC_FALSE (defaults to PETSC_TRUE)
508: Level: intermediate
510: .seealso: PetscLogStagePush(), PetscLogStagePop(), PetscLogEventBegin(), PetscLogEventEnd(), PreLoadBegin(), PreLoadEnd(), PreLoadStage()
511: @*/
512: int PetscLogStageGetActive(int stage, PetscTruth *isActive) {
513: StageLog stageLog;
514: int ierr;
517: PetscLogGetStageLog(&stageLog);
518: StageLogGetActive(stageLog, stage, isActive);
519: return(0);
520: }
522: #undef __FUNCT__
524: /*@
525: PetscLogStageSetVisible - Determines stage visibility in PetscLogPrintSummary()
527: Not Collective
529: Input Parameters:
530: + stage - The stage
531: - isVisible - The visibility flag, PETSC_TRUE to print, else PETSC_FALSE (defaults to PETSC_TRUE)
533: Level: intermediate
535: .seealso: PetscLogStagePush(), PetscLogStagePop(), PetscLogPrintSummary()
536: @*/
537: int PetscLogStageSetVisible(int stage, PetscTruth isVisible)
538: {
539: StageLog stageLog;
540: int ierr;
543: PetscLogGetStageLog(&stageLog);
544: StageLogSetVisible(stageLog, stage, isVisible);
545: return(0);
546: }
548: #undef __FUNCT__
550: /*@
551: PetscLogStageGetVisible - Returns stage visibility in PetscLogPrintSummary()
553: Not Collective
555: Input Parameter:
556: . stage - The stage
558: Output Parameter:
559: . isVisible - The visibility flag, PETSC_TRUE to print, else PETSC_FALSE (defaults to PETSC_TRUE)
561: Level: intermediate
563: .seealso: PetscLogStagePush(), PetscLogStagePop(), PetscLogPrintSummary()
564: @*/
565: int PetscLogStageGetVisible(int stage, PetscTruth *isVisible)
566: {
567: StageLog stageLog;
568: int ierr;
571: PetscLogGetStageLog(&stageLog);
572: StageLogGetVisible(stageLog, stage, isVisible);
573: return(0);
574: }
576: #undef __FUNCT__
578: /*@
579: PetscLogStageGetId - Returns the stage id when given the stage name.
581: Not Collective
583: Input Parameter:
584: . name - The stage name
586: Output Parameter:
587: . stage - The stage
589: Level: intermediate
591: .seealso: PetscLogStagePush(), PetscLogStagePop(), PreLoadBegin(), PreLoadEnd(), PreLoadStage()
592: @*/
593: int PetscLogStageGetId(const char name[], int *stage)
594: {
595: StageLog stageLog;
596: int ierr;
599: PetscLogGetStageLog(&stageLog);
600: StageLogGetStage(stageLog, name, stage);
601: return(0);
602: }
604: /*------------------------------------------------ Event Functions --------------------------------------------------*/
605: #undef __FUNCT__
607: /*@C
608: PetscLogEventRegister - Registers an event name for logging operations in an application code.
610: Not Collective
612: Input Parameter:
613: + name - The name associated with the event
614: - cookie - The cookie associated to the class for this event
615:
616: Output Parameter:
617: . event - The event id for use with PetscLogEventBegin() and PetscLogEventEnd().
619: Example of Usage:
620: .vb
621: int USER_EVENT;
622: int user_event_flops;
623: PetscLogEventRegister(&USER_EVENT,"User event name");
624: PetscLogEventBegin(USER_EVENT,0,0,0,0);
625: [code segment to monitor]
626: PetscLogFlops(user_event_flops);
627: PetscLogEventEnd(USER_EVENT,0,0,0,0);
628: .ve
630: Notes:
631: PETSc automatically logs library events if the code has been
632: compiled with -DPETSC_USE_LOG (which is the default) and -log,
633: -log_summary, or -log_all are specified. PetscLogEventRegister() is
634: intended for logging user events to supplement this PETSc
635: information.
637: PETSc can gather data for use with the utilities Upshot/Nupshot
638: (part of the MPICH distribution). If PETSc has been compiled
639: with flag -DPETSC_HAVE_MPE (MPE is an additional utility within
640: MPICH), the user can employ another command line option, -log_mpe,
641: to create a logfile, "mpe.log", which can be visualized
642: Upshot/Nupshot.
644: Level: intermediate
646: .keywords: log, event, register
647: .seealso: PetscLogEventBegin(), PetscLogEventEnd(), PetscLogFlops(),
648: PetscLogEventMPEActivate(), PetscLogEventMPEDeactivate(),
649: PetscLogEventActivate(), PetscLogEventDeactivate()
650: @*/
651: int PetscLogEventRegister(int *event, const char name[],int cookie) {
652: StageLog stageLog;
653: int stage;
654: int ierr;
657: *event = PETSC_DECIDE;
658: PetscLogGetStageLog(&stageLog);
659: EventRegLogRegister(stageLog->eventLog, name, cookie, event);
660: for(stage = 0; stage < stageLog->numStages; stage++) {
661: EventPerfLogEnsureSize(stageLog->stageInfo[stage].eventLog, stageLog->eventLog->numEvents);
662: ClassPerfLogEnsureSize(stageLog->stageInfo[stage].classLog, stageLog->classLog->numClasses);
663: }
664: return(0);
665: }
667: #undef __FUNCT__
669: /*@
670: PetscLogEventActivate - Indicates that a particular event should be logged.
672: Not Collective
674: Input Parameter:
675: . event - The event id
677: Usage:
678: .vb
679: PetscLogEventDeactivate(VEC_SetValues);
680: [code where you do not want to log VecSetValues()]
681: PetscLogEventActivate(VEC_SetValues);
682: [code where you do want to log VecSetValues()]
683: .ve
685: Note:
686: The event may be either a pre-defined PETSc event (found in include/petsclog.h)
687: or an event number obtained with PetscLogEventRegister().
689: Level: advanced
691: .keywords: log, event, activate
692: .seealso: PetscLogEventMPEDeactivate(),PetscLogEventMPEActivate(),PlogEventDeactivate()
693: @*/
694: int PetscLogEventActivate(int event) {
695: StageLog stageLog;
696: int stage;
697: int ierr;
700: PetscLogGetStageLog(&stageLog);
701: StageLogGetCurrent(stageLog, &stage);
702: EventPerfLogActivate(stageLog->stageInfo[stage].eventLog, event);
703: return(0);
704: }
706: #undef __FUNCT__
708: /*@
709: PetscLogEventDeactivate - Indicates that a particular event should not be logged.
711: Not Collective
713: Input Parameter:
714: . event - The event id
716: Usage:
717: .vb
718: PetscLogEventDeactivate(VEC_SetValues);
719: [code where you do not want to log VecSetValues()]
720: PetscLogEventActivate(VEC_SetValues);
721: [code where you do want to log VecSetValues()]
722: .ve
724: Note:
725: The event may be either a pre-defined PETSc event (found in
726: include/petsclog.h) or an event number obtained with PetscLogEventRegister()).
728: Level: advanced
730: .keywords: log, event, deactivate
731: .seealso: PetscLogEventMPEDeactivate(),PetscLogEventMPEActivate(),PlogEventActivate()
732: @*/
733: int PetscLogEventDeactivate(int event) {
734: StageLog stageLog;
735: int stage;
736: int ierr;
739: PetscLogGetStageLog(&stageLog);
740: StageLogGetCurrent(stageLog, &stage);
741: EventPerfLogDeactivate(stageLog->stageInfo[stage].eventLog, event);
742: return(0);
743: }
745: #undef __FUNCT__
747: /*@
748: PetscLogEventSetActiveAll - Sets the event activity in every stage.
750: Not Collective
752: Input Parameters:
753: + event - The event id
754: - isActive - The activity flag determining whether the event is logged
756: Level: advanced
758: .keywords: log, event, activate
759: .seealso: PetscLogEventMPEDeactivate(),PetscLogEventMPEActivate(),PlogEventActivate(),PlogEventDeactivate()
760: @*/
761: int PetscLogEventSetActiveAll(int event, PetscTruth isActive) {
762: StageLog stageLog;
763: int stage;
764: int ierr;
767: PetscLogGetStageLog(&stageLog);
768: for(stage = 0; stage < stageLog->numStages; stage++) {
769: if (isActive == PETSC_TRUE) {
770: EventPerfLogActivate(stageLog->stageInfo[stage].eventLog, event);
771: } else {
772: EventPerfLogDeactivate(stageLog->stageInfo[stage].eventLog, event);
773: }
774: }
775: return(0);
776: }
778: #undef __FUNCT__
780: /*@
781: PetscLogEventActivateClass - Activates event logging for a PETSc object class.
783: Not Collective
785: Input Parameter:
786: . cookie - The event class, for example MAT_COOKIE, SNES_COOKIE, etc.
788: Level: developer
790: .keywords: log, event, activate, class
791: .seealso: PetscLogInfoActivate(),PetscLogInfo(),PetscLogInfoAllow(),PetscLogEventDeactivateClass(), PetscLogEventActivate(),PetscLogEventDeactivate()
792: @*/
793: int PetscLogEventActivateClass(int cookie) {
794: StageLog stageLog;
795: int stage;
796: int ierr;
799: PetscLogGetStageLog(&stageLog);
800: StageLogGetCurrent(stageLog, &stage);
801: EventPerfLogActivateClass(stageLog->stageInfo[stage].eventLog, stageLog->eventLog, cookie);
802: return(0);
803: }
805: #undef __FUNCT__
807: /*@
808: PetscLogEventDeactivateClass - Deactivates event logging for a PETSc object class.
810: Not Collective
812: Input Parameter:
813: . cookie - The event class, for example MAT_COOKIE, SNES_COOKIE, etc.
815: Level: developer
817: .keywords: log, event, deactivate, class
818: .seealso: PetscLogInfoActivate(),PetscLogInfo(),PetscLogInfoAllow(),PetscLogEventActivateClass(), PetscLogEventActivate(),PetscLogEventDeactivate()
819: @*/
820: int PetscLogEventDeactivateClass(int cookie) {
821: StageLog stageLog;
822: int stage;
823: int ierr;
826: PetscLogGetStageLog(&stageLog);
827: StageLogGetCurrent(stageLog, &stage);
828: EventPerfLogDeactivateClass(stageLog->stageInfo[stage].eventLog, stageLog->eventLog, cookie);
829: return(0);
830: }
832: /*MC
833: PetscLogEventBegin - Logs the beginning of a user event.
835: Input Parameters:
836: + e - integer associated with the event obtained from PetscLogEventRegister()
837: - o1,o2,o3,o4 - objects associated with the event, or 0
839: Synopsis:
840: void PetscLogEventBegin(int e,PetscObject o1,PetscObject o2,PetscObject o3,
841: PetscObject o4)
843: Fortran Synopsis:
844: void PetscLogEventEnd(int e,int ierr)
846: Usage:
847: .vb
848: int USER_EVENT;
849: int user_event_flops;
850: PetscLogEventRegister(&USER_EVENT,"User event");
851: PetscLogEventBegin(USER_EVENT,0,0,0,0);
852: [code segment to monitor]
853: PetscLogFlops(user_event_flops);
854: PetscLogEventEnd(USER_EVENT,0,0,0,0);
855: .ve
857: Notes:
858: You need to register each integer event with the command
859: PetscLogEventRegister(). The source code must be compiled with
860: -DPETSC_USE_LOG, which is the default.
862: PETSc automatically logs library events if the code has been
863: compiled with -DPETSC_USE_LOG, and -log, -log_summary, or -log_all are
864: specified. PetscLogEventBegin() is intended for logging user events
865: to supplement this PETSc information.
867: Level: intermediate
869: .seealso: PetscLogEventRegister(), PetscLogEventEnd(), PetscLogFlops()
871: .keywords: log, event, begin
872: M*/
874: /*MC
875: PetscLogEventEnd - Log the end of a user event.
877: Input Parameters:
878: + e - integer associated with the event obtained with PetscLogEventRegister()
879: - o1,o2,o3,o4 - objects associated with the event, or 0
881: Synopsis:
882: void PetscLogEventEnd(int e,PetscObject o1,PetscObject o2,PetscObject o3,
883: PetscObject o4)
885: Fortran Synopsis:
886: void PetscLogEventEnd(int e,int ierr)
888: Usage:
889: .vb
890: int USER_EVENT;
891: int user_event_flops;
892: PetscLogEventRegister(&USER_EVENT,"User event");
893: PetscLogEventBegin(USER_EVENT,0,0,0,0);
894: [code segment to monitor]
895: PetscLogFlops(user_event_flops);
896: PetscLogEventEnd(USER_EVENT,0,0,0,0);
897: .ve
899: Notes:
900: You should also register each additional integer event with the command
901: PetscLogEventRegister(). Source code must be compiled with
902: -DPETSC_USE_LOG, which is the default.
904: PETSc automatically logs library events if the code has been
905: compiled with -DPETSC_USE_LOG, and -log, -log_summary, or -log_all are
906: specified. PetscLogEventEnd() is intended for logging user events
907: to supplement this PETSc information.
909: Level: intermediate
911: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogFlops()
913: .keywords: log, event, end
914: M*/
916: /*MC
917: PetscLogEventBarrierBegin - Logs the time in a barrier before an event.
919: Input Parameters:
920: . e - integer associated with the event obtained from PetscLogEventRegister()
921: . o1,o2,o3,o4 - objects associated with the event, or 0
922: . comm - communicator the barrier takes place over
924: Synopsis:
925: void PetscLogEventBarrierBegin(int e,PetscObject o1,PetscObject o2,PetscObject o3,
926: PetscObject o4,MPI_Comm comm)
928: Usage:
929: .vb
930: PetscLogEventBarrierBegin(VEC_NormBarrier,0,0,0,0,comm);
931: MPI_Allreduce()
932: PetscLogEventBarrierEnd(VEC_NormBarrier,0,0,0,0,comm);
933: .ve
935: Notes:
936: This is for logging the amount of time spent in a barrier for an event
937: that requires synchronization.
939: Additional Notes:
940: Synchronization events always come in pairs; for example, VEC_NormBarrier and
941: VEC_NormComm = VEC_NormBarrier + 1
943: Level: advanced
945: .seealso: PetscLogEventRegister(), PetscLogEventEnd(), PetscLogFlops(), PetscLogEventBegin(),
946: PetscLogEventBarrierEnd()
948: .keywords: log, event, begin, barrier
949: M*/
951: /*MC
952: PetscLogEventBarrierEnd - Logs the time in a barrier before an event.
954: Input Parameters:
955: . e - integer associated with the event obtained from PetscLogEventRegister()
956: . o1,o2,o3,o4 - objects associated with the event, or 0
957: . comm - communicator the barrier takes place over
959: Synopsis:
960: void PetscLogEventBarrierEnd(int e,PetscObject o1,PetscObject o2,PetscObject o3,
961: PetscObject o4,MPI_Comm comm)
963: Usage:
964: .vb
965: PetscLogEventBarrierBegin(VEC_NormBarrier,0,0,0,0,comm);
966: MPI_Allreduce()
967: PetscLogEventBarrierEnd(VEC_NormBarrier,0,0,0,0,comm);
968: .ve
970: Notes:
971: This is for logging the amount of time spent in a barrier for an event
972: that requires synchronization.
974: Additional Notes:
975: Synchronization events always come in pairs; for example, VEC_NormBarrier and
976: VEC_NormComm = VEC_NormBarrier + 1
978: Level: advanced
980: .seealso: PetscLogEventRegister(), PetscLogEventEnd(), PetscLogFlops(), PetscLogEventBegin(),
981: PetscLogEventBarrierBegin()
983: .keywords: log, event, begin, barrier
984: M*/
986: /*------------------------------------------------ Class Functions --------------------------------------------------*/
987: #undef __FUNCT__
989: /*@C
990: PetscLogClassRegister - Registers a class name for logging operations in an application code.
992: Not Collective
994: Input Parameter:
995: . name - The class name
996:
997: Output Parameter:
998: . oclass - The class id or cookie
1000: Level: developer
1002: .keywords: log, class, register
1003: .seealso: ClassLogRegister()
1004: @*/
1005: int PetscLogClassRegister(int *oclass, const char name[])
1006: {
1007: StageLog stageLog;
1008: int ierr;
1011: *oclass = PETSC_DECIDE;
1012: PetscLogGetStageLog(&stageLog);
1013: ClassRegLogRegister(stageLog->classLog, name, oclass);
1014: return(0);
1015: }
1017: /*------------------------------------------------ Output Functions -------------------------------------------------*/
1018: #undef __FUNCT__
1020: /*@C
1021: PetscLogDump - Dumps logs of objects to a file. This file is intended to
1022: be read by petsc/bin/petscview.
1024: Collective on PETSC_COMM_WORLD
1026: Input Parameter:
1027: . name - an optional file name
1029: Options Database Keys:
1030: + -log - Prints basic log information (for code compiled with PETSC_USE_LOG)
1031: - -log_all - Prints extensive log information (for code compiled with PETSC_USE_LOG)
1032:
1033: Usage:
1034: .vb
1035: PetscInitialize(...);
1036: PetscLogBegin(); or PetscLogAllBegin();
1037: ... code ...
1038: PetscLogDump(filename);
1039: PetscFinalize();
1040: .ve
1042: Notes:
1043: The default file name is
1044: $ Log.<rank>
1045: where <rank> is the processor number. If no name is specified,
1046: this file will be used.
1048: Level: advanced
1050: .keywords: log, dump
1051: .seealso: PetscLogBegin(), PetscLogAllBegin(), PetscLogPrintSummary()
1052: @*/
1053: int PetscLogDump(const char sname[]) {
1054: StageLog stageLog;
1055: EventPerfInfo *eventInfo;
1056: FILE *fd;
1057: char file[PETSC_MAX_PATH_LEN], fname[PETSC_MAX_PATH_LEN];
1058: PetscLogDouble flops, _TotalTime;
1059: int rank, curStage;
1060: int action, object, event;
1061: int ierr;
1062:
1064: /* Calculate the total elapsed time */
1065: PetscTime(_TotalTime);
1066: _TotalTime -= BaseTime;
1067: /* Open log file */
1068: MPI_Comm_rank(PETSC_COMM_WORLD, &rank);
1069: if (sname != PETSC_NULL) {
1070: sprintf(file, "%s.%d", sname, rank);
1071: } else {
1072: sprintf(file, "Log.%d", rank);
1073: }
1074: PetscFixFilename(file, fname);
1075: PetscFOpen(PETSC_COMM_WORLD, fname, "w", &fd);
1076: if ((rank == 0) && (fd == PETSC_NULL)) SETERRQ1(PETSC_ERR_FILE_OPEN, "Cannot open file: %s", fname);
1077: /* Output totals */
1078: PetscFPrintf(PETSC_COMM_WORLD, fd, "Total Flops %14e %16.8en", _TotalFlops, _TotalTime);
1079: PetscFPrintf(PETSC_COMM_WORLD, fd, "Clock Resolution %gn", 0.0);
1080: /* Output actions */
1081: PetscFPrintf(PETSC_COMM_WORLD, fd, "Actions accomplished %dn", numActions);
1082: for(action = 0; action < numActions; action++) {
1083: PetscFPrintf(PETSC_COMM_WORLD, fd, "%g %d %d %d %d %d %d %g %g %gn",
1084: actions[action].time, actions[action].action, actions[action].event, actions[action].cookie, actions[action].id1,
1085: actions[action].id2, actions[action].id3, actions[action].flops, actions[action].mem, actions[action].maxmem);
1086: }
1087: /* Output objects */
1088: PetscFPrintf(PETSC_COMM_WORLD, fd, "Objects created %d destroyed %dn", numObjects, numObjectsDestroyed);
1089: for(object = 0; object < numObjects; object++) {
1090: PetscFPrintf(PETSC_COMM_WORLD, fd, "Parent ID: %d Memory: %dn", objects[object].parent, (int) objects[object].mem);
1091: if (!objects[object].name[0]) {
1092: PetscFPrintf(PETSC_COMM_WORLD, fd,"No Namen");
1093: } else {
1094: PetscFPrintf(PETSC_COMM_WORLD, fd, "Name: %sn", objects[object].name);
1095: }
1096: if (objects[object].info[0] != 0) {
1097: PetscFPrintf(PETSC_COMM_WORLD, fd, "No Infon");
1098: } else {
1099: PetscFPrintf(PETSC_COMM_WORLD, fd, "Info: %sn", objects[object].info);
1100: }
1101: }
1102: /* Output events */
1103: PetscFPrintf(PETSC_COMM_WORLD, fd, "Event log:n");
1104: PetscLogGetStageLog(&stageLog);
1105: StackTop(stageLog->stack, &curStage);
1106: eventInfo = stageLog->stageInfo[curStage].eventLog->eventInfo;
1107: for(event = 0; event < stageLog->stageInfo[curStage].eventLog->numEvents; event++) {
1108: if (eventInfo[event].time != 0.0) {
1109: flops = eventInfo[event].flops/eventInfo[event].time;
1110: } else {
1111: flops = 0.0;
1112: }
1113: PetscFPrintf(PETSC_COMM_WORLD, fd, "%d %16d %16g %16g %16gn", event, eventInfo[event].count,
1114: eventInfo[event].flops, eventInfo[event].time, flops);
1115: }
1116: PetscFClose(PETSC_COMM_WORLD, fd);
1117: return(0);
1118: }
1120: #undef __FUNCT__
1122: /*@C
1123: PetscLogPrintSummary - Prints a summary of the logging.
1125: Collective over MPI_Comm
1127: Input Parameter:
1128: + comm - The MPI communicator (only one processor prints output)
1129: - file - [Optional] The output file name
1131: Options Database Keys:
1132: . -log_summary - Prints summary of log information (for code compiled with PETSC_USE_LOG)
1134: Usage:
1135: .vb
1136: PetscInitialize(...);
1137: PetscLogBegin();
1138: ... code ...
1139: PetscLogPrintSummary(MPI_Comm,filename);
1140: PetscFinalize(...);
1141: .ve
1143: Notes:
1144: By default the summary is printed to stdout.
1145: More extensive examination of the log information can be done with
1146: PetscLogDump(), which is activated by the option -log or -log_all, in
1147: combination with petsc/bin/petscview.
1149: Level: beginner
1150:
1151: .keywords: log, dump, print
1152: .seealso: PetscLogBegin(), PetscLogDump()
1153: @*/
1154: int PetscLogPrintSummary(MPI_Comm comm, const char filename[]) {
1155: FILE *fd = stdout;
1156: PetscScalar zero = 0.0;
1157: StageLog stageLog;
1158: StageInfo *stageInfo = PETSC_NULL;
1159: EventPerfInfo *eventInfo = PETSC_NULL;
1160: ClassPerfInfo *classInfo;
1161: char arch[10], hostname[64], username[16], pname[PETSC_MAX_PATH_LEN], date[64];
1162: char *name;
1163: PetscLogDouble locTotalTime, TotalTime, TotalFlops;
1164: PetscLogDouble numMessages, messageLength, avgMessLen, numReductions;
1165: PetscLogDouble stageTime, flops, flopr, mem, mess, messLen, red;
1166: PetscLogDouble fracTime, fracFlops, fracMessages, fracLength, fracReductions, fracMess, fracMessLen, fracRed;
1167: PetscLogDouble fracStageTime, fracStageFlops, fracStageMess, fracStageMessLen, fracStageRed;
1168: PetscLogDouble min, max, tot, ratio, avg, x, y;
1169: PetscLogDouble minf, maxf, totf, ratf, mint, maxt, tott, ratt, ratCt, totm, totml, totr;
1170: int minCt, maxCt;
1171: int numProcs, rank;
1172: PetscTruth *localStageUsed, *stageUsed;
1173: PetscTruth *localStageVisible, *stageVisible;
1174: int numStages, localNumEvents, numEvents;
1175: int stage, event, oclass;
1176: int ierr;
1177: char version[256];
1180: MPI_Comm_size(comm, &numProcs);
1181: MPI_Comm_rank(comm, &rank);
1182: /* Pop off any stages the user forgot to remove */
1183: PetscLogGetStageLog(&stageLog);
1184: StageLogGetCurrent(stageLog, &stage);
1185: while (stage >= 0) {
1186: StageLogPop(stageLog);
1187: StageLogGetCurrent(stageLog, &stage);
1188: }
1189: /* Get the total elapsed time */
1190: PetscTime(locTotalTime); locTotalTime -= BaseTime;
1191: /* Open the summary file */
1192: if (filename != PETSC_NULL) {
1193: PetscFOpen(comm, filename, "w", &fd);
1194: }
1196: PetscFPrintf(comm, fd, "************************************************************************************************************************n");
1197: PetscFPrintf(comm, fd, "*** WIDEN YOUR WINDOW TO 120 CHARACTERS. Use 'enscript -r -fCourier9' to print this document ***n");
1198: PetscFPrintf(comm, fd, "************************************************************************************************************************n");
1199: PetscFPrintf(comm, fd, "n---------------------------------------------- PETSc Performance Summary: ----------------------------------------------nn");
1200: PetscGetArchType(arch, 10);
1201: PetscGetHostName(hostname, 64);
1202: PetscGetUserName(username, 16);
1203: PetscGetProgramName(pname, PETSC_MAX_PATH_LEN);
1204: PetscGetDate(date, 64);
1205: PetscGetVersion(&version);
1206: if (numProcs == 1) {
1207: PetscFPrintf(comm,fd,"%s on a %s named %s with %d processor, by %s %sn", pname, arch, hostname, numProcs, username, date);
1208:
1209: } else {
1210: PetscFPrintf(comm,fd,"%s on a %s named %s with %d processors, by %s %sn", pname, arch, hostname, numProcs, username, date);
1211:
1212: }
1213: PetscFPrintf(comm, fd, "Using %sn", version);
1215: /* Must preserve reduction count before we go on */
1216: red = allreduce_ct/((PetscLogDouble) numProcs);
1218: /* Calculate summary information */
1219: PetscFPrintf(comm, fd, "n Max Max/Min Avg Total n");
1220: /* Time */
1221: MPI_Allreduce(&locTotalTime, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1222: MPI_Allreduce(&locTotalTime, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1223: MPI_Allreduce(&locTotalTime, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1224: avg = (tot)/((PetscLogDouble) numProcs);
1225: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1226: PetscFPrintf(comm, fd, "Time (sec): %5.3e %10.5f %5.3en", max, ratio, avg);
1227: TotalTime = tot;
1228: /* Objects */
1229: avg = (PetscLogDouble) numObjects;
1230: MPI_Allreduce(&avg, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1231: MPI_Allreduce(&avg, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1232: MPI_Allreduce(&avg, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1233: avg = (tot)/((PetscLogDouble) numProcs);
1234: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1235: PetscFPrintf(comm, fd, "Objects: %5.3e %10.5f %5.3en", max, ratio, avg);
1236: /* Flops */
1237: MPI_Allreduce(&_TotalFlops, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1238: MPI_Allreduce(&_TotalFlops, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1239: MPI_Allreduce(&_TotalFlops, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1240: avg = (tot)/((PetscLogDouble) numProcs);
1241: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1242: PetscFPrintf(comm, fd, "Flops: %5.3e %10.5f %5.3e %5.3en", max, ratio, avg, tot);
1243: TotalFlops = tot;
1244: /* Flops/sec -- Must talk to Barry here */
1245: if (locTotalTime != 0.0) flops = _TotalFlops/locTotalTime; else flops = 0.0;
1246: MPI_Allreduce(&flops, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1247: MPI_Allreduce(&flops, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1248: MPI_Allreduce(&flops, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1249: avg = (tot)/((PetscLogDouble) numProcs);
1250: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1251: PetscFPrintf(comm, fd, "Flops/sec: %5.3e %10.5f %5.3e %5.3en", max, ratio, avg, tot);
1252: /* Memory */
1253: PetscTrSpace(PETSC_NULL, PETSC_NULL, &mem);
1254: if (mem > 0.0) {
1255: MPI_Allreduce(&mem, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1256: MPI_Allreduce(&mem, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1257: MPI_Allreduce(&mem, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1258: avg = (tot)/((PetscLogDouble) numProcs);
1259: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1260: PetscFPrintf(comm, fd, "Memory: %5.3e %10.5f %5.3en", max, ratio, tot);
1261: }
1262: /* Messages */
1263: mess = 0.5*(irecv_ct + isend_ct + recv_ct + send_ct);
1264: MPI_Allreduce(&mess, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1265: MPI_Allreduce(&mess, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1266: MPI_Allreduce(&mess, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1267: avg = (tot)/((PetscLogDouble) numProcs);
1268: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1269: PetscFPrintf(comm, fd, "MPI Messages: %5.3e %10.5f %5.3e %5.3en", max, ratio, avg, tot);
1270: numMessages = tot;
1271: /* Message Lengths */
1272: mess = 0.5*(irecv_len + isend_len + recv_len + send_len);
1273: MPI_Allreduce(&mess, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1274: MPI_Allreduce(&mess, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1275: MPI_Allreduce(&mess, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1276: if (numMessages != 0) avg = (tot)/(numMessages); else avg = 0.0;
1277: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1278: PetscFPrintf(comm, fd, "MPI Message Lengths: %5.3e %10.5f %5.3e %5.3en", max, ratio, avg, tot);
1279: messageLength = tot;
1280: /* Reductions */
1281: MPI_Allreduce(&red, &min, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1282: MPI_Allreduce(&red, &max, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1283: MPI_Allreduce(&red, &tot, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1284: if (min != 0.0) ratio = max/min; else ratio = 0.0;
1285: PetscFPrintf(comm, fd, "MPI Reductions: %5.3e %10.5fn", max, ratio);
1286: numReductions = tot;
1287: PetscFPrintf(comm, fd, "nFlop counting convention: 1 flop = 1 real number operation of type (multiply/divide/add/subtract)n");
1288: PetscFPrintf(comm, fd, " e.g., VecAXPY() for real vectors of length N --> 2N flopsn");
1289: PetscFPrintf(comm, fd, " and VecAXPY() for complex vectors of length N --> 8N flopsn");
1291: /* Get total number of stages --
1292: Currently, a single processor can register more stages than another, but stages must all be registered in order.
1293: We can removed this requirement if necessary by having a global stage numbering and indirection on the stage ID.
1294: This seems best accomplished by assoicating a communicator with each stage.
1295: */
1296: MPI_Allreduce(&stageLog->numStages, &numStages, 1, MPI_INT, MPI_MAX, comm);
1297: PetscMalloc(numStages * sizeof(PetscTruth), &localStageUsed);
1298: PetscMalloc(numStages * sizeof(PetscTruth), &stageUsed);
1299: PetscMalloc(numStages * sizeof(PetscTruth), &localStageVisible);
1300: PetscMalloc(numStages * sizeof(PetscTruth), &stageVisible);
1301: if (numStages > 0) {
1302: stageInfo = stageLog->stageInfo;
1303: for(stage = 0; stage < numStages; stage++) {
1304: if (stage < stageLog->numStages) {
1305: localStageUsed[stage] = stageInfo[stage].used;
1306: localStageVisible[stage] = stageInfo[stage].perfInfo.visible;
1307: } else {
1308: localStageUsed[stage] = PETSC_FALSE;
1309: localStageVisible[stage] = PETSC_TRUE;
1310: }
1311: }
1312: MPI_Allreduce(localStageUsed, stageUsed, numStages, MPI_INT, MPI_LOR, comm);
1313: MPI_Allreduce(localStageVisible, stageVisible, numStages, MPI_INT, MPI_LAND, comm);
1314: for(stage = 0; stage < numStages; stage++) {
1315: if (stageUsed[stage] == PETSC_TRUE) {
1316: PetscFPrintf(comm, fd, "nSummary of Stages: ----- Time ------ ----- Flops ----- --- Messages --- -- Message Lengths -- -- Reductions --n");
1317: PetscFPrintf(comm, fd, " Avg %%Total Avg %%Total counts %%Total Avg %%Total counts %%Total n");
1318: break;
1319: }
1320: }
1321: for(stage = 0; stage < numStages; stage++) {
1322: if (stageUsed[stage] == PETSC_FALSE) continue;
1323: if (localStageUsed[stage] == PETSC_TRUE) {
1324: MPI_Allreduce(&stageInfo[stage].perfInfo.time, &stageTime, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1325: MPI_Allreduce(&stageInfo[stage].perfInfo.flops, &flops, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1326: MPI_Allreduce(&stageInfo[stage].perfInfo.numMessages, &mess, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1327: MPI_Allreduce(&stageInfo[stage].perfInfo.messageLength, &messLen, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1328: MPI_Allreduce(&stageInfo[stage].perfInfo.numReductions, &red, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1329: name = stageInfo[stage].name;
1330: } else {
1331: MPI_Allreduce(&zero, &stageTime, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1332: MPI_Allreduce(&zero, &flops, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1333: MPI_Allreduce(&zero, &mess, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1334: MPI_Allreduce(&zero, &messLen, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1335: MPI_Allreduce(&zero, &red, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1336: name = "";
1337: }
1338: mess *= 0.5; messLen *= 0.5; red /= numProcs;
1339: if (TotalTime != 0.0) fracTime = stageTime/TotalTime; else fracTime = 0.0;
1340: if (TotalFlops != 0.0) fracFlops = flops/TotalFlops; else fracFlops = 0.0;
1341: /* Talk to Barry if (stageTime != 0.0) flops = (numProcs*flops)/stageTime; else flops = 0.0; */
1342: if (numMessages != 0.0) fracMessages = mess/numMessages; else fracMessages = 0.0;
1343: if (numMessages != 0.0) avgMessLen = messLen/numMessages; else avgMessLen = 0.0;
1344: if (messageLength != 0.0) fracLength = messLen/messageLength; else fracLength = 0.0;
1345: if (numReductions != 0.0) fracReductions = red/numReductions; else fracReductions = 0.0;
1346: PetscFPrintf(comm, fd, "%2d: %15s: %6.4e %5.1f%% %6.4e %5.1f%% %5.3e %5.1f%% %5.3e %5.1f%% %5.3e %5.1f%% n",
1347: stage, name, stageTime/numProcs, 100.0*fracTime, flops, 100.0*fracFlops,
1348: mess, 100.0*fracMessages, avgMessLen, 100.0*fracLength, red, 100.0*fracReductions);
1349:
1350: }
1351: }
1353: PetscFPrintf(comm, fd,
1354: "n------------------------------------------------------------------------------------------------------------------------n");
1355:
1356: PetscFPrintf(comm, fd, "See the 'Profiling' chapter of the users' manual for details on interpreting output.n");
1357: PetscFPrintf(comm, fd, "Phase summary info:n");
1358: PetscFPrintf(comm, fd, " Count: number of times phase was executedn");
1359: PetscFPrintf(comm, fd, " Time and Flops/sec: Max - maximum over all processorsn");
1360: PetscFPrintf(comm, fd, " Ratio - ratio of maximum to minimum over all processorsn");
1361: PetscFPrintf(comm, fd, " Mess: number of messages sentn");
1362: PetscFPrintf(comm, fd, " Avg. len: average message lengthn");
1363: PetscFPrintf(comm, fd, " Reduct: number of global reductionsn");
1364: PetscFPrintf(comm, fd, " Global: entire computationn");
1365: PetscFPrintf(comm, fd, " Stage: stages of a computation. Set stages with PetscLogStagePush() and PetscLogStagePop().n");
1366: PetscFPrintf(comm, fd, " %%T - percent time in this phase %%F - percent flops in this phasen");
1367: PetscFPrintf(comm, fd, " %%M - percent messages in this phase %%L - percent message lengths in this phasen");
1368: PetscFPrintf(comm, fd, " %%R - percent reductions in this phasen");
1369: PetscFPrintf(comm, fd, " Total Mflop/s: 10e-6 * (sum of flops over all processors)/(max time over all processors)n");
1370: PetscFPrintf(comm, fd,
1371: "------------------------------------------------------------------------------------------------------------------------n");
1372:
1374: #if defined(PETSC_USE_BOPT_g)
1375: PetscFPrintf(comm, fd, "nn");
1376: PetscFPrintf(comm, fd, " ##########################################################n");
1377: PetscFPrintf(comm, fd, " # #n");
1378: PetscFPrintf(comm, fd, " # WARNING!!! #n");
1379: PetscFPrintf(comm, fd, " # #n");
1380: PetscFPrintf(comm, fd, " # This code was compiled with a debugging option, #n");
1381: PetscFPrintf(comm, fd, " # BOPT=<g,g_c++,g_complex>. To get timing results #n");
1382: PetscFPrintf(comm, fd, " # ALWAYS compile your code with an optimized version, #n");
1383: PetscFPrintf(comm, fd, " # BOPT=<O,O_c++,O_complex>; the performance will #n");
1384: PetscFPrintf(comm, fd, " # be generally two or three times faster. #n");
1385: PetscFPrintf(comm, fd, " # #n");
1386: PetscFPrintf(comm, fd, " ##########################################################nnn");
1387: #endif
1388: #if defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_FORTRAN_KERNELS)
1389: PetscFPrintf(comm, fd, "nn");
1390: PetscFPrintf(comm, fd, " ##########################################################n");
1391: PetscFPrintf(comm, fd, " # #n");
1392: PetscFPrintf(comm, fd, " # WARNING!!! #n");
1393: PetscFPrintf(comm, fd, " # #n");
1394: PetscFPrintf(comm, fd, " # The code for various complex numbers numerical #n");
1395: PetscFPrintf(comm, fd, " # kernels uses C++, which generally is not well #n");
1396: PetscFPrintf(comm, fd, " # optimized. For performance that is about 4-5 times #n");
1397: PetscFPrintf(comm, fd, " # faster, specify the flag -DPETSC_USE_FORTRAN_KERNELS #n");
1398: PetscFPrintf(comm, fd, " # in base_variables and recompile the PETSc libraries. #n");
1399: PetscFPrintf(comm, fd, " # #n");
1400: PetscFPrintf(comm, fd, " ##########################################################nnn");
1401: #endif
1403: if (!PetscPreLoadingUsed) {
1404: PetscFPrintf(comm,fd,"nn");
1405: PetscFPrintf(comm,fd," ##########################################################n");
1406: PetscFPrintf(comm,fd," # #n");
1407: PetscFPrintf(comm,fd," # WARNING!!! #n");
1408: PetscFPrintf(comm,fd," # #n");
1409: PetscFPrintf(comm,fd," # This code was run without the PreLoadBegin() #n");
1410: PetscFPrintf(comm,fd," # macros. To get timing results we always recommend #n");
1411: PetscFPrintf(comm,fd," # preloading. otherwise timing numbers may be #n");
1412: PetscFPrintf(comm,fd," # meaningless. #n");
1413: PetscFPrintf(comm,fd," ##########################################################nnn");
1414: }
1416: /* Report events */
1417: PetscFPrintf(comm, fd,
1418: "Event Count Time (sec) Flops/sec --- Global --- --- Stage --- Totaln");
1419:
1420: PetscFPrintf(comm, fd,
1421: " Max Ratio Max Ratio Max Ratio Mess Avg len Reduct %%T %%F %%M %%L %%R %%T %%F %%M %%L %%R Mflop/sn");
1422:
1423: PetscFPrintf(comm,fd,
1424: "------------------------------------------------------------------------------------------------------------------------n");
1426:
1427: /* Problem: The stage name will not show up unless the stage executed on proc 1 */
1428: for(stage = 0; stage < numStages; stage++) {
1429: if (stageVisible[stage] == PETSC_FALSE) continue;
1430: if (localStageUsed[stage] == PETSC_TRUE) {
1431: PetscFPrintf(comm, fd, "n--- Event Stage %d: %snn", stage, stageInfo[stage].name);
1432: MPI_Allreduce(&stageInfo[stage].perfInfo.time, &stageTime, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1433: MPI_Allreduce(&stageInfo[stage].perfInfo.flops, &flops, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1434: MPI_Allreduce(&stageInfo[stage].perfInfo.numMessages, &mess, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1435: MPI_Allreduce(&stageInfo[stage].perfInfo.messageLength, &messLen, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1436: MPI_Allreduce(&stageInfo[stage].perfInfo.numReductions, &red, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1437: } else {
1438: PetscFPrintf(comm, fd, "n--- Event Stage %d: Unknownnn", stage);
1439: MPI_Allreduce(&zero, &stageTime, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1440: MPI_Allreduce(&zero, &flops, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1441: MPI_Allreduce(&zero, &mess, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1442: MPI_Allreduce(&zero, &messLen, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1443: MPI_Allreduce(&zero, &red, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1444: }
1445: mess *= 0.5; messLen *= 0.5; red /= numProcs;
1447: /* Get total number of events in this stage --
1448: Currently, a single processor can register more events than another, but events must all be registered in order,
1449: just like stages. We can removed this requirement if necessary by having a global event numbering and indirection
1450: on the event ID. This seems best accomplished by assoicating a communicator with each stage.
1452: Problem: If the event did not happen on proc 1, its name will not be available.
1453: Problem: Event visibility is not implemented
1454: */
1455: if (localStageUsed[stage] == PETSC_TRUE) {
1456: eventInfo = stageLog->stageInfo[stage].eventLog->eventInfo;
1457: localNumEvents = stageLog->stageInfo[stage].eventLog->numEvents;
1458: } else {
1459: localNumEvents = 0;
1460: }
1461: MPI_Allreduce(&localNumEvents, &numEvents, 1, MPI_INT, MPI_MAX, comm);
1462: for(event = 0; event < numEvents; event++) {
1463: if ((localStageUsed[stage] == PETSC_TRUE) && (event < stageLog->stageInfo[stage].eventLog->numEvents)) {
1464: if ((eventInfo[event].count > 0) && (eventInfo[event].time > 0.0)) {
1465: flopr = eventInfo[event].flops/eventInfo[event].time;
1466: } else {
1467: flopr = 0.0;
1468: }
1469: MPI_Allreduce(&flopr, &minf, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1470: MPI_Allreduce(&flopr, &maxf, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1471: MPI_Allreduce(&eventInfo[event].flops, &totf, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1472: MPI_Allreduce(&eventInfo[event].time, &mint, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1473: MPI_Allreduce(&eventInfo[event].time, &maxt, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1474: MPI_Allreduce(&eventInfo[event].time, &tott, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1475: MPI_Allreduce(&eventInfo[event].numMessages, &totm, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1476: MPI_Allreduce(&eventInfo[event].messageLength, &totml, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1477: MPI_Allreduce(&eventInfo[event].numReductions, &totr, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1478: MPI_Allreduce(&eventInfo[event].count, &minCt, 1, MPI_INT, MPI_MIN, comm);
1479: MPI_Allreduce(&eventInfo[event].count, &maxCt, 1, MPI_INT, MPI_MAX, comm);
1480: name = stageLog->eventLog->eventInfo[event].name;
1481: } else {
1482: flopr = 0.0;
1483: MPI_Allreduce(&flopr, &minf, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1484: MPI_Allreduce(&flopr, &maxf, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1485: MPI_Allreduce(&zero, &totf, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1486: MPI_Allreduce(&zero, &mint, 1, MPIU_PETSCLOGDOUBLE, MPI_MIN, comm);
1487: MPI_Allreduce(&zero, &maxt, 1, MPIU_PETSCLOGDOUBLE, MPI_MAX, comm);
1488: MPI_Allreduce(&zero, &tott, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1489: MPI_Allreduce(&zero, &totm, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1490: MPI_Allreduce(&zero, &totml, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1491: MPI_Allreduce(&zero, &totr, 1, MPIU_PETSCLOGDOUBLE, MPI_SUM, comm);
1492: MPI_Allreduce(&ierr, &minCt, 1, MPI_INT, MPI_MIN, comm);
1493: MPI_Allreduce(&ierr, &maxCt, 1, MPI_INT, MPI_MAX, comm);
1494: name = "";
1495: }
1496: totm *= 0.5; totml *= 0.5; totr /= numProcs;
1497:
1498: if (maxCt != 0) {
1499: if (minCt != 0) ratCt = ((PetscLogDouble) maxCt)/minCt; else ratCt = 0.0;
1500: if (mint != 0.0) ratt = maxt/mint; else ratt = 0.0;
1501: if (minf != 0.0) ratf = maxf/minf; else ratf = 0.0;
1502: if (TotalTime != 0.0) fracTime = tott/TotalTime; else fracTime = 0.0;
1503: if (TotalFlops != 0.0) fracFlops = totf/TotalFlops; else fracFlops = 0.0;
1504: if (stageTime != 0.0) fracStageTime = tott/stageTime; else fracStageTime = 0.0;
1505: if (flops != 0.0) fracStageFlops = totf/flops; else fracStageFlops = 0.0;
1506: if (numMessages != 0.0) fracMess = totm/numMessages; else fracMess = 0.0;
1507: if (messageLength != 0.0) fracMessLen = totml/messageLength; else fracMessLen = 0.0;
1508: if (numReductions != 0.0) fracRed = totr/numReductions; else fracRed = 0.0;
1509: if (mess != 0.0) fracStageMess = totm/mess; else fracStageMess = 0.0;
1510: if (messLen != 0.0) fracStageMessLen = totml/messLen; else fracStageMessLen = 0.0;
1511: if (red != 0.0) fracStageRed = totr/red; else fracStageRed = 0.0;
1512: if (totm != 0.0) totml /= totm; else totml = 0.0;
1513: if (maxt != 0.0) flopr = totf/maxt; else flopr = 0.0;
1514: PetscFPrintf(comm, fd,
1515: "%-16s %7d%4.1f %5.4e%4.1f %3.2e%4.1f %2.1e %2.1e %2.1e%3.0f%3.0f%3.0f%3.0f%3.0f %3.0f%3.0f%3.0f%3.0f%3.0f %5.0fn",
1516: name, maxCt, ratCt, maxt, ratt, maxf, ratf, totm, totml, totr,
1517: 100.0*fracTime, 100.0*fracFlops, 100.0*fracMess, 100.0*fracMessLen, 100.0*fracRed,
1518: 100.0*fracStageTime, 100.0*fracStageFlops, 100.0*fracStageMess, 100.0*fracStageMessLen, 100.0*fracStageRed,
1519: flopr/1.0e6);
1520:
1521: }
1522: }
1523: }
1525: /* Memory usage and object creation */
1526: PetscFPrintf(comm, fd,
1527: "------------------------------------------------------------------------------------------------------------------------n");
1528:
1529: PetscFPrintf(comm, fd, "n");
1530: PetscFPrintf(comm, fd, "Memory usage is given in bytes:nn");
1532: /* Right now, only stages on the first processor are reported here, meaning only objects associated with
1533: the global communicator, or MPI_COMM_SELF for proc 1. We really should report global stats and then
1534: stats for stages local to processor sets.
1535: */
1536: /* We should figure out the longest object name here (now 20 characters) */
1537: PetscFPrintf(comm, fd, "Object Type Creations Destructions Memory Descendants' Mem.n");
1538: for(stage = 0; stage < numStages; stage++) {
1539: if (localStageUsed[stage] == PETSC_TRUE) {
1540: classInfo = stageLog->stageInfo[stage].classLog->classInfo;
1541: PetscFPrintf(comm, fd, "n--- Event Stage %d: %snn", stage, stageInfo[stage].name);
1542: for(oclass = 0; oclass < stageLog->stageInfo[stage].classLog->numClasses; oclass++) {
1543: if ((classInfo[oclass].creations > 0) || (classInfo[oclass].destructions > 0)) {
1544: PetscFPrintf(comm, fd, "%20s %5d %5d %9d %gn", stageLog->classLog->classInfo[oclass].name,
1545: classInfo[oclass].creations, classInfo[oclass].destructions, (int) classInfo[oclass].mem,
1546: classInfo[oclass].descMem);
1547:
1548: }
1549: }
1550: } else {
1551: PetscFPrintf(comm, fd, "n--- Event Stage %d: Unknownnn", stage);
1552: }
1553: }
1555: PetscFree(localStageUsed);
1556: PetscFree(stageUsed);
1557: PetscFree(localStageVisible);
1558: PetscFree(stageVisible);
1560: /* Information unrelated to this particular run */
1561: PetscFPrintf(comm, fd,
1562: "========================================================================================================================n");
1563:
1564: PetscTime(y);
1565: PetscTime(x);
1566: PetscTime(y); PetscTime(y); PetscTime(y); PetscTime(y); PetscTime(y);
1567: PetscTime(y); PetscTime(y); PetscTime(y); PetscTime(y); PetscTime(y);
1568: PetscFPrintf(comm,fd,"Average time to get PetscTime(): %gn", (y-x)/10.0);
1569: /* MPI information */
1570: if (numProcs > 1) {
1571: MPI_Status status;
1572: int tag;
1574: MPI_Barrier(comm);
1575: PetscTime(x);
1576: MPI_Barrier(comm);
1577: MPI_Barrier(comm);
1578: MPI_Barrier(comm);
1579: MPI_Barrier(comm);
1580: MPI_Barrier(comm);
1581: PetscTime(y);
1582: PetscFPrintf(comm, fd, "Average time for MPI_Barrier(): %gn", (y-x)/5.0);
1583: PetscCommGetNewTag(comm, &tag);
1584: MPI_Barrier(comm);
1585: if (rank) {
1586: MPI_Recv(0, 0, MPI_INT, rank-1, tag, comm, &status);
1587: MPI_Send(0, 0, MPI_INT, (rank+1)%numProcs, tag, comm);
1588: } else {
1589: PetscTime(x);
1590: MPI_Send(0, 0, MPI_INT, 1, tag, comm);
1591: MPI_Recv(0, 0, MPI_INT, numProcs-1, tag, comm, &status);
1592: PetscTime(y);
1593: PetscFPrintf(comm,fd,"Average time for zero size MPI_Send(): %gn", (y-x)/numProcs);
1594: }
1595: }
1596: /* Machine and compile information */
1597: #if defined(PETSC_USE_FORTRAN_KERNELS)
1598: PetscFPrintf(comm, fd, "Compiled with FORTRAN kernelsn");
1599: #else
1600: PetscFPrintf(comm, fd, "Compiled without FORTRAN kernelsn");
1601: #endif
1602: #if defined(PETSC_USE_MAT_SINGLE)
1603: PetscFPrintf(comm, fd, "Compiled with single precision matricesn");
1604: #else
1605: PetscFPrintf(comm, fd, "Compiled with double precision matrices (default)n");
1606: #endif
1607: PetscFPrintf(comm, fd, "sizeof(short) %d sizeof(int) %d sizeof(long) %d sizeof(void *) %d",
1608: (int) sizeof(short), (int) sizeof(int), (int) sizeof(long), (int) sizeof(void*));
1609:
1611: PetscFPrintf(comm, fd, "%s", petscmachineinfo);
1612: PetscFPrintf(comm, fd, "%s", petsccompilerinfo);
1613: PetscFPrintf(comm, fd, "%s", petsccompilerflagsinfo);
1614: PetscFPrintf(comm, fd, "%s", petsclinkerinfo);
1616: /* Cleanup */
1617: PetscFPrintf(comm, fd, "n");
1618: PetscFClose(comm, fd);
1619: return(0);
1620: }
1622: /*----------------------------------------------- Counter Functions -------------------------------------------------*/
1623: #undef __FUNCT__
1625: /*@C
1626: PetscGetFlops - Returns the number of flops used on this processor
1627: since the program began.
1629: Not Collective
1631: Output Parameter:
1632: flops - number of floating point operations
1634: Notes:
1635: A global counter logs all PETSc flop counts. The user can use
1636: PetscLogFlops() to increment this counter to include flops for the
1637: application code.
1639: PETSc automatically logs library events if the code has been
1640: compiled with -DPETSC_USE_LOG (which is the default), and -log,
1641: -log_summary, or -log_all are specified. PetscLogFlops() is
1642: intended for logging user flops to supplement this PETSc
1643: information.
1645: Level: intermediate
1647: .keywords: log, flops, floating point operations
1649: .seealso: PetscGetTime(), PetscLogFlops()
1650: @*/
1651: int PetscGetFlops(PetscLogDouble *flops)
1652: {
1654: *flops = _TotalFlops;
1655: return(0);
1656: }
1658: #undef __FUNCT__
1660: int PetscLogObjectState(PetscObject obj, const char format[], ...)
1661: {
1662: va_list Argp;
1665: if (logObjects == PETSC_FALSE) return(0);
1666: va_start(Argp, format);
1667: #if defined(PETSC_HAVE_VPRINTF_CHAR)
1668: vsprintf(objects[obj->id].info, format, (char *) Argp);
1669: #else
1670: vsprintf(objects[obj->id].info, format, Argp);
1671: #endif
1672: va_end(Argp);
1673: return(0);
1674: }
1676: #else /* end of -DPETSC_USE_LOG section */
1678: #undef __FUNCT__
1680: int PetscLogObjectState(PetscObject obj, const char format[], ...)
1681: {
1683: return(0);
1684: }
1686: #endif /* PETSC_USE_LOG*/
1688: #undef __FUNCT__
1690: /*@
1691: PetscGetTime - Returns the current time of day in seconds. This
1692: returns wall-clock time.
1694: Not Collective
1696: Output Parameter:
1697: . v - time counter
1699: Usage:
1700: .vb
1701: PetscLogDouble v1,v2,elapsed_time;
1702: PetscGetTime(&v1);CHKERR(ierr);
1703: .... perform some calculation ...
1704: PetscGetTime(&v2);CHKERR(ierr);
1705: elapsed_time = v2 - v1;
1706: .ve
1708: Notes:
1709: Since the PETSc libraries incorporate timing of phases and operations,
1710: PetscGetTime() is intended only for timing of application codes.
1711: The options database commands -log, -log_summary, and -log_all activate
1712: PETSc library timing. See the users manual for further details.
1714: Level: intermediate
1716: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogEventEnd(), PetscLogStagePush(),
1717: PetscLogStagePop(), PetscLogStageRegister(), PetscGetFlops()
1719: .keywords: get, time
1720: @*/
1721: int PetscGetTime(PetscLogDouble *t)
1722: {
1724: PetscTime(*t);
1725: return(0);
1726: }
1728: #undef __FUNCT__
1730: /*@
1731: PetscLogGetStageLog - This function returns the default stage logging object.
1733: Not collective
1735: Output Parameter:
1736: . stageLog - The default StageLog
1738: Level: beginner
1740: .keywords: log, stage
1741: .seealso: StageLogCreate()
1742: @*/
1743: int PetscLogGetStageLog(StageLog *stageLog)
1744: {
1747: *stageLog = _stageLog;
1748: return(0);
1749: }
1751: /*MC
1752: PetscLogFlops - Adds floating point operations to the global counter.
1754: Input Parameter:
1755: . f - flop counter
1757: Synopsis:
1758: void PetscLogFlops(int f)
1760: Usage:
1761: .vb
1762: int USER_EVENT;
1763: PetscLogEventRegister(&USER_EVENT,"User event");
1764: PetscLogEventBegin(USER_EVENT,0,0,0,0);
1765: [code segment to monitor]
1766: PetscLogFlops(user_flops)
1767: PetscLogEventEnd(USER_EVENT,0,0,0,0);
1768: .ve
1770: Notes:
1771: A global counter logs all PETSc flop counts. The user can use
1772: PetscLogFlops() to increment this counter to include flops for the
1773: application code.
1775: PETSc automatically logs library events if the code has been
1776: compiled with -DPETSC_USE_LOG (which is the default), and -log,
1777: -log_summary, or -log_all are specified. PetscLogFlops() is
1778: intended for logging user flops to supplement this PETSc
1779: information.
1781: Level: intermediate
1783: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogEventEnd(), PetscGetFlops()
1785: .keywords: log, flops, floating point operations
1786: M*/
1788: PetscTruth PetscPreLoadingUsed = PETSC_FALSE;
1789: PetscTruth PetscPreLoadingOn = PETSC_FALSE;
1791: /*MC
1792: PreLoadBegin - Begin a segment of code that may be preloaded (run twice)
1793: to get accurate timings
1795: Input Parameter:
1796: + flag - PETSC_TRUE to run twice, PETSC_FALSE to run once, may be overridden
1797: with command line option -preload true or -preload false
1798: - name - name of first stage (lines of code timed seperately with -log_summary) to
1799: be preloaded
1801: Synopsis:
1802: void PreLoadBegin(PetscTruth flag,char *name);
1804: Usage:
1805: .vb
1806: PreLoadBegin(PETSC_TRUE,"first stage);
1807: lines of code
1808: PreLoadStage("second stage");
1809: lines of code
1810: PreLoadEnd();
1811: .ve
1813: Level: intermediate
1815: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogEventEnd(), PreLoadEnd(), PreLoadStage()
1817: Concepts: preloading
1818: Concepts: timing^accurate
1819: Concepts: paging^eliminating effects of
1822: M*/
1824: /*MC
1825: PreLoadEnd - End a segment of code that may be preloaded (run twice)
1826: to get accurate timings
1828: Synopsis:
1829: void PreLoadEnd(void);
1831: Usage:
1832: .vb
1833: PreLoadBegin(PETSC_TRUE,"first stage);
1834: lines of code
1835: PreLoadStage("second stage");
1836: lines of code
1837: PreLoadEnd();
1838: .ve
1840: Level: intermediate
1842: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogEventEnd(), PreLoadBegin(), PreLoadStage()
1844: M*/
1846: /*MC
1847: PreLoadStage - Start a new segment of code to be timed seperately.
1848: to get accurate timings
1850: Synopsis:
1851: void PreLoadStage(char *name);
1853: Usage:
1854: .vb
1855: PreLoadBegin(PETSC_TRUE,"first stage);
1856: lines of code
1857: PreLoadStage("second stage");
1858: lines of code
1859: PreLoadEnd();
1860: .ve
1862: Level: intermediate
1864: .seealso: PetscLogEventRegister(), PetscLogEventBegin(), PetscLogEventEnd(), PreLoadBegin(), PreLoadEnd()
1866: M*/
1868: /*----------------------------------------------- Stack Functions ---------------------------------------------------*/
1869: #undef __FUNCT__
1871: /*@C
1872: StackDestroy - This function destroys a stack.
1874: Not Collective
1876: Input Parameter:
1877: . stack - The stack
1879: Level: beginner
1881: .keywords: log, stack, destroy
1882: .seealso: StackCreate(), StackEmpty(), StackPush(), StackPop(), StackTop()
1883: @*/
1884: int StackDestroy(IntStack stack)
1885: {
1889: PetscFree(stack->stack);
1890: PetscFree(stack);
1891: return(0);
1892: }
1894: #undef __FUNCT__
1896: /*@C
1897: StackEmpty - This function determines whether any items have been pushed.
1899: Not Collective
1901: Input Parameter:
1902: . stack - The stack
1904: Output Parameter:
1905: . empty - PETSC_TRUE if the stack is empty
1907: Level: intermediate
1909: .keywords: log, stack, empty
1910: .seealso: StackCreate(), StackDestroy(), StackPush(), StackPop(), StackTop()
1911: @*/
1912: int StackEmpty(IntStack stack, PetscTruth *empty)
1913: {
1916: if (stack->top == -1) {
1917: *empty = PETSC_TRUE;
1918: } else {
1919: *empty = PETSC_FALSE;
1920: }
1921: return(0);
1922: }
1924: #undef __FUNCT__
1926: /*@C
1927: StackTop - This function returns the top of the stack.
1929: Not Collective
1931: Input Parameter:
1932: . stack - The stack
1934: Output Parameter:
1935: . top - The integer on top of the stack
1937: Level: intermediate
1939: .keywords: log, stack, top
1940: .seealso: StackCreate(), StackDestroy(), StackEmpty(), StackPush(), StackPop()
1941: @*/
1942: int StackTop(IntStack stack, int *top)
1943: {
1946: *top = stack->stack[stack->top];
1947: return(0);
1948: }
1950: #undef __FUNCT__
1952: /*@C
1953: StackPush - This function pushes an integer on the stack.
1955: Not Collective
1957: Input Parameters:
1958: + stack - The stack
1959: - item - The integer to push
1961: Level: intermediate
1963: .keywords: log, stack, push
1964: .seealso: StackCreate(), StackDestroy(), StackEmpty(), StackPop(), StackTop()
1965: @*/
1966: int StackPush(IntStack stack, int item)
1967: {
1968: int *array;
1969: int ierr;
1972: stack->top++;
1973: if (stack->top >= stack->max) {
1974: PetscMalloc(stack->max*2 * sizeof(int), &array);
1975: PetscMemcpy(array, stack->stack, stack->max * sizeof(int));
1976: PetscFree(stack->stack);
1977: stack->stack = array;
1978: stack->max *= 2;
1979: }
1980: stack->stack[stack->top] = item;
1981: return(0);
1982: }
1984: #undef __FUNCT__
1986: /*@C
1987: StackPop - This function pops an integer from the stack.
1989: Not Collective
1991: Input Parameter:
1992: . stack - The stack
1994: Output Parameter:
1995: . item - The integer popped
1997: Level: intermediate
1999: .keywords: log, stack, pop
2000: .seealso: StackCreate(), StackDestroy(), StackEmpty(), StackPush(), StackTop()
2001: @*/
2002: int StackPop(IntStack stack, int *item)
2003: {
2006: if (stack->top == -1) SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Stack is empty");
2007: *item = stack->stack[stack->top--];
2008: return(0);
2009: }
2011: #undef __FUNCT__
2013: /*@C
2014: StackCreate - This function creates a stack.
2016: Not Collective
2018: Output Parameter:
2019: . stack - The stack
2021: Level: beginner
2023: .keywords: log, stack, pop
2024: .seealso: StackDestroy(), StackEmpty(), StackPush(), StackPop(), StackTop()
2025: @*/
2026: int StackCreate(IntStack *stack)
2027: {
2028: IntStack s;
2029: int ierr;
2033: PetscNew(struct _IntStack, &s);
2034: s->top = -1;
2035: s->max = 128;
2036: PetscMalloc(s->max * sizeof(int), &s->stack);
2037: PetscMemzero(s->stack, s->max * sizeof(int));
2038: *stack = s;
2039: return(0);
2040: }