OpenCores
URL https://opencores.org/ocsvn/altor32/altor32/trunk

Subversion Repositories altor32

[/] [altor32/] [trunk/] [gcc-x64/] [or1knd-elf/] [share/] [gdb/] [python/] [gdb/] [command/] [pretty_printers.py] - Blame information for rev 35

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 35 ultra_embe
# Pretty-printer commands.
2
# Copyright (C) 2010-2012 Free Software Foundation, Inc.
3
 
4
# This program is free software; you can redistribute it and/or modify
5
# it under the terms of the GNU General Public License as published by
6
# the Free Software Foundation; either version 3 of the License, or
7
# (at your option) any later version.
8
#
9
# This program is distributed in the hope that it will be useful,
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
# GNU General Public License for more details.
13
#
14
# You should have received a copy of the GNU General Public License
15
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
16
 
17
"""GDB commands for working with pretty-printers."""
18
 
19
import copy
20
import gdb
21
import re
22
 
23
 
24
def parse_printer_regexps(arg):
25
    """Internal utility to parse a pretty-printer command argv.
26
 
27
    Arguments:
28
        arg: The arguments to the command.  The format is:
29
             [object-regexp [name-regexp]].
30
             Individual printers in a collection are named as
31
             printer-name;subprinter-name.
32
 
33
    Returns:
34
        The result is a 3-tuple of compiled regular expressions, except that
35
        the resulting compiled subprinter regexp is None if not provided.
36
 
37
    Raises:
38
        SyntaxError: an error processing ARG
39
    """
40
 
41
    argv = gdb.string_to_argv(arg);
42
    argc = len(argv)
43
    object_regexp = ""  # match everything
44
    name_regexp = ""  # match everything
45
    subname_regexp = None
46
    if argc > 3:
47
        raise SyntaxError("too many arguments")
48
    if argc >= 1:
49
        object_regexp = argv[0]
50
    if argc >= 2:
51
        name_subname = argv[1].split(";", 1)
52
        name_regexp = name_subname[0]
53
        if len(name_subname) == 2:
54
            subname_regexp = name_subname[1]
55
    # That re.compile raises SyntaxError was determined empirically.
56
    # We catch it and reraise it to provide a slightly more useful
57
    # error message for the user.
58
    try:
59
        object_re = re.compile(object_regexp)
60
    except SyntaxError:
61
        raise SyntaxError("invalid object regexp: %s" % object_regexp)
62
    try:
63
        name_re = re.compile (name_regexp)
64
    except SyntaxError:
65
        raise SyntaxError("invalid name regexp: %s" % name_regexp)
66
    if subname_regexp is not None:
67
        try:
68
            subname_re = re.compile(subname_regexp)
69
        except SyntaxError:
70
            raise SyntaxError("invalid subname regexp: %s" % subname_regexp)
71
    else:
72
        subname_re = None
73
    return(object_re, name_re, subname_re)
74
 
75
 
76
def printer_enabled_p(printer):
77
    """Internal utility to see if printer (or subprinter) is enabled."""
78
    if hasattr(printer, "enabled"):
79
        return printer.enabled
80
    else:
81
        return True
82
 
83
 
84
class InfoPrettyPrinter(gdb.Command):
85
    """GDB command to list all registered pretty-printers.
86
 
87
    Usage: info pretty-printer [object-regexp [name-regexp]]
88
 
89
    OBJECT-REGEXP is a regular expression matching the objects to list.
90
    Objects are "global", the program space's file, and the objfiles within
91
    that program space.
92
 
93
    NAME-REGEXP matches the name of the pretty-printer.
94
    Individual printers in a collection are named as
95
    printer-name;subprinter-name.
96
    """
97
 
98
    def __init__ (self):
99
        super(InfoPrettyPrinter, self).__init__("info pretty-printer",
100
                                                 gdb.COMMAND_DATA)
101
 
102
    @staticmethod
103
    def enabled_string(printer):
104
        """Return "" if PRINTER is enabled, otherwise " [disabled]"."""
105
        if printer_enabled_p(printer):
106
            return ""
107
        else:
108
            return " [disabled]"
109
 
110
    @staticmethod
111
    def printer_name(printer):
112
        """Return the printer's name."""
113
        if hasattr(printer, "name"):
114
            return printer.name
115
        if hasattr(printer, "__name__"):
116
            return printer.__name__
117
        # This "shouldn't happen", but the public API allows for
118
        # direct additions to the pretty-printer list, and we shouldn't
119
        # crash because someone added a bogus printer.
120
        # Plus we want to give the user a way to list unknown printers.
121
        return "unknown"
122
 
123
    def list_pretty_printers(self, pretty_printers, name_re, subname_re):
124
        """Print a list of pretty-printers."""
125
        # A potential enhancement is to provide an option to list printers in
126
        # "lookup order" (i.e. unsorted).
127
        sorted_pretty_printers = copy.copy(pretty_printers)
