Actual source code: eventLog.c
1: #define PETSC_DLL
3: #include petsc.h
4: #include petsctime.h
5: #include ../src/sys/plog/plog.h
7: /* Variables for the tracing logger */
14: /*----------------------------------------------- Creation Functions -------------------------------------------------*/
15: /* Note: these functions do not have prototypes in a public directory, so they are considered "internal" and not exported. */
19: /*@C
20: EventRegLogCreate - This creates a EventRegLog object.
22: Not collective
24: Input Parameter:
25: . eventLog - The EventRegLog
27: Level: beginner
29: .keywords: log, event, create
30: .seealso: EventRegLogDestroy(), StageLogCreate()
31: @*/
32: PetscErrorCode EventRegLogCreate(EventRegLog *eventLog)
33: {
34: EventRegLog l;
38: PetscNew(struct _n_EventRegLog, &l);
39: l->numEvents = 0;
40: l->maxEvents = 100;
41: PetscMalloc(l->maxEvents * sizeof(EventRegInfo), &l->eventInfo);
42: *eventLog = l;
43: return(0);
44: }
48: /*@C
49: EventRegLogDestroy - This destroys a EventRegLog object.
51: Not collective
53: Input Paramter:
54: . eventLog - The EventRegLog
56: Level: beginner
58: .keywords: log, event, destroy
59: .seealso: EventRegLogCreate()
60: @*/
61: PetscErrorCode EventRegLogDestroy(EventRegLog eventLog)
62: {
63: int e;
67: for(e = 0; e < eventLog->numEvents; e++) {
68: PetscFree(eventLog->eventInfo[e].name);
69: }
70: PetscFree(eventLog->eventInfo);
71: PetscFree(eventLog);
72: return(0);
73: }
77: /*@C
78: EventPerfLogCreate - This creates a EventPerfLog object.
80: Not collective
82: Input Parameter:
83: . eventLog - The EventPerfLog
85: Level: beginner
87: .keywords: log, event, create
88: .seealso: EventPerfLogDestroy(), StageLogCreate()
89: @*/
90: PetscErrorCode EventPerfLogCreate(EventPerfLog *eventLog)
91: {
92: EventPerfLog l;
96: PetscNew(struct _n_EventPerfLog, &l);
97: l->numEvents = 0;
98: l->maxEvents = 100;
99: PetscMalloc(l->maxEvents * sizeof(EventPerfInfo), &l->eventInfo);
100: *eventLog = l;
101: return(0);
102: }
106: /*@C
107: EventPerfLogDestroy - This destroys a EventPerfLog object.
109: Not collective
111: Input Paramter:
112: . eventLog - The EventPerfLog
114: Level: beginner
116: .keywords: log, event, destroy
117: .seealso: EventPerfLogCreate()
118: @*/
119: PetscErrorCode EventPerfLogDestroy(EventPerfLog eventLog)
120: {
124: PetscFree(eventLog->eventInfo);
125: PetscFree(eventLog);
126: return(0);
127: }
129: /*------------------------------------------------ General Functions -------------------------------------------------*/
132: /*@C
133: EventPerfInfoClear - This clears a EventPerfInfo object.
135: Not collective
137: Input Paramter:
138: . eventInfo - The EventPerfInfo
140: Level: beginner
142: .keywords: log, event, destroy
143: .seealso: EventPerfLogCreate()
144: @*/
145: PetscErrorCode EventPerfInfoClear(EventPerfInfo *eventInfo)
146: {
148: eventInfo->id = -1;
149: eventInfo->active = PETSC_TRUE;
150: eventInfo->visible = PETSC_TRUE;
151: eventInfo->depth = 0;
152: eventInfo->count = 0;
153: eventInfo->flops = 0.0;
154: eventInfo->time = 0.0;
155: eventInfo->numMessages = 0.0;
156: eventInfo->messageLength = 0.0;
157: eventInfo->numReductions = 0.0;
158: return(0);
159: }
163: /*@C
164: EventPerfInfoCopy - Copy the activity and visibility data in eventInfo to outInfo
166: Not collective
168: Input Paramter:
169: . eventInfo - The input EventPerfInfo
171: Output Paramter:
172: . outInfo - The output EventPerfInfo
174: Level: beginner
176: .keywords: log, event, copy
177: .seealso: EventPerfInfoClear()
178: @*/
179: PetscErrorCode EventPerfInfoCopy(EventPerfInfo *eventInfo, EventPerfInfo *outInfo)
180: {
182: outInfo->id = eventInfo->id;
183: outInfo->active = eventInfo->active;
184: outInfo->visible = eventInfo->visible;
185: return(0);
186: }
190: /*@C
191: EventPerfLogEnsureSize - This ensures that a EventPerfLog is at least of a certain size.
193: Not collective
195: Input Paramters:
196: + eventLog - The EventPerfLog
197: - size - The size
199: Level: intermediate
201: .keywords: log, event, size, ensure
202: .seealso: EventPerfLogCreate()
203: @*/
204: PetscErrorCode EventPerfLogEnsureSize(EventPerfLog eventLog, int size)
205: {
206: EventPerfInfo *eventInfo;
210: while(size > eventLog->maxEvents) {
211: PetscMalloc(eventLog->maxEvents*2 * sizeof(EventPerfInfo), &eventInfo);
212: PetscMemcpy(eventInfo, eventLog->eventInfo, eventLog->maxEvents * sizeof(EventPerfInfo));
213: PetscFree(eventLog->eventInfo);
214: eventLog->eventInfo = eventInfo;
215: eventLog->maxEvents *= 2;
216: }
217: while(eventLog->numEvents < size) {
218: EventPerfInfoClear(&eventLog->eventInfo[eventLog->numEvents++]);
219: }
220: return(0);
221: }
223: /*--------------------------------------------- Registration Functions ----------------------------------------------*/
226: /*@C
227: EventRegLogRegister - Registers an event for logging operations in an application code.
229: Not Collective
231: Input Parameters:
232: + eventLog - The EventLog
233: . ename - The name associated with the event
234: - cookie - The cookie associated to the class for this event
236: Output Parameter:
237: . event - The event
239: Example of Usage:
240: .vb
241: int USER_EVENT;
242: int user_event_flops;
243: PetscLogEventRegister("User event name",0,&USER_EVENT);
244: PetscLogEventBegin(USER_EVENT,0,0,0,0);
245: [code segment to monitor]
246: PetscLogFlops(user_event_flops);
247: PetscLogEventEnd(USER_EVENT,0,0,0,0);
248: .ve
250: Notes:
251: PETSc automatically logs library events if the code has been
252: compiled with -DPETSC_USE_LOG (which is the default) and -log,
253: -log_summary, or -log_all are specified. PetscLogEventRegister() is
254: intended for logging user events to supplement this PETSc
255: information.
257: PETSc can gather data for use with the utilities Upshot/Nupshot
258: (part of the MPICH distribution). If PETSc has been compiled
259: with flag -DPETSC_HAVE_MPE (MPE is an additional utility within
260: MPICH), the user can employ another command line option, -log_mpe,
261: to create a logfile, "mpe.log", which can be visualized
262: Upshot/Nupshot.
264: Level: intermediate
266: .keywords: log, event, register
267: .seealso: PetscLogEventBegin(), PetscLogEventEnd(), PetscLogFlops(), PetscLogEventMPEActivate(), PetscLogEventMPEDeactivate(),
268: EventLogActivate(), EventLogDeactivate()
269: @*/
270: PetscErrorCode EventRegLogRegister(EventRegLog eventLog, const char ename[], PetscCookie cookie, PetscLogEvent *event)
271: {
272: EventRegInfo *eventInfo;
273: char *str;
274: int e;
280: /* Should check cookie I think */
281: e = eventLog->numEvents++;
282: if (eventLog->numEvents > eventLog->maxEvents) {
283: PetscMalloc(eventLog->maxEvents*2 * sizeof(EventRegInfo), &eventInfo);
284: PetscMemcpy(eventInfo, eventLog->eventInfo, eventLog->maxEvents * sizeof(EventRegInfo));
285: PetscFree(eventLog->eventInfo);
286: eventLog->eventInfo = eventInfo;
287: eventLog->maxEvents *= 2;
288: }
289: PetscStrallocpy(ename, &str);
290: eventLog->eventInfo[e].name = str;
291: eventLog->eventInfo[e].cookie = cookie;
292: #if defined(PETSC_HAVE_MPE)
293: if (UseMPE) {
294: const char *color;
295: PetscMPIInt rank;
296: int beginID, endID;
298: beginID = MPE_Log_get_event_number();
299: endID = MPE_Log_get_event_number();
300: eventLog->eventInfo[e].mpe_id_begin = beginID;
301: eventLog->eventInfo[e].mpe_id_end = endID;
302: MPI_Comm_rank(PETSC_COMM_WORLD, &rank);
303: if (!rank) {
304: PetscLogGetRGBColor(&color);
305: MPE_Describe_state(beginID, endID, str, (char*)color);
306: }
307: }
308: #endif
309: *event = e;
310: return(0);
311: }
313: /*---------------------------------------------- Activation Functions -----------------------------------------------*/
316: /*@C
317: EventPerfLogActivate - Indicates that a particular event should be logged.
319: Not Collective
321: Input Parameters:
322: + eventLog - The EventPerfLog
323: - event - The event
325: Usage:
326: .vb
327: EventPerfLogDeactivate(log, VEC_SetValues);
328: [code where you do not want to log VecSetValues()]
329: EventPerfLogActivate(log, VEC_SetValues);
330: [code where you do want to log VecSetValues()]
331: .ve
333: Note:
334: The event may be either a pre-defined PETSc event (found in
335: include/petsclog.h) or an event number obtained with EventRegLogRegister().
337: Level: advanced
339: .keywords: log, event, activate
340: .seealso: PetscLogEventMPEDeactivate(), PetscLogEventMPEActivate(), EventPerfLogDeactivate()
341: @*/
342: PetscErrorCode EventPerfLogActivate(EventPerfLog eventLog, PetscLogEvent event)
343: {
345: eventLog->eventInfo[event].active = PETSC_TRUE;
346: return(0);
347: }
351: /*@C
352: EventPerfLogDeactivate - Indicates that a particular event should not be logged.
354: Not Collective
356: Input Parameters:
357: + eventLog - The EventPerfLog
358: - event - The event
360: Usage:
361: .vb
362: EventPerfLogDeactivate(log, VEC_SetValues);
363: [code where you do not want to log VecSetValues()]
364: EventPerfLogActivate(log, VEC_SetValues);
365: [code where you do want to log VecSetValues()]
366: .ve
368: Note:
369: The event may be either a pre-defined PETSc event (found in
370: include/petsclog.h) or an event number obtained with EventRegLogRegister().
372: Level: advanced
374: .keywords: log, event, activate
375: .seealso: PetscLogEventMPEDeactivate(), PetscLogEventMPEActivate(), EventPerfLogActivate()
376: @*/
377: PetscErrorCode EventPerfLogDeactivate(EventPerfLog eventLog, PetscLogEvent event)
378: {
380: eventLog->eventInfo[event].active = PETSC_FALSE;
381: return(0);
382: }
386: /*@C
387: EventPerfLogActivateClass - Activates event logging for a PETSc object class.
389: Not Collective
391: Input Parameters:
392: + eventLog - The EventPerfLog
393: . eventRegLog - The EventRegLog
394: - cookie - The class id, for example MAT_COOKIE, SNES_COOKIE,
396: Level: developer
398: .seealso: EventPerfLogDeactivateClass(), EventPerfLogActivate(), EventPerfLogDeactivate()
399: @*/
400: PetscErrorCode EventPerfLogActivateClass(EventPerfLog eventLog, EventRegLog eventRegLog, PetscCookie cookie)
401: {
402: int e;
405: for(e = 0; e < eventLog->numEvents; e++) {
406: int c = eventRegLog->eventInfo[e].cookie;
408: if (c == cookie) eventLog->eventInfo[e].active = PETSC_TRUE;
409: }
410: return(0);
411: }
415: /*@C
416: EventPerfLogDeactivateClass - Deactivates event logging for a PETSc object class.
418: Not Collective
420: Input Parameters:
421: + eventLog - The EventPerfLog
422: . eventRegLog - The EventRegLog
423: - cookie - The class id, for example MAT_COOKIE, SNES_COOKIE,
425: Level: developer
427: .seealso: EventPerfLogDeactivateClass(), EventPerfLogDeactivate(), EventPerfLogActivate()
428: @*/
429: PetscErrorCode EventPerfLogDeactivateClass(EventPerfLog eventLog, EventRegLog eventRegLog, PetscCookie cookie)
430: {
431: int e;
434: for(e = 0; e < eventLog->numEvents; e++) {
435: int c = eventRegLog->eventInfo[e].cookie;
437: if (c == cookie) eventLog->eventInfo[e].active = PETSC_FALSE;
438: }
439: return(0);
440: }
442: /*------------------------------------------------ Query Functions --------------------------------------------------*/
445: /*@
446: EventRegLogGetEvent - This function returns the event id given the event name.
448: Not Collective
450: Input Parameters:
451: + eventLog - The EventRegLog
452: - name - The stage name
454: Output Parameter:
455: . event - The event id
457: Level: intermediate
459: .keywords: log, stage
460: .seealso: EventRegLogRegister()
461: @*/
462: PetscErrorCode EventRegLogGetEvent(EventRegLog eventLog, const char name[], PetscLogEvent *event)
463: {
464: PetscTruth match;
465: int e;
471: *event = -1;
472: for(e = 0; e < eventLog->numEvents; e++) {
473: PetscStrcasecmp(eventLog->eventInfo[e].name, name, &match);
474: if (match) break;
475: }
476: if (e == eventLog->numEvents) SETERRQ1(PETSC_ERR_ARG_WRONG, "No event named %s", name);
477: *event = e;
478: return(0);
479: }
483: /*@C
484: EventPerfLogSetVisible - This function determines whether an event is printed during PetscLogPrintSummary()
486: Not Collective
488: Input Parameters:
489: + eventLog - The EventPerfLog
490: . event - The event to log
491: - isVisible - The visibility flag, PETSC_TRUE for printing, otherwise PETSC_FALSE (default is PETSC_TRUE)
493: Database Options:
494: . -log_summary - Activates log summary
496: Level: intermediate
498: .keywords: log, visible, event
499: .seealso: EventPerfLogGetVisible(), EventRegLogRegister(), StageLogGetEventLog()
500: @*/
501: PetscErrorCode EventPerfLogSetVisible(EventPerfLog eventLog, PetscLogEvent event, PetscTruth isVisible)
502: {
504: eventLog->eventInfo[event].visible = isVisible;
505: return(0);
506: }
510: /*@C
511: EventPerfLogGetVisible - This function returns whether an event is printed during PetscLogPrintSummary()
513: Not Collective
515: Input Parameters:
516: + eventLog - The EventPerfLog
517: - event - The event id to log
519: Output Parameter:
520: . isVisible - The visibility flag, PETSC_TRUE for printing, otherwise PETSC_FALSE (default is PETSC_TRUE)
522: Database Options:
523: . -log_summary - Activates log summary
525: Level: intermediate
527: .keywords: log, visible, event
528: .seealso: EventPerfLogSetVisible(), EventRegLogRegister(), StageLogGetEventLog()
529: @*/
530: PetscErrorCode EventPerfLogGetVisible(EventPerfLog eventLog, PetscLogEvent event, PetscTruth *isVisible)
531: {
534: *isVisible = eventLog->eventInfo[event].visible;
535: return(0);
536: }
538: /*------------------------------------------------ Action Functions -------------------------------------------------*/
541: PetscErrorCode PetscLogEventBeginDefault(PetscLogEvent event, int t, PetscObject o1, PetscObject o2, PetscObject o3, PetscObject o4)
542: {
543: StageLog stageLog;
544: EventPerfLog eventLog;
545: int stage;
549: PetscLogGetStageLog(&stageLog);
550: StageLogGetCurrent(stageLog, &stage);
551: StageLogGetEventPerfLog(stageLog, stage, &eventLog);
552: /* Check for double counting */
553: eventLog->eventInfo[event].depth++;
554: if (eventLog->eventInfo[event].depth > 1) return(0);
555: /* Log performance info */
556: eventLog->eventInfo[event].count++;
557: PetscTimeSubtract(eventLog->eventInfo[event].time);
558: eventLog->eventInfo[event].flops -= _TotalFlops;
559: eventLog->eventInfo[event].numMessages -= irecv_ct + isend_ct + recv_ct + send_ct;
560: eventLog->eventInfo[event].messageLength -= irecv_len + isend_len + recv_len + send_len;
561: eventLog->eventInfo[event].numReductions -= allreduce_ct;
562: return(0);
563: }
567: PetscErrorCode PetscLogEventEndDefault(PetscLogEvent event, int t, PetscObject o1, PetscObject o2, PetscObject o3, PetscObject o4)
568: {
569: StageLog stageLog;
570: EventPerfLog eventLog;
571: int stage;
575: PetscLogGetStageLog(&stageLog);
576: StageLogGetCurrent(stageLog, &stage);
577: StageLogGetEventPerfLog(stageLog, stage, &eventLog);
578: /* Check for double counting */
579: eventLog->eventInfo[event].depth--;
580: if (eventLog->eventInfo[event].depth > 0) {
581: return(0);
582: } else if (eventLog->eventInfo[event].depth < 0) {
583: SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Logging event had unbalanced begin/end pairs");
584: }
585: /* Log performance info */
586: PetscTimeAdd(eventLog->eventInfo[event].time);
587: eventLog->eventInfo[event].flops += _TotalFlops;
588: eventLog->eventInfo[event].numMessages += irecv_ct + isend_ct + recv_ct + send_ct;
589: eventLog->eventInfo[event].messageLength += irecv_len + isend_len + recv_len + send_len;
590: eventLog->eventInfo[event].numReductions += allreduce_ct;
591: return(0);
592: }
596: PetscErrorCode PetscLogEventBeginComplete(PetscLogEvent event, int t, PetscObject o1, PetscObject o2, PetscObject o3, PetscObject o4)
597: {
598: StageLog stageLog;
599: EventRegLog eventRegLog;
600: EventPerfLog eventPerfLog;
601: Action *tmpAction;
602: PetscLogDouble start, end;
603: PetscLogDouble curTime;
604: int stage;
608: /* Dynamically enlarge logging structures */
609: if (numActions >= maxActions) {
610: PetscTime(start);
611: PetscMalloc(maxActions*2 * sizeof(Action), &tmpAction);
612: PetscMemcpy(tmpAction, actions, maxActions * sizeof(Action));
613: PetscFree(actions);
614: actions = tmpAction;
615: maxActions *= 2;
616: PetscTime(end);
617: BaseTime += (end - start);
618: }
619: /* Record the event */
620: PetscLogGetStageLog(&stageLog);
621: StageLogGetCurrent(stageLog, &stage);
622: StageLogGetEventRegLog(stageLog, &eventRegLog);
623: StageLogGetEventPerfLog(stageLog, stage, &eventPerfLog);
624: PetscTime(curTime);
625: if (logActions) {
626: actions[numActions].time = curTime - BaseTime;
627: actions[numActions].action = ACTIONBEGIN;
628: actions[numActions].event = event;
629: actions[numActions].cookie = eventRegLog->eventInfo[event].cookie;
630: if (o1) actions[numActions].id1 = o1->id; else actions[numActions].id1 = -1;
631: if (o2) actions[numActions].id2 = o2->id; else actions[numActions].id2 = -1;
632: if (o3) actions[numActions].id3 = o3->id; else actions[numActions].id3 = -1;
633: actions[numActions].flops = _TotalFlops;
634: PetscMallocGetCurrentUsage(&actions[numActions].mem);
635: PetscMallocGetMaximumUsage(&actions[numActions].maxmem);
636: numActions++;
637: }
638: /* Check for double counting */
639: eventPerfLog->eventInfo[event].depth++;
640: if (eventPerfLog->eventInfo[event].depth > 1) return(0);
641: /* Log the performance info */
642: eventPerfLog->eventInfo[event].count++;
643: eventPerfLog->eventInfo[event].time -= curTime;
644: eventPerfLog->eventInfo[event].flops -= _TotalFlops;
645: eventPerfLog->eventInfo[event].numMessages -= irecv_ct + isend_ct + recv_ct + send_ct;
646: eventPerfLog->eventInfo[event].messageLength -= irecv_len + isend_len + recv_len + send_len;
647: eventPerfLog->eventInfo[event].numReductions -= allreduce_ct;
648: return(0);
649: }
653: PetscErrorCode PetscLogEventEndComplete(PetscLogEvent event, int t, PetscObject o1, PetscObject o2, PetscObject o3, PetscObject o4)
654: {
655: StageLog stageLog;
656: EventRegLog eventRegLog;
657: EventPerfLog eventPerfLog;
658: Action *tmpAction;
659: PetscLogDouble start, end;
660: PetscLogDouble curTime;
661: int stage;
665: /* Dynamically enlarge logging structures */
666: if (numActions >= maxActions) {
667: PetscTime(start);
668: PetscMalloc(maxActions*2 * sizeof(Action), &tmpAction);
669: PetscMemcpy(tmpAction, actions, maxActions * sizeof(Action));
670: PetscFree(actions);
671: actions = tmpAction;
672: maxActions *= 2;
673: PetscTime(end);
674: BaseTime += (end - start);
675: }
676: /* Record the event */
677: PetscLogGetStageLog(&stageLog);
678: StageLogGetCurrent(stageLog, &stage);
679: StageLogGetEventRegLog(stageLog, &eventRegLog);
680: StageLogGetEventPerfLog(stageLog, stage, &eventPerfLog);
681: PetscTime(curTime);
682: if (logActions) {
683: actions[numActions].time = curTime - BaseTime;
684: actions[numActions].action = ACTIONEND;
685: actions[numActions].event = event;
686: actions[numActions].cookie = eventRegLog->eventInfo[event].cookie;
687: if (o1) actions[numActions].id1 = o1->id; else actions[numActions].id1 = -1;
688: if (o2) actions[numActions].id2 = o2->id; else actions[numActions].id2 = -1;
689: if (o3) actions[numActions].id3 = o3->id; else actions[numActions].id3 = -1;
690: actions[numActions].flops = _TotalFlops;
691: PetscMallocGetCurrentUsage(&actions[numActions].mem);
692: PetscMallocGetMaximumUsage(&actions[numActions].maxmem);
693: numActions++;
694: }
695: /* Check for double counting */
696: eventPerfLog->eventInfo[event].depth--;
697: if (eventPerfLog->eventInfo[event].depth > 0) {
698: return(0);
699: } else if (eventPerfLog->eventInfo[event].depth < 0) {
700: SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Logging event had unbalanced begin/end pairs");
701: }
702: /* Log the performance info */
703: eventPerfLog->eventInfo[event].count++;
704: eventPerfLog->eventInfo[event].time += curTime;
705: eventPerfLog->eventInfo[event].flops += _TotalFlops;
706: eventPerfLog->eventInfo[event].numMessages += irecv_ct + isend_ct + recv_ct + send_ct;
707: eventPerfLog->eventInfo[event].messageLength += irecv_len + isend_len + recv_len + send_len;
708: eventPerfLog->eventInfo[event].numReductions += allreduce_ct;
709: return(0);
710: }
714: PetscErrorCode PetscLogEventBeginTrace(PetscLogEvent event, int t, PetscObject o1, PetscObject o2, PetscObject o3, PetscObject o4)
715: {
716: StageLog stageLog;
717: EventRegLog eventRegLog;
718: EventPerfLog eventPerfLog;
719: PetscLogDouble cur_time;
720: PetscMPIInt rank;
721: int stage,err;
725: if (!tracetime) {PetscTime(tracetime);}
727: MPI_Comm_rank(PETSC_COMM_WORLD, &rank);
728: PetscLogGetStageLog(&stageLog);
729: StageLogGetCurrent(stageLog, &stage);
730: StageLogGetEventRegLog(stageLog, &eventRegLog);
731: StageLogGetEventPerfLog(stageLog, stage, &eventPerfLog);
732: /* Check for double counting */
733: eventPerfLog->eventInfo[event].depth++;
734: tracelevel++;
735: if (eventPerfLog->eventInfo[event].depth > 1) return(0);
736: /* Log performance info */
737: PetscStrncpy(tracespace, traceblanks, 2*tracelevel);
738: tracespace[2*tracelevel] = 0;
739: PetscTime(cur_time);
740: PetscFPrintf(PETSC_COMM_SELF,tracefile, "%s[%d] %g Event begin: %s\n", tracespace, rank, cur_time-tracetime, eventRegLog->eventInfo[event].name);
741: err = fflush(tracefile);
742: if (err) SETERRQ(PETSC_ERR_SYS,"fflush() failed on file");
744: return(0);
745: }
749: PetscErrorCode PetscLogEventEndTrace(PetscLogEvent event,int t,PetscObject o1,PetscObject o2,PetscObject o3,PetscObject o4)
750: {
751: StageLog stageLog;
752: EventRegLog eventRegLog;
753: EventPerfLog eventPerfLog;
754: PetscLogDouble cur_time;
755: int stage,err;
756: PetscMPIInt rank;
760: tracelevel--;
761: MPI_Comm_rank(PETSC_COMM_WORLD, &rank);
762: PetscLogGetStageLog(&stageLog);
763: StageLogGetCurrent(stageLog, &stage);
764: StageLogGetEventRegLog(stageLog, &eventRegLog);
765: StageLogGetEventPerfLog(stageLog, stage, &eventPerfLog);
766: /* Check for double counting */
767: eventPerfLog->eventInfo[event].depth--;
768: if (eventPerfLog->eventInfo[event].depth > 0) {
769: return(0);
770: } else if (eventPerfLog->eventInfo[event].depth < 0 || tracelevel < 0) {
771: SETERRQ(PETSC_ERR_ARG_WRONGSTATE, "Logging event had unbalanced begin/end pairs");
772: }
773: /* Log performance info */
774: PetscStrncpy(tracespace, traceblanks, 2*tracelevel);
775: tracespace[2*tracelevel] = 0;
776: PetscTime(cur_time);
777: PetscFPrintf(PETSC_COMM_SELF,tracefile, "%s[%d] %g Event end: %s\n", tracespace, rank, cur_time-tracetime, eventRegLog->eventInfo[event].name);
778: err = fflush(tracefile);
779: if (err) SETERRQ(PETSC_ERR_SYS,"fflush() failed on file");
780: return(0);
781: }