File: profiling.py

package info (click to toggle)
thuban 1.2.2-6
  • links: PTS, VCS
  • area: main
  • in suites: jessie, jessie-kfreebsd
  • size: 7,872 kB
  • ctags: 5,853
  • sloc: python: 30,410; ansic: 6,181; xml: 4,234; cpp: 1,595; makefile: 141
file content (148 lines) | stat: -rw-r--r-- 4,235 bytes parent folder | download | duplicates (6)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
# Copyright (C) 2003, 2004 by Intevation GmbH
# Authors:
# Bernhard Herzog <bh@intevation.de> (2003)
# Jan-Oliver Wagner <jan@intevation.de> (2003, 2004)
#
# This program is free software under the GPL (>=v2)
# Read the file COPYING coming with the software for details.

"""Performance Measurement

This module implements two Thuban commands in a new Profiling menu:

   Profile Screen Render -- Run the screen rendering code in a profile

   Time Screen Render -- Measure the time taken for a complete redraw

See the individual functions for more details.
"""

__version__ = "$Revision: 2721 $"
# $Source$
# $Id: profiling.py 2721 2007-01-13 15:11:42Z dpinte $

import os
import StringIO
import sys
import tempfile
import profile
import time
import pstats

from wx.lib.dialogs import ScrolledMessageDialog

from Thuban import _
from Thuban.UI.command import registry, Command
from Thuban.UI.mainwindow import main_menu

#
# Customization
#
# Assign to these in your ~/.thuban/thubanstart

# The machine specific profiler bias. See the standard python profile
# module for details on how to find out which value to use.
profiler_bias = 0

# The directory the profile output is to be written to
# (Call mktemp once to initialize tempfile.tempdir)
tempfile.mktemp()
profile_dir = tempfile.tempdir

# Wether to pop up a dialog box with the result.
popup_dialog_box = True


#
#       Timing and profiling a complete redraw
#

def do_redraw(context):
    """Perform a complete redraw in the canvas in context"""
    canvas = context.mainwindow.canvas

    # Make sure there are no no finished bitmaps and active renderer
    canvas.full_redraw()

    # Iterate until all is drawn
    for c in canvas._render_iterator():
        pass


#
# Profiling the redraw
#


def profile_screen_renderer(context):
    """Script to run the redraw in the profiler

    The data gathered by the profiler will be written to
    <TMPDIR>/thuban-render.profile (<TMPDIR> is your system specific
    temporary directory.

    See the python documentation of the profile and pstats modules for
    how to access the data in the generated .profile file.
    """
    print "profiling screen renderer...",
    sys.stdout.flush()
    prof = profile.Profile(bias = profiler_bias)
    prof.runctx("do_redraw(context)", globals(), locals())
    filename = os.path.join(profile_dir, "thuban-render.profile")
    prof.dump_stats(filename)
    print "done and saved to", filename

    if popup_dialog_box:
        # catch the printout to stdout so that we can present the
        # text in a dialog
        f = StringIO.StringIO()
        orig_stdout = sys.stdout
        sys.stdout = f
        try:
            p = pstats.Stats(filename)
            msg = _('These are the statistics sorted by cumulative time:')
            p.strip_dirs().sort_stats('cumulative').print_stats()
            m = f.getvalue()
            msg = '%s\n\n%s' % (msg, m)
        finally:
            sys.stdout = orig_stdout

        dlg = ScrolledMessageDialog(context.mainwindow, msg,
                                      _('Profile Screen Render'))
        dlg.ShowModal()


registry.Add(Command("profile_screen_renderer", _('Profile Screen Render'),
                     profile_screen_renderer,
                     helptext = _('Profile the screen render')))


#
# Timing the redraw
#

def time_screen_renderer(context):
    """Script to measure the time of a complete redraw.

    The time taken will be printed to stdout.
    """
    start = time.clock()
    do_redraw(context)
    duration = time.clock() - start
    msg = _('Redraw finished in %g seconds.') % duration
    if popup_dialog_box:
        context.mainwindow.RunMessageBox(_('Time Screen Render'), msg)
    else:
        print msg


registry.Add(Command("time_screen_renderer", _('Time Screen Render'),
                     time_screen_renderer,
                     helptext = _('Time the screen render')))

# find the extensions menu (create it anew if not found)
extensions_menu = main_menu.FindOrInsertMenu('extensions', _('E&xtensions'))

profiler_menu = extensions_menu.InsertMenu("profiler", _('&Profiler'))
profiler_menu.InsertItem("time_screen_renderer")
profiler_menu.InsertItem("profile_screen_renderer")