128
        sorted_pretty_printers.sort(lambda x, y:
129
                                        cmp(self.printer_name(x),
130
                                            self.printer_name(y)))
131
        for printer in sorted_pretty_printers:
132
            name = self.printer_name(printer)
133
            enabled = self.enabled_string(printer)
134
            if name_re.match(name):
135
                print "  %s%s" % (name, enabled)
136
                if (hasattr(printer, "subprinters") and
137
                    printer.subprinters is not None):
138
                    sorted_subprinters = copy.copy(printer.subprinters)
139
                    sorted_subprinters.sort(lambda x, y:
140
                                                cmp(self.printer_name(x),
141
                                                    self.printer_name(y)))
142
                    for subprinter in sorted_subprinters:
143
                        if (not subname_re or
144
                            subname_re.match(subprinter.name)):
145
                            print ("    %s%s" %
146
                                   (subprinter.name,
147
                                    self.enabled_string(subprinter)))
148
 
149
    def invoke1(self, title, printer_list,
150
                obj_name_to_match, object_re, name_re, subname_re):
151
        """Subroutine of invoke to simplify it."""
152
        if printer_list and object_re.match(obj_name_to_match):
153
            print title
154
            self.list_pretty_printers(printer_list, name_re, subname_re)
155
 
156
    def invoke(self, arg, from_tty):
157
        """GDB calls this to perform the command."""
158
        (object_re, name_re, subname_re) = parse_printer_regexps(arg)
159
        self.invoke1("global pretty-printers:", gdb.pretty_printers,
160
                     "global", object_re, name_re, subname_re)
161
        cp = gdb.current_progspace()
162
        self.invoke1("progspace %s pretty-printers:" % cp.filename,
163
                     cp.pretty_printers, "progspace",
164
                     object_re, name_re, subname_re)
165
        for objfile in gdb.objfiles():
166
            self.invoke1("  objfile %s pretty-printers:" % objfile.filename,
167
                         objfile.pretty_printers, objfile.filename,
168
                         object_re, name_re, subname_re)
169
 
170
 
171
def count_enabled_printers(pretty_printers):
172
    """Return a 2-tuple of number of enabled and total printers."""
173
    enabled = 0
174
    total = 0
175
    for printer in pretty_printers:
176
        if (hasattr(printer, "subprinters")
177
            and printer.subprinters is not None):
178
            if printer_enabled_p(printer):
179
                for subprinter in printer.subprinters:
180
                    if printer_enabled_p(subprinter):
181
                        enabled += 1
182
            total += len(printer.subprinters)
183
        else:
184
            if printer_enabled_p(printer):
185
                enabled += 1
186
            total += 1
187
    return (enabled, total)
188
 
189
 
190
def count_all_enabled_printers():
191
    """Return a 2-tuble of the enabled state and total number of all printers.
192
    This includes subprinters.
193
    """
194
    enabled_count = 0
195
    total_count = 0
196
    (t_enabled, t_total) = count_enabled_printers(gdb.pretty_printers)
197
    enabled_count += t_enabled
198
    total_count += t_total
199
    (t_enabled, t_total) = count_enabled_printers(gdb.current_progspace().pretty_printers)
200
    enabled_count += t_enabled
201
    total_count += t_total
202
    for objfile in gdb.objfiles():
203
        (t_enabled, t_total) = count_enabled_printers(objfile.pretty_printers)
204
        enabled_count += t_enabled
205
        total_count += t_total
206
    return (enabled_count, total_count)
207
 
208
 
209
def pluralize(text, n, suffix="s"):
210
    """Return TEXT pluralized if N != 1."""
211
    if n != 1:
212
        return "%s%s" % (text, suffix)
213
    else:
214
        return text
215
 
216
 
217
def show_pretty_printer_enabled_summary():
218
    """Print the number of printers enabled/disabled.
219
    We count subprinters individually.
220
    """
221
    (enabled_count, total_count) = count_all_enabled_printers()
222
    print "%d of %d printers enabled" % (enabled_count, total_count)
223
 
224
 
225
def do_enable_pretty_printer_1 (pretty_printers, name_re, subname_re, flag):
226
    """Worker for enabling/disabling pretty-printers.
227
 
228
    Arguments:
229
        pretty_printers: list of pretty-printers
230
        name_re: regular-expression object to select printers
231
        subname_re: regular expression object to select subprinters or None
232
                    if all are affected
233
        flag: True for Enable, False for Disable
234
 
235
    Returns:
236
        The number of printers affected.
237
        This is just for informational purposes for the user.
238
    """
239
    total = 0
240
    for printer in pretty_printers:
241
        if (hasattr(printer, "name") and name_re.match(printer.name) or
242
            hasattr(printer, "__name__") and name_re.match(printer.__name__)):
243
            if (hasattr(printer, "subprinters") and
244
                printer.subprinters is not None):
245
                if not subname_re:
246
                    # Only record printers that change state.
247
                    if printer_enabled_p(printer) != flag:
248
                        for subprinter in printer.subprinters:
