HDK
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
UT_Performance.h
Go to the documentation of this file.
1 /*
2  * PROPRIETARY INFORMATION. This software is proprietary to
3  * Side Effects Software Inc., and is not to be reproduced,
4  * transmitted, or disclosed in any way without written permission.
5  *
6  * NAME: UT_Performance.h ( UT Library, C++)
7  *
8  * COMMENTS:
9  *
10  * The performance monitor.
11  */
12 
13 #ifndef __UT_Performance__
14 #define __UT_Performance__
15 
16 #include "UT_API.h"
17 
18 #include "UT_Condition.h"
19 #include "UT_Lock.h"
20 #include "UT_Map.h"
21 #include "UT_PerfMonProfile.h"
22 #include "UT_PerfMonTimedEvent.h"
23 #include "UT_PerfMonTypes.h"
24 #include "UT_Color.h"
25 #include "UT_Ramp.h"
26 #include "UT_ThreadSpecificValue.h"
27 #include "UT_DirUtil.h"
28 #include <SYS/SYS_AtomicInt.h>
29 
30 #include <tbb/spin_rw_mutex.h>
31 
32 #define UT_PERFMON_INVALID_ID -1
33 #define UT_PERFMON_INTERNAL_TASKS_LABEL "Internal Tasks"
34 
36 {
47 };
48 
51 
52 typedef void (*UT_PerfMonEventCB)
53  (void *callee, const UT_PerfMonEvent *event);
54 
55 class OP_Node;
56 class SIM_Solver;
57 class UT_NetSocket;
58 class UT_PerfMonEvent;
59 class UT_PerfMonProfile;
60 class UT_PerfMonStats;
61 class ut_PerfMonProfileInterest;
62 class ut_PerfMonEventInterest;
63 class UT_WorkBuffer;
64 
66 {
67 public:
69  virtual ~UT_Performance();
70 
71  /// ********************************************************
72  /// EVENT MANAGEMENT
73  /// ********************************************************
74 
75  /// Start a generic timed event or memory event. For custom monitoring.
76  /// Check if there are more specific startTimed*() and startMemory*()
77  /// methods below that you can call instead before using these methods.
78  ///
79  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
80  /// was not recorded (i.e. no profile has been started).
81  /// If `auto_nest_events` is true, then any other events
82  /// that are started and stopped before this event is stopped
83  /// will be treated as dependencies on this event.
84  int startTimedEvent(
85  const char *event,
86  const char *object,
87  bool auto_nest_events=true);
88  int startMemoryEvent(
89  const char *object,
90  bool auto_nest_events=true);
91 
92  /// Start a timed event or memory event for OP cooks.
93  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
94  /// was not recorded (i.e. no profile has been started).
95  int startTimedCookEvent(
96  int node_id,
97  const char *cook_event_name=NULL);
98  int startMemoryCookEvent(
99  int node_id,
100  const char *cook_event_name=NULL);
101 
102  /// Add a new timed cook event.
103  /// Instead of starting and stopping the event,
104  /// immediately set the event's run time to `time`. The event is
105  /// added to any interested profiles and observers.
106  void addTimedCookEvent(
107  int node_id,
108  fpreal time,
109  const char *cook_event_name=NULL);
110 
111  /// Start a timed event or memory event for PDG work item cooks.
112  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
113  /// was not recorded (i.e. no profile has been started).
114  int startTimedPDGEvent(
115  const char *path,
116  const char *pdg_event_name=NULL);
117  int startMemoryPDGEvent(
118  const char *path,
119  const char *pdg_event_name=NULL);
120 
121  /// Add a new timed cook event.
122  /// Instead of starting and stopping the event,
123  /// immediately set the event's run time to `time`. The event is
124  /// added to any interested profiles and observers.
125  void addTimedPDGEvent(
126  const char *path,
127  fpreal time,
128  const char *pdg_event_name=NULL);
129 
130 
131  /// Start a timed event or memory event for DOP solves.
132  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
133  /// was not recorded (i.e. no profile has been started).
134  int startTimedSolveEvent(
135  const SIM_Solver *solver,
136  const char *solver_event_name=NULL);
137  int startMemorySolveEvent(
138  const SIM_Solver *solver,
139  const char *solver_event_name=NULL);
140 
141  /// Start a timed event or memory event for a generic draw event.
142  /// Set `is_gpu_draw` to true if the draw event occurred on the GPU.
143  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
144  /// was not recorded (i.e. no profile has been started).
145  int startTimedDrawEvent(
146  const char *object,
147  const char *draw_event_name,
148  bool is_gpu_draw=false);
149  int startMemoryDrawEvent(
150  const char *object,
151  const char *draw_event_name,
152  bool is_gpu_draw=false);
153 
154  /// Start a timed event or memory event for viewport draws.
155  /// Set `is_gpu_draw` to true if the draw event occurred on the GPU.
156  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
157  /// was not recorded (i.e. no profile has been started).
158  int startTimedViewportDrawEvent(
159  const char *viewport_name,
160  const char *draw_event_name,
161  UT_PerfMonViewportType viewport_type,
162  bool is_gpu_draw=false);
163  int startMemoryViewportDrawEvent(
164  const char *viewport_name,
165  const char *draw_event_name,
166  UT_PerfMonViewportType viewport_type,
167  bool is_gpu_draw=false);
168 
169  /// Add a new timed draw event.
170  /// Instead of starting and stopping the event,
171  /// immediately set the event's run time to `time`. The event is
172  /// added to any interested profiles and observers.
173  void addTimedDrawEvent(
174  const char *object,
175  const char *draw_event_name,
176  fpreal time,
177  bool is_gpu_draw=false);
178 
179  /// Add a new timed viewport draw event.
180  /// Instead of starting and stopping the event,
181  /// immediately set the event's run time to `time`. The event is
182  /// added to any interested profiles and observers.
183  void addTimedViewportDrawEvent(
184  const char *object,
185  const char *draw_event_name,
186  UT_PerfMonViewportType viewport_type,
187  fpreal time,
188  bool is_gpu_draw=false);
189 
190  /// Start a timed script event or memory script event.
191  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
192  /// was not recorded (i.e. no profile has been started).
193  int startTimedScriptEvent(
194  const char *code_description,
195  UT_PerfMonScriptType script_type,
196  bool auto_nest_events=true);
197  int startMemoryScriptEvent(
198  const char *code_description,
199  UT_PerfMonScriptType script_type,
200  bool auto_nest_events=true);
201 
202  /// Similar to startTimedScriptEvent() and startMemoryScriptEvent()
203  /// but are tied to nodes.
204  int startTimedNodeScriptEvent(
205  int node_id,
206  const char *code_description,
207  UT_PerfMonScriptType script_type);
208  int startMemoryNodeScriptEvent(
209  int node_id,
210  const char *code_description,
211  UT_PerfMonScriptType script_type);
212 
213  /// Start a timed render event or a memory render event.
214  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
215  /// was not recorded (i.e. no profile has been started).
216  int startTimedRenderEvent(
217  const char *renderer,
218  const char *operation,
219  bool is_renderer_a_node,
220  int frame_num,
221  const char *object=NULL);
222  int startMemoryRenderEvent(
223  const char *renderer,
224  const char *operation,
225  bool is_renderer_a_node,
226  int frame_num,
227  const char *object=NULL);
228 
229  /// Add a new timed or memory render event.
230  /// Instead of starting and stopping the event,
231  /// immediately set the event's run time or memory.
232  /// The event is added to any interested profiles and observers.
233  void addTimedRenderEvent(
234  const char *object,
235  bool is_renderer_a_node,
236  int frame_num,
237  fpreal time);
238  void addMemoryRenderEvent(
239  const char *object,
240  bool is_renderer_a_node,
241  int frame_num,
242  fpreal value);
243 
244  /// Start a timed or memory frame event.
245  /// Return the event id, or UT_PERFMON_INVALID_ID if the event
246  /// was not recorded.
247  int startTimedFrameEvent(fpreal frame);
248  int startMemoryFrameEvent(fpreal frame);
249 
250  /// These methods start and stop events that are specifically designed
251  /// to measure the creation of nodes.
252  int startTimedNodeCreationEvent();
253  int startMemoryNodeCreationEvent();
254  void stopNodeCreationEvent(int event_id, int node_id);
255 
256  /// Start a timed geometry spreadsheet render event
257  int startTimedPaneEvent(const char *pane,
258  const char *operation);
259  int startMemoryPaneEvent(const char *pane,
260  const char *operation);
261 
262  /// Stop a running event.
263  /// Return the event's (self) value if `return_value` is set to true.
264  /// If the event defined by `event_id` does not exist, or is not running,
265  /// or if `return_value` is set to false, then return 0.
266  /// Note that calculating the event's value can be expensive.
267  fpreal stopEvent(int event_id, bool return_value=false);
268 
269  /// Cancel a running event. The event is stopped but is not added
270  /// to any profiles nor is it broadcast to any observers.
271  /// Do nothing if the event does not exist or if it is not running.
272  void cancelEvent(int event_id);
273 
274  /// Log a generic message event.
275  void logMessage(const char *message);
276 
277  /// Return the specified event. (read-only)
278  /// Return NULL if the requested event does not exist.
279  const UT_PerfMonEvent *getEvent(int event_id) const;
280 
281  /// Return the specified timed event. (read-only)
282  /// Return NULL if the requested event does not exist
283  /// or is not a timed event.
284  const UT_PerfMonTimedEvent *getTimedEvent(int event_id) const;
285 
286  /// Start timing the given task scope.
287  /// Return the id of the event that the task is attached to.
288  /// Return UT_PERMON_INVALID_ID if no such event exists.
289  /// This method should only be called in UT_TaskScope's constructor.
290  virtual int startTaskScope(const UT_TaskScope* task_scope);
291 
292  /// Stop timing the given task scope.
293  /// This method should only be called in UT_TaskScope's destructor.
294  virtual void stopTaskScope(
295  const UT_TaskScope* task_scope,
296  int event_id);
297 
298  /// Set extra information that will appear with the event in the
299  /// stats and event log.
300  void setEventExtraInfo(
301  int event_id, const char *extra_info) const;
302 
303  /// Return the port that the performance monitor is listening on
304  /// for remote events. Return 0 if the performance monitor
305  /// is currently not listening for events.
306  virtual int getEventListenPort() const { return 0; }
307 
308  /// ********************************************************
309  /// PROFILE MANAGEMENT
310  /// ********************************************************
311 
312  /// Start a new profile and capture timed and memory events.
313  /// When the profile is stopped, the events are processed
314  /// to produce a statistical report.
315  /// Return the unique id for the new profile.
316  int startProfile(
317  const char *title,
318  const UT_PerfMonRecordOptions *options=NULL);
319 
320  /// Stop the specified profile. Tabulate timings.
321  /// Do nothing if the profile does not exist or has already stopped.
322  void stopProfile(int profile_id);
323 
324  /// Cancel the specified profile. Do nothing if the profile
325  /// does not exist or is not profiling.
326  void cancelProfile(int profile_id);
327 
328  /// Pause the specified profile. Do nothing if the profile
329  /// does not exist, or if it is not profiling,
330  /// or if it is already paused.
331  void pauseProfile(int profile_id);
332 
333  /// Resume the specified profile. Do nothing if the profile
334  /// does not exist, or if it is not profiling,
335  /// or if it is not paused.
336  void resumeProfile(int profile_id);
337 
338  /// Load a profile from disk. Return the id of the loaded profile.
339  /// If a profile has already been loaded from the provided file path,
340  /// remove the existing profile before loading in the new one.
341  /// Return UT_PERFMON_INVALID_ID if the load failed.
342  int loadProfile(
343  const char *file_path,
344  UT_StringArray &errors);
345 
346  /// Save a profile to disk. Also update the mapping from file path to
347  /// profile ID, used to identify if a profile is loaded from the same file
348  // path in the future.
349  /// Return true if the save succeeded. Return false otherwise.
350  bool saveProfile(
351  int profile_id,
352  const char *file_path);
353 
354  /// Delete the specified profile and unregister it from
355  /// the performance monitor. Do nothing if the profile does not exist.
356  void removeProfile(int profile_id);
357 
358  /// Delete all profiles and unregister them from the performance monitor.
359  void removeAllProfiles();
360 
361  /// Rename the specified profile.
362  void renameProfile(
363  int profile_id,
364  const char *profile_name);
365 
366  /// Change the recording options for the specified profile.
367  void changeProfileRecordOptions(
368  int profile_id,
369  const UT_PerfMonRecordOptions &options);
370 
371  /// Clear the stats for the given profile.
372  void clearProfileStats(int profile_id);
373 
374  /// Return the specified profile. (read-only)
375  /// Return NULL if the requested profile does not exist.
376  const UT_PerfMonProfile *getProfile(int profile_id) const;
377 
378  /// Return the id of the active profile.
379  /// Return UT_PERFMON_INVALID_ID if there is no active profile.
380  int getActiveProfileId() const
381  { return myActiveProfileId; }
382 
383  /// Set the active profile to the given id
384  void setActiveProfileId(int profile_id);
385 
386  /// Return the number of completed profiles that the performance monitor
387  /// is storing. A completed profile is a profile that is no longer
388  /// recording events and has generated stats.
389  int numCompletedProfiles() const;
390 
391  /// Return the completed profile at the specified index.
392  /// A completed profile is a profile that is no longer recording events
393  /// and has generated stats.
394  const UT_PerfMonProfile *getCompletedProfile(int index) const;
395 
396  /// Return ID of a loaded profile corresponding to the provided file path.
397  /// Return UT_PERFMON_INVALID_ID if no such mapping exists.
398  int getProfileByFilePath(
399  const char *file_path) const;
400 
401  /// Add an interest for profile events.
402  /// Do nothing if the interest has been previously added.
403  void addProfileInterest(
404  void *callee,
406 
407  /// Remove an interest for profile events.
408  /// Do nothing if the specified interest does not exist.
409  void removeProfileInterest(
410  void *callee,
412 
413  /// Return true if the performance monitor already
414  /// has the given profile interest. Return false otherwise.
415  bool hasProfileInterest(
416  void *callee,
418 
419  /// Add an interest for running events.
420  /// You can pass in a set of record options to define the types of events
421  /// that you are interested in.
422  void addEventInterest(
423  void *callee,
424  UT_PerfMonEventCB callback,
425  const UT_PerfMonRecordOptions &options);
426 
427  /// Update the recording options for the specified event interest.
428  void changeEventInterestRecordOptions(
429  void *callee,
430  UT_PerfMonEventCB callback,
431  const UT_PerfMonRecordOptions &options);
432 
433  /// Remove an interest for events.
434  void removeEventInterest(
435  void *callee,
436  UT_PerfMonEventCB callback);
437 
438  /// Return true if the performance monitor already
439  /// has the given profile interest. Return false otherwise.
440  bool hasEventInterest(
441  void *callee,
442  UT_PerfMonEventCB callback);
443 
444  /// Create a new profile that stores difference in stats between profiles
445  /// Return the unique id for the new profile.
446  int createDiffProfile(int id1, int id2);
447 
448  /// ********************************************************
449  /// RECORDING METHODS
450  /// ********************************************************
451 
452  /// Return true if the performance monitor is recording Houdini events.
453  /// When `profile_only` is enabled, only returns true if the performance
454  /// monitor is explicitly recording a profile (settings such as
455  /// getDisplayNodeInfo() still record cook events for the node info window).
456  bool isRecording(bool profile_only = false) const {
457  return myIsRecordingCount.load() > 0 ||
458  (!profile_only && getDisplayNodeInfo());
459  }
460 
461  /// Return true if Houdini is recording cook stats.
462  bool isRecordingCookStats(bool profile_only = false) const {
463  return myRecordCookStatsCount.load() > 0 ||
464  (!profile_only && getDisplayNodeInfo());
465  }
466 
467  /// Return true if Houdini is recording pdg cook stats.
468  bool isRecordingPDGCookStats() const {
469  return myRecordPDGCookStatsCount.load() > 0;
470  }
471 
472  /// Return true if Houdini is recording simulation solve stats.
473  bool isRecordingSolveStats() const {
474  return myRecordSolveStatsCount.load() > 0;
475  }
476 
477  /// Return true if Houdini is recording object draw stats.
479  return
480  myRecordObjectDrawStatsCount.load() > 0;
481  }
482 
483  /// Return true if Houdini is recording object draw stats.
485  return
486  myRecordObjectGPUDrawStatsCount.load() > 0;
487  }
488 
489  /// Return true if Houdini is recording viewport draw stats.
491  return myRecordViewportStatsCount.load() > 0;
492  }
493 
494  /// Return true if Houdini is recording pane related stats.
495  bool isRecordingPaneStats() const {
496  return myRecordPaneStatsCount.load() > 0;
497  }
498 
499  /// Return true if Houdini is recording script stats.
500  bool isRecordingScriptStats() const {
501  return myRecordScriptStatsCount.load() > 0;
502  }
503 
504  /// Return true if Houdini is recording render stats.
505  bool isRecordingRenderStats() const {
506  return myRecordRenderStatsCount.load() > 0;
507  }
508 
509  /// Return true if Houdini is recording thread stats.
510  bool isRecordingThreadStats() const {
511  return myRecordThreadStatsCount.load() > 0;
512  }
513 
514  /// Return true if Houdini is recording frame stats.
515  bool isRecordingFrameStats() const {
516  return myRecordFrameStatsCount.load() > 0;
517  }
518 
519  /// Return true if Houdini is recording memory stats.
520  bool isRecordingMemoryStats() const {
521  return myRecordMemoryStatsCount.load() > 0;
522  }
523 
524  /// Return true if Houdini is recording errors.
525  bool isRecordingErrors() const {
526  return myRecordErrorsCount.load() > 0;
527  }
528 
529  /// Returns true if the particular node passed is allowed to
530  /// participate in recording of the statistics, false otherwise.
531  /// This is currently used for disallowing recording of the contents
532  /// of compiled nodes.
533  virtual bool isRecordingAllowedFor(OP_Node* node) const;
534 
535  /// ********************************************************
536  /// FRAME STATISTIC METHODS
537  /// ********************************************************
538 
539  /// Return the number of timed frame events
540  /// recorded by the performance monitor.
542  { return myTimedFrameEventCounter; }
543 
544  /// Return the number of memory frame events
545  /// recorded by the performance monitor.
547  { return myMemoryFrameEventCounter; }
548 
549  /// Return the total time spent in the frame events
550  /// recorded by the performance monitor.
552  { return myTotalFrameTime; }
553 
554  /// Return the total memory accumulation in the frame events
555  /// recorded by the performance monitor.
557  { return myTotalFrameMemory; }
558 
559  /// Reset the performance monitor's accumulated frame statistics.
560  void resetCumulativeFrameStats();
561 
562  /// ********************************************************
563  /// MISCELLANEOUS
564  /// ********************************************************
565 
566  /// Return the icon name to use for the given stats object.
567  /// Return NULL if there is no known icon to use for the object.
568  /// Subclasses can override this method to set up their own mappings
569  /// of stats objects to icons.
570  virtual const char *getStatsIcon(const UT_PerfMonStats *stats) const;
571 
572  /// ********************************************************
573  /// DISPLAY OPTIONS
574  /// ********************************************************
575 
576  /// Toggle whether or not the performance info is displayed in
577  /// the Node info.
578  void setDisplayNodeInfo(bool display);
579  bool getDisplayNodeInfo() const
580  { return myDisplayNodeInfo; }
581 
582  /// Thresholds for displaying various colours in the network editor and
583  /// in the Spreadsheet.
584  void getPerformanceColor(fpreal pos, UT_Color &c);
585 
586  /// Return the ramp color scheme used by the performance monitor.
587  const UT_Ramp &getRampColorScheme() const;
588 
589  /// Set the performance monitor's ramp color scheme.
590  void setRampColorScheme(const UT_Ramp &src_ramp);
591 
592  /// Load the ramp color scheme from the given string representation.
593  void loadRampColorScheme(const char *str_color_scheme);
594 
595  /// Save a representation of the ramp color scheme to the given string.
596  void saveRampColorScheme(UT_String &str_color_scheme);
597 
598  /// Return the default ramp color scheme.
599  const UT_Ramp &getDefaultColorRampScheme();
600 
601  /// ********************************************************
602  /// MAINTENANCE
603  /// ********************************************************
604 
605  /// Reset the state of the performance monitor.
606  /// Reset counters and delete events and profiles.
607  /// This method should never be called. It is handy for testing purposes.
608  void reset();
609 
610 protected:
611  /// Return the current frame.
612  virtual int getCurrentFrameSubclass_();
613 
614  /// Return a pointer to the node specified by the given id.
615  virtual OP_Node *getNodeSubclass_(int node_id) const;
616 
617  /// Return a pointer to the node that is bound to the given SIM solver.
618  virtual OP_Node *getNodeFromSolverSubclass_(
619  const SIM_Solver *solver) const;
620 
621  /// Pass back an object path that can be tied to a UT_PerfMonStats object.
622  /// The path is generated from the given node and event name.
623  virtual void getObjectPathFromNodeSubclass_(
624  OP_Node *node, const char *event_name,
625  UT_WorkBuffer &object_path) const;
626 
627  /// Pass back an object path that can be tied to a UT_PerfMonStats object.
628  /// The path is generated from the given solver, node and event name.
629  virtual void getObjectPathFromSolverAndNodeSubclass_(
630  const SIM_Solver *solver, OP_Node *node,
631  const char *event_name, UT_WorkBuffer &object_path)
632  const;
633 
634  /// Pass back extra info that can be tied to a UT_PerfMonStats object.
635  /// The extra info is generated from the given node.
636  virtual void getExtraInfoFromNodeSubclass_(
637  OP_Node *node, UT_WorkBuffer &extra_info) const;
638 
639  /// Start the remote listener to handle incoming information.
640  virtual void startRemoteListener_() {};
641 
642 private:
643 
644  int newEventId_();
645  int newProfileId_();
646 
647 
648  /// Return the specified timed event.
649  /// Return NULL if the requested event does not exist
650  /// or is not a timed event.
651  UT_PerfMonTimedEvent *getTimedEvent_(int event_id) const;
652 
653  /// Return the specified event.
654  /// Return NULL if the requested event does not exist.
655  UT_PerfMonEvent *getEvent_(int event_id) const;
656 
657  /// Start a event.
658  /// Subclasses must call this method when starting their own events.
659  int startEvent_(
660  const UT_StringHolder &event,
661  const UT_StringHolder &object,
662  bool auto_nest_events,
663  UT_PerfMonCategory category,
665  UT_PerfMonObjectType object_type,
666  const UT_StringHolder &object_icon,
667  int *frame_num=NULL,
669 
670  /// Start a cook event.
671  int startCookEvent_(
673  int node_id, const char *cook_event_name);
674 
675  /// Start a work item event.
676  int startPDGEvent_(
678  const char *path,
679  const char *pdg_event_name);
680 
681  /// Start a solve event.
682  int startSolveEvent_(
684  const SIM_Solver *solver,
685  const char *solver_event_name);
686 
687  /// Start a draw event.
688  int startDrawEvent_(
690  const char *object,
691  const char *draw_event_name,
692  bool is_gpu_draw);
693 
694  /// Start a viewport draw event.
695  int startViewportDrawEvent_(
697  const char *viewport_name,
698  const char *draw_event_name,
699  UT_PerfMonViewportType viewport_type,
700  bool is_gpu_draw);
701 
702  /// Start a generic draw event.
703  int startGenericDrawEvent_(
705  const char *object,
706  const char *draw_event_name,
707  UT_PerfMonObjectType object_type,
708  const char *object_icon,
709  bool is_gpu_draw);
710 
711  /// Start a script event.
712  int startScriptEvent_(
714  const char *code_description,
715  UT_PerfMonScriptType script_type,
716  bool auto_nest_events,
717  OP_Node *node);
718 
719  /// Start a render event.
720  int startRenderEvent_(
722  const char *renderer,
723  const char *operation,
724  bool is_renderer_a_node,
725  int frame_num,
726  const char *object);
727 
728  /// Return the specified profile.
729  /// Return NULL if the requested profile does not exist.
730  UT_PerfMonProfile *getProfile_(int profile_id) const;
731 
732  /// Activate profile.
733  void activateProfile_(UT_PerfMonProfile *profile);
734 
735  /// De-activate profile.
736  void deactivateProfile_(UT_PerfMonProfile *profile);
737 
738  /// Increment recording counters based on the specified options.
739  void incrementRecordingCounters_(
740  const UT_PerfMonRecordOptions &options);
741 
742  /// Decrement recording counters based on the specified options.
743  void decrementRecordingCounters_(
744  const UT_PerfMonRecordOptions &options);
745 
746  /// Remove and delete the specified profile. Returns the profile id
747  int removeProfile_(UT_PerfMonProfile *profile);
748 
749  /// Notify that given profile id has been destroyed
750  void notifyRemovedProfile_(int profile_id);
751 
752  /// Return ID of a loaded profile corresponding to the provided file path.
753  /// Return UT_PERFMON_INVALID_ID if no such mapping exists.
754  /// It is up to the caller to acquire the appropriate profile mutex lock.
755  int getProfileByFilePath_(const char *file_path) const;
756 
757  /// Add a mapping from file path to a loaded profile's ID.
758  /// It is up to the caller to acquire the appropriate profile mutex lock.
759  void addFilePathToLoadedProfileMapping_(
760  const char *file_path,
761  int profile_id);
762 
763  /// Remove a mapping from file path to a loaded profile's ID if it exists,
764  /// otherwise do nothing.
765  /// It is up to the caller to acquire the appropriate profile mutex lock.
766  void removeFilePathToLoadedProfileMapping_(int profile_id);
767 
768  /// Remove all filePath-to-profile mappings.
769  /// It is up to the caller to acquire the appropriate profile mutex lock.
770  void clearFilePathToLoadedProfileMappings_();
771 
772  /// Return canonicalized file path by expanding variables, making absolute,
773  /// and normalizing.
774  UT_String convertFilePathToCanonicalForm_(
775  UT_String file_path) const;
776 
777  /// Remove the event. Delete it if it is a top-level event.
778  void removeEvent_(
779  int event_id,
780  UT_PerfMonEvent *event,
781  bool is_cancelled=false);
782 
783  // Find the running parent event (if any) of the given event
784  // and create a link between them.
785  void findAndLinkToRunningParentEvent_(
786  UT_PerfMonEvent *event);
787 
788  UT_PerfMonEvent *findRunningParentEvent_(
789  const UT_TaskScope *task,
790  bool for_memory_event,
791  bool require_auto_nest);
792 
793  void addChildToRunningParentEvent_(
794  UT_PerfMonEvent *event,
795  const UT_TaskScope *task,
796  bool for_memory_event,
797  bool require_auto_nest);
798 
799  /// Return the list of running events for the given task.
800  /// The most recently started event will appear at the end of the list.
801  /// This method will create a new list if no such list already exists.
802  UT_PerfMonEventList *getOrCreateRunningEventList_(
803  const UT_TaskScope *task,
804  bool for_memory_event);
805 
806  /// Return the list of running events for the given task.
807  /// Return NULL if no such list exists.
808  /// It is up to the caller to acquire the appropriate thread events lock.
809  UT_PerfMonEventList *getRunningEventList_(
810  const UT_TaskScope *task,
811  bool for_memory_event) const;
812 
813  /// Remove the specified event from the running events list
814  /// associated with the given task.
815  /// It is up to the caller to acquire the appropriate thread events lock.
816  void removeFromRunningEventList_(
817  const UT_TaskScope *task,
818  UT_PerfMonEvent *event);
819 
820  /// Add the specified event to the running events list
821  /// associated with the given task.
822  void addToRunningEventList_(
823  const UT_TaskScope *task,
824  UT_PerfMonEvent *event);
825 
826  /// Reset the thread tasks to running event lists data structure.
827  void resetRunningEventLists_();
828 
829  /// Contribute the event's data to any interested profiles.
830  void contributeEventToProfiles_(UT_PerfMonEvent *event);
831 
832  /// Return the index of the profile interest that matches the given
833  /// callee and callback. Return -1 if no such interest exists.
834  int findProfileInterest_(void *callee,
835  UT_PerfMonProfileEventMethod callback) const;
836 
837  /// Notify interests that the given profile event has taken place.
838  void notifyProfileInterests_(
839  UT_PerfMonProfileEventType event_type,
840  int profile_id) const;
841 
842  /// Return the index of the event interest that matches the given
843  /// callee and callback. Return -1 if no such interest exists.
844  int findEventInterest_(void *callee,
845  UT_PerfMonEventCB callback) const;
846 
847  /// Notify interests that the given event has been stopped.
848  void notifyEventInterests_(
849  const UT_PerfMonEvent *event) const;
850 
851  using RWLock = tbb::spin_rw_mutex;
852 
853  /// Return the lock to use for the given task's running events list.
854  RWLock &getRunningEventsLock_(
855  const UT_TaskScope *task,
856  bool for_memory_event);
857 
858  /// Return true if the given options are interested in recording
859  /// the passed-in event.
860  bool areOptionsInterestedInEvent_(
861  const UT_PerfMonRecordOptions &options,
862  const UT_PerfMonEvent *event) const;
863 
864  /// Implementation of stopEvent() without locking
865  fpreal stopEvent_(int event_id, bool return_value);
866 
867  /// Helper method for stopEvent().
868  /// Update cumulative frame statistics with the given frame value.
869  void addToCumulativeFrameStats_(
870  fpreal frame_value, bool is_memory_value);
871 
872  /// Initialize the default color ramp scheme.
873  void initDefaultColorRampScheme_();
874 
875  /// Keep track of the active profile.
876  int myActiveProfileId;
877 
878  /// Option that determines whether performance information is displayed
879  /// with Node info.
880  bool myDisplayNodeInfo;
881 
882  UT_Ramp myColorRamp;
883  UT_Ramp myDefaultColorRamp;
884 
885  // Members dealing with events.
886  SYS_AtomicInt32 myEventIdCounter;
888 
889  // Members dealing with profiles.
890  SYS_AtomicInt32 myProfileIdCounter;
892  UT_PerfMonProfileList myRecordingProfiles;
893  UT_PerfMonProfileList myCompletedProfiles;
894  UT_StringMap<int> myFilePathsToLoadedProfiles;
895 
896  // These locks protect the performance monitor's events and profiles.
897  // If you plan to use both locks in a method, be sure to
898  // lock the profiles lock first, then the events lock.
899  mutable RWLock myEventsLock;
900  mutable RWLock myProfilesLock;
901  mutable RWLock myProfileInterestsLock;
902  mutable RWLock myEventInterestsLock;
903 
904  /// A map of task scopes to running timed event lists for each thread.
905  typedef UT_Map<const UT_TaskScope *, UT_PerfMonEventList *> TaskToEventListMap;
906  UT_ThreadSpecificValue<TaskToEventListMap *> myTasksToRunningTimedEvents;
907  UT_ThreadSpecificValue<RWLock> myTasksToRunningTimedEventsLock;
908 
909  /// A map of task scopes to running memory event lists for each thread.
910  UT_ThreadSpecificValue<TaskToEventListMap *> myTasksToRunningMemoryEvents;
911  UT_ThreadSpecificValue<RWLock> myTasksToRunningMemoryEventsLock;
912 
913  /// A list of interests on profile events.
914  UT_ValArray<ut_PerfMonProfileInterest *> myProfileInterests;
915 
916  /// A list of interests on events.
918 
919  // Recording counters.
920  SYS_AtomicInt32 myIsRecordingCount;
921  SYS_AtomicInt32 myRecordCookStatsCount;
922  SYS_AtomicInt32 myRecordPDGCookStatsCount;
923  SYS_AtomicInt32 myRecordSolveStatsCount;
924  SYS_AtomicInt32 myRecordObjectDrawStatsCount;
925  SYS_AtomicInt32 myRecordObjectGPUDrawStatsCount;
926  SYS_AtomicInt32 myRecordViewportStatsCount;
927  SYS_AtomicInt32 myRecordPaneStatsCount;
928  SYS_AtomicInt32 myRecordScriptStatsCount;
929  SYS_AtomicInt32 myRecordRenderStatsCount;
930  SYS_AtomicInt32 myRecordThreadStatsCount;
931  SYS_AtomicInt32 myRecordFrameStatsCount;
932  SYS_AtomicInt32 myRecordMemoryStatsCount;
933  SYS_AtomicInt32 myRecordErrorsCount;
934 
935  // Frame stat counters.
936  fpreal myTotalFrameTime;
937  fpreal myTotalFrameMemory;
938  int myTimedFrameEventCounter;
939  int myMemoryFrameEventCounter;
940 };
941 
942 UT_API UT_Performance *UTgetPerformance(bool create=true);
943 UT_API void UTsetPerformance(UT_Performance *perfmon);
944 
945 #endif
946 
GLuint GLsizei const GLchar * message
Definition: glcorearb.h:2543
UT_PerfMonEventType
Event types.
int getNumRecordedMemoryFrameEvents() const
UT_API UT_Performance * UTgetPerformance(bool create=true)
void
Definition: png.h:1083
GT_API const UT_StringHolder time
GLsizei const GLchar *const * path
Definition: glcorearb.h:3341
virtual void startRemoteListener_()
Start the remote listener to handle incoming information.
#define UT_API
Definition: UT_API.h:14
bool isRecordingRenderStats() const
Return true if Houdini is recording render stats.
bool isRecordingSolveStats() const
Return true if Houdini is recording simulation solve stats.
bool isRecordingErrors() const
Return true if Houdini is recording errors.
bool isRecording(bool profile_only=false) const
bool isRecordingMemoryStats() const
Return true if Houdini is recording memory stats.
struct _cl_event * event
Definition: glcorearb.h:2961
void(* UT_PerfMonProfileEventMethod)(void *callee, UT_PerfMonProfileEventType type, int profile_id)
bool isRecordingScriptStats() const
Return true if Houdini is recording script stats.
bool isRecordingViewportStats() const
Return true if Houdini is recording viewport draw stats.
bool getDisplayNodeInfo() const
GLboolean reset
Definition: glad.h:5138
UT_PerfMonObjectType
Object types.
static const UT_StringHolder theEmptyString
fpreal getTotalRecordedFrameEventTime() const
UT_PerfMonCategory
Categories.
bool isRecordingCookStats(bool profile_only=false) const
Return true if Houdini is recording cook stats.
bool isRecordingPaneStats() const
Return true if Houdini is recording pane related stats.
UT_PerfMonProfileEventType
UT_PerfMonViewportType
Viewport types recognized by the performance monitor.
A collection of statistics for a particular object (i.e. node, viewport).
int getNumRecordedTimedFrameEvents() const
fpreal64 fpreal
Definition: SYS_Types.h:277
bool isRecordingObjectDrawStats() const
Return true if Houdini is recording object draw stats.
Utility class for containing a color ramp.
Definition: UT_Ramp.h:88
GLuint index
Definition: glcorearb.h:786
int getActiveProfileId() const
void(* UT_PerfMonEventCB)(void *callee, const UT_PerfMonEvent *event)
GT_API const UT_StringHolder profile_id
bool isRecordingObjectGPUDrawStats() const
Return true if Houdini is recording object draw stats.
Definition: core.h:1131
bool isRecordingFrameStats() const
Return true if Houdini is recording frame stats.
bool isRecordingPDGCookStats() const
Return true if Houdini is recording pdg cook stats.
UT_PerfMonScriptType
Script types recognized by the performance monitor.
fpreal getTotalRecordedFrameEventMemory() const
virtual int getEventListenPort() const
type
Definition: core.h:1059
UT_API void UTsetPerformance(UT_Performance *perfmon)
bool isRecordingThreadStats() const
Return true if Houdini is recording thread stats.