From 865589332ed1cb412cfc7e7614cbecdba3c5439f Mon Sep 17 00:00:00 2001 From: Jorge Gorbe Date: Fri, 30 Nov 2012 14:37:44 +0100 Subject: [PATCH] view.py fixes, more samples --- samples/array.cc | 19 +++++++++++++++++++ samples/loop.c | 28 +++++++++++++++++++++++++++ samples/plotarray.py | 44 +++++++++++++++++++++++++++++++++++++++++++ samples/plotsimple.py | 19 +++++++++++++++++++ samples/test-ref.cc | 28 +++++++++++++++++++++++++++ samples/test.d | 16 ++++++++++++++++ samples/view.py | 32 +++++++++++++++---------------- 7 files changed, 170 insertions(+), 16 deletions(-) create mode 100644 samples/array.cc create mode 100644 samples/loop.c create mode 100644 samples/plotarray.py create mode 100644 samples/plotsimple.py create mode 100644 samples/test-ref.cc create mode 100644 samples/test.d diff --git a/samples/array.cc b/samples/array.cc new file mode 100644 index 0000000..1bd9587 --- /dev/null +++ b/samples/array.cc @@ -0,0 +1,19 @@ +#include +#include +#include + +int main(int argc, char **argv) { + const int N=200; + double array[N]; + double *sine = new double[N]; + + srand(time(NULL)); + + for (int i=0; i < N; i++) { + array[i] = rand()/(double)RAND_MAX; + sine[i] = sin(2*M_PI*i/(double)N); + } + + delete[] sine; + return 0; +} diff --git a/samples/loop.c b/samples/loop.c new file mode 100644 index 0000000..700049c --- /dev/null +++ b/samples/loop.c @@ -0,0 +1,28 @@ +#include +#include + +typedef struct snode { + int value; + float blah; + struct snode *next; +} node; + +void add(node **head, int x) { + node *n = malloc(sizeof(node)); + n->value = x; + n->blah = 1234.0f; + n->next = *head; + *head = n; +} + +int main() { + node *list = NULL; + add(&list, 10); + add(&list, 20); + add(&list, 30); + add(&list, 99); + + // close the loop! + list->next->next->next->next = list; +} + diff --git a/samples/plotarray.py b/samples/plotarray.py new file mode 100644 index 0000000..5d4afdb --- /dev/null +++ b/samples/plotarray.py @@ -0,0 +1,44 @@ +import gdb +import gdb.types +import matplotlib.pyplot as plt + +import sys, traceback + + +class PlotterCommand(gdb.Command): + """Plot arrays""" + def __init__(self): + super(PlotterCommand, self).__init__("plot", gdb.COMMAND_DATA, gdb.COMPLETE_SYMBOL) + + + def invoke(self, arg, from_tty): + args = gdb.string_to_argv(arg) + v = gdb.parse_and_eval(args[0]) + + # check value is array or pointer + t = v.type.strip_typedefs() + if t.code != gdb.TYPE_CODE_ARRAY and t.code != gdb.TYPE_CODE_PTR: + raise TypeError("Only arrays and pointers are supported") + + # find array size + if len(args) > 1: + n = int(args[1]) # user defined size + else: + if v.type.code == gdb.TYPE_CODE_ARRAY: + n = v.type.sizeof / v.type.target().sizeof # arraysize + else: + raise gdb.error("array size must be specified for pointers") + + + try: + l = [float(v[i]) for i in range(n)] + plt.plot(l) + plt.show() + except: + exc_type, exc_value, exc_traceback = sys.exc_info() + traceback.print_exception(exc_type, exc_value, exc_traceback) + + +PlotterCommand() + + diff --git a/samples/plotsimple.py b/samples/plotsimple.py new file mode 100644 index 0000000..ffaee53 --- /dev/null +++ b/samples/plotsimple.py @@ -0,0 +1,19 @@ +import gdb +import matplotlib.pyplot as plt + +class PlotterCommand(gdb.Command): + """Plot arrays""" + def __init__(self): + super(PlotterCommand, self).__init__("plot", gdb.COMMAND_DATA, gdb.COMPLETE_SYMBOL) + + def invoke(self, arg, from_tty): + args = gdb.string_to_argv(arg) + v = gdb.parse_and_eval(args[0]) + t = v.type.strip_typedefs() + n = t.sizeof / t.target().sizeof + l = [float(v[i]) for i in range(n)] + plt.plot(l) + plt.show() + +PlotterCommand() + diff --git a/samples/test-ref.cc b/samples/test-ref.cc new file mode 100644 index 0000000..06f8a16 --- /dev/null +++ b/samples/test-ref.cc @@ -0,0 +1,28 @@ +#include +#include + +typedef struct snode { + int value; + float blah; + struct snode *next; +} node; + +void add(node **head, int x) { + node *n = (node*) malloc(sizeof(node)); + n->value = x; + n->blah = 1234.0f; + n->next = *head; + *head = n; +} + +int main() { + node *list = NULL; + add(&list, 10); + add(&list, 20); + add(&list, 30); + add(&list, 99); + + node &l2 = *list; + l2.blah=99.0f; +} + diff --git a/samples/test.d b/samples/test.d new file mode 100644 index 0000000..8117c49 --- /dev/null +++ b/samples/test.d @@ -0,0 +1,16 @@ +import std.stdio; + +class S +{ + S next; +} + + +void main() +{ + S s = new S(); + s.next = new S(); + s.next.next = new S(); + +} + diff --git a/samples/view.py b/samples/view.py index 5820da9..0016ee3 100644 --- a/samples/view.py +++ b/samples/view.py @@ -66,9 +66,9 @@ def find_outgoing_pointers(value): member_pointers = find_outgoing_pointers(value[f.name]) merge_dict(result, member_pointers) elif type_is_pointer(f.type): - result[f.name] = value[f.name] + result["->"+f.name] = value[f.name] elif type_is_reference(f.type): - result[f.name] = value[f.name].referenced_value().address + result["."+f.name] = value[f.name].referenced_value().address return result else: @@ -204,8 +204,8 @@ class GraphViewer(gtk.Layout): # draw node name name_layout = context.create_layout() name_layout.set_font_description(pango.FontDescription("sans 8")) - display_name = str(node.gdb_value.address) #node.name - #display_name = node.name + #display_name = str(node.gdb_value.address) + display_name = node.name if node is not self.selected_node: template_args_start = display_name.find("<") if template_args_start != -1: @@ -261,6 +261,7 @@ class GraphViewer(gtk.Layout): name_layout = context.create_layout() name_layout.set_font_description(pango.FontDescription("sans 8")) name_layout.set_text(u"\u2192"+name) + #name_layout.set_text(name) _, name_height = name_layout.get_pixel_size() rotation = -orientation(vx, vy) y_offset = -name_height - 2 # a couple of extra pixels to avoid text "stepping on the line" @@ -394,11 +395,11 @@ class ViewerWindow(gtk.Window): def on_entry_changed(self, entry): expression = entry.get_text() value = gdb.parse_and_eval(expression) - nodes = create_viewer_nodes(value, self.recursion_level) + nodes = create_viewer_nodes(expression, value, self.recursion_level) self.viewer.nodes = nodes self.viewer.queue_draw() -def visit_values(node_dict, value, x, y, recursion_level): +def visit_values(node_dict, node_name, value, x, y, recursion_level): """ Recursively traverse children of a gdb Value, storing pairs (address_as_uint, GraphViewerNode). returns (width, height, node_dict) @@ -414,7 +415,7 @@ def visit_values(node_dict, value, x, y, recursion_level): return NODE_SPACING, NODE_SPACING # check if node has already been visited, don't create repeated nodes - node_dict[address_to_uint(value.address)] = GraphViewerNode(x, y, str(value.type), value) + node_dict[address_to_uint(value.address)] = GraphViewerNode(x, y, node_name, value) width = NODE_SPACING height = 0 children_x = x+NODE_SPACING @@ -422,16 +423,15 @@ def visit_values(node_dict, value, x, y, recursion_level): children_height = 0 children = find_outgoing_pointers(value) - print "value =",value - children2 = {} - for k in children: - children2[k] = str(children[k]) - print "children =",children2 for (child_name, child_value) in children.iteritems(): # compute child "tree" dimensions (layout is always tree-like even if there are edges that make this a generic graph) + if child_name == '*': + child_node_name = "(*%s)"%node_name + else: + child_node_name = node_name + child_name if child_value != 0: - child_width, child_height = visit_values(node_dict, child_value.referenced_value(), children_x, children_y, recursion_level - 1) + child_width, child_height = visit_values(node_dict, child_node_name, child_value.referenced_value(), children_x, children_y, recursion_level - 1) children_y += child_height children_height += child_height width = max(width, NODE_SPACING + child_width) @@ -466,10 +466,10 @@ def fill_node_connections(nodes, addr, value): print "unknown type:", value.type -def create_viewer_nodes(value, recursion_level): +def create_viewer_nodes(expr, value, recursion_level): # create the nodes nodes = {} - width, height = visit_values(nodes, value, 50, 50, recursion_level) + width, height = visit_values(nodes, expr, value, 50, 50, recursion_level) # establish connections between nodes when all the nodes are there for addr in nodes: @@ -514,7 +514,7 @@ class ViewerCommand(gdb.Command): window.recursion_level = recursion_level window.show_all() - nodes = create_viewer_nodes(value, recursion_level) + nodes = create_viewer_nodes(args[0], value, recursion_level) window.viewer.nodes = nodes window.viewer.queue_draw() is_gtk_main_running = True -- 2.34.1