249
                            if printer_enabled_p(subprinter):
250
                                total += 1
251
                    # NOTE: We preserve individual subprinter settings.
252
                    printer.enabled = flag
253
                else:
254
                    # NOTE: Whether this actually disables the subprinter
255
                    # depends on whether the printer's lookup function supports
256
                    # the "enable" API.  We can only assume it does.
257
                    for subprinter in printer.subprinters:
258
                        if subname_re.match(subprinter.name):
259
                            # Only record printers that change state.
260
                           if (printer_enabled_p(printer) and
261
                               printer_enabled_p(subprinter) != flag):
262
                               total += 1
263
                           subprinter.enabled = flag
264
            else:
265
                # This printer has no subprinters.
266
                # If the user does "disable pretty-printer .* .* foo"
267
                # should we disable printers that don't have subprinters?
268
                # How do we apply "foo" in this context?  Since there is no
269
                # "foo" subprinter it feels like we should skip this printer.
270
                # There's still the issue of how to handle
271
                # "disable pretty-printer .* .* .*", and every other variation
272
                # that can match everything.  For now punt and only support
273
                # "disable pretty-printer .* .*" (i.e. subname is elided)
274
                # to disable everything.
275
                if not subname_re:
276
                    # Only record printers that change state.
277
                    if printer_enabled_p(printer) != flag:
278
                        total += 1
279
                    printer.enabled = flag
280
    return total
281
 
282
 
283
def do_enable_pretty_printer (arg, flag):
284
    """Internal worker for enabling/disabling pretty-printers."""
285
    (object_re, name_re, subname_re) = parse_printer_regexps(arg)
286
 
287
    total = 0
288
    if object_re.match("global"):
289
        total += do_enable_pretty_printer_1(gdb.pretty_printers,
290
                                            name_re, subname_re, flag)
291
    cp = gdb.current_progspace()
292
    if object_re.match("progspace"):
293
        total += do_enable_pretty_printer_1(cp.pretty_printers,
294
                                            name_re, subname_re, flag)
295
    for objfile in gdb.objfiles():
296
        if object_re.match(objfile.filename):
297
            total += do_enable_pretty_printer_1(objfile.pretty_printers,
298
                                                name_re, subname_re, flag)
299
 
300
    if flag:
301
        state = "enabled"
302
    else:
303
        state = "disabled"
304
    print "%d %s %s" % (total, pluralize("printer", total), state)
305
 
306
    # Print the total list of printers currently enabled/disabled.
307
    # This is to further assist the user in determining whether the result
308
    # is expected.  Since we use regexps to select it's useful.
309
    show_pretty_printer_enabled_summary()
310
 
311
 
312
# Enable/Disable one or more pretty-printers.
313
#
314
# This is intended for use when a broken pretty-printer is shipped/installed
315
# and the user wants to disable that printer without disabling all the other
316
# printers.
317
#
318
# A useful addition would be -v (verbose) to show each printer affected.
319
 
320
class EnablePrettyPrinter (gdb.Command):
321
    """GDB command to enable the specified pretty-printer.
322
 
323
    Usage: enable pretty-printer [object-regexp [name-regexp]]
324
 
325
    OBJECT-REGEXP is a regular expression matching the objects to examine.
326
    Objects are "global", the program space's file, and the objfiles within
327
    that program space.
328
 
329
    NAME-REGEXP matches the name of the pretty-printer.
330
    Individual printers in a collection are named as
331
    printer-name;subprinter-name.
332
    """
333
 
334
    def __init__(self):
335
        super(EnablePrettyPrinter, self).__init__("enable pretty-printer",
336
                                                   gdb.COMMAND_DATA)
337
 
338
    def invoke(self, arg, from_tty):
339
        """GDB calls this to perform the command."""
340
        do_enable_pretty_printer(arg, True)
341
 
342
 
343
class DisablePrettyPrinter (gdb.Command):
344
    """GDB command to disable the specified pretty-printer.
345
 
346
    Usage: disable pretty-printer [object-regexp [name-regexp]]
347
 
348
    OBJECT-REGEXP is a regular expression matching the objects to examine.
349
    Objects are "global", the program space's file, and the objfiles within
350
    that program space.
351
 
352
    NAME-REGEXP matches the name of the pretty-printer.
353
    Individual printers in a collection are named as
354
    printer-name;subprinter-name.
355
    """
356
 
357
    def __init__(self):
358
        super(DisablePrettyPrinter, self).__init__("disable pretty-printer",
359
                                                   gdb.COMMAND_DATA)
360
 
361
    def invoke(self, arg, from_tty):
362
        """GDB calls this to perform the command."""
363
        do_enable_pretty_printer(arg, False)
364
 
365
 
366
def register_pretty_printer_commands():
367
    """Call from a top level script to install the pretty-printer commands."""
368
    InfoPrettyPrinter()
369
    EnablePrettyPrinter()
370
    DisablePrettyPrinter()
371
 
372
register_pretty_printer_commands()

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.