Skip to content

Commit 89fb134

Browse files
committed
add support of global variables
First commit to support the global variables, which has been slightly tested with "C", but not with "C++" : - global variables panel is opened with [ctrl+f9], when focus is on a source file - When selecting a global variable from the list, it is added to the GDB View "Variable" - The list of global variables is set with the results of gdb command "info variables". In case structure/enum (without typedef), the overall structure is present in the panel list. - The list of global variables is persistent so that they are set in GDB View "Variable" at the first stop of next launch. TODO list: - Invalid the saved global variables list in case of rebuild/etc.... - Filter the content of structure/enum when setting the panel list. - bugs. The first version does not work perfectly, but it is good enough to be used.
1 parent c39ee60 commit 89fb134

File tree

3 files changed

+108
-8
lines changed

3 files changed

+108
-8
lines changed

Default.sublime-commands

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -81,4 +81,9 @@
8181
"caption": "SublimeGDB: Open Threads View",
8282
"command": "gdb_open_threads_view"
8383
}
84+
{
85+
"caption": "SublimeGDB: Open Global Variable Panel",
86+
"command": "gdb_open_global_variable_panel"
87+
},
88+
8489
]

Default.sublime-keymap

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,11 @@
2828
"command": "gdb_toggle_breakpoint",
2929
"keys": ["f9"]
3030
},
31+
{
32+
"command": "gdb_open_global_variable_panel",
33+
"context": [{"key": "gdb_running", "operator": "equal", "operand": true}],
34+
"keys": ["ctrl+f9"]
35+
},
3136
{
3237
"command": "gdb_launch",
3338
"context": [{"key": "gdb_running", "operator": "equal", "operand": false}],

sublimegdb.py

Lines changed: 98 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -126,6 +126,8 @@ def expand_path(value, window):
126126
DEBUG_FILE = None
127127
__debug_file_handle = None
128128

129+
gdb_gvar_panel_list = []
130+
gdb_lastoutput = ""
129131
gdb_lastresult = ""
130132
gdb_lastline = ""
131133
gdb_cursor = ""
@@ -635,6 +637,7 @@ class GDBVariablesView(GDBView):
635637
def __init__(self):
636638
super(GDBVariablesView, self).__init__("GDB Variables", False, settingsprefix="variables")
637639
self.variables = []
640+
self.gvariables = []
638641

639642
def open(self):
640643
super(GDBVariablesView, self).open()
@@ -647,9 +650,20 @@ def update_view(self):
647650
output = ""
648651
line = 0
649652
dirtylist = []
653+
654+
if len(self.gvariables) > 0:
655+
output, line = ("====== GLOBAL =======\n", line+1)
656+
self.add_line(output)
657+
for g in self.gvariables:
658+
output, line = g.format(line=line, dirty=dirtylist)
659+
self.add_line(output)
660+
661+
output, line = ("====== LOCAL =======\n", line+1)
662+
self.add_line(output)
650663
for local in self.variables:
651664
output, line = local.format(line=line, dirty=dirtylist)
652665
self.add_line(output)
666+
653667
self.update()
654668
regions = []
655669
v = self.get_view()
@@ -668,10 +682,13 @@ def extract_varnames(self, res):
668682
return [x["name"] for x in res]
669683
return []
670684

671-
def add_variable(self, exp):
685+
def add_variable(self, exp, g = False):
672686
v = self.create_variable(exp)
673687
if v:
674-
self.variables.append(v)
688+
if g == True:
689+
self.gvariables.append(v)
690+
else:
691+
self.variables.append(v)
675692

676693
def create_variable(self, exp):
677694
line = run_cmd("-var-create - * %s" % exp, True)
@@ -686,12 +703,27 @@ def create_variable(self, exp):
686703
def update_variables(self, sameFrame):
687704
if not self.should_update():
688705
return
706+
707+
ret = parse_result_line(run_cmd("-var-update --all-values *", True))["changelist"]
708+
if "varobj" in ret:
709+
ret = listify(ret["varobj"])
710+
711+
# Update value of global variables
712+
for var in self.gvariables:
713+
var.clear_dirty()
714+
for value in ret:
715+
name = value["name"]
716+
for var in self.gvariables:
717+
real = var.find(name)
718+
if real is not None:
719+
real.update(value)
720+
if not "value" in value and not "new_value" in value:
721+
real.update_value()
722+
break
723+
689724
if sameFrame:
690725
for var in self.variables:
691726
var.clear_dirty()
692-
ret = parse_result_line(run_cmd("-var-update --all-values *", True))["changelist"]
693-
if "varobj" in ret:
694-
ret = listify(ret["varobj"])
695727
dellist = []
696728
for value in ret:
697729
name = value["name"]
@@ -734,11 +766,12 @@ def update_variables(self, sameFrame):
734766
loc = self.extract_varnames(parse_result_line(run_cmd("-stack-list-locals 0", True))["locals"])
735767
for var in loc:
736768
self.add_variable(var)
769+
737770
self.update_view()
738771

739772
def get_variable_at_line(self, line, var_list=None):
740773
if var_list is None:
741-
var_list = self.variables
774+
var_list = self.gvariables + self.variables
742775
if len(var_list) == 0:
743776
return None
744777

@@ -1264,9 +1297,11 @@ def update_view_markers(view=None):
12641297

12651298
def run_cmd(cmd, block=False, mimode=True, timeout=10):
12661299
global count
1300+
global gdb_lastoutput
12671301
if not is_running():
12681302
return "0^error,msg=\"no session running\""
12691303

1304+
gdb_lastoutput = ""
12701305
timeoutcount = timeout/0.001
12711306

12721307
### handle a list of commands by recursively calling run_cmd
@@ -1383,6 +1418,7 @@ def gdboutput(pipe):
13831418
global gdb_process
13841419
global gdb_lastresult
13851420
global gdb_lastline
1421+
global gdb_lastoutput
13861422
global gdb_stack_frame
13871423
global gdb_run_status
13881424
global gdb_stack_index
@@ -1420,8 +1456,9 @@ def gdboutput(pipe):
14201456
gdb_lastresult = line
14211457

14221458
if line.startswith("~"):
1423-
gdb_console_view.add_line(
1424-
line[2:-1].replace("\\n", "\n").replace("\\\"", "\"").replace("\\t", "\t"), False)
1459+
line_ = line[2:-1].replace("\\n", "\n").replace("\\\"", "\"").replace("\\t", "\t")
1460+
gdb_lastoutput += line_
1461+
gdb_console_view.add_line(line_, False)
14251462

14261463
except:
14271464
traceback.print_exc()
@@ -1748,6 +1785,11 @@ def launch(self):
17481785
else:
17491786
gdb_run_status = "stopped"
17501787

1788+
# Add global variables of previous execution
1789+
gvariables = list(gdb_variables_view.gvariables)
1790+
gdb_variables_view.gvariables = []
1791+
for var in gvariables:
1792+
gdb_variables_view.add_variable(var['exp'], True)
17511793

17521794
show_input()
17531795
else:
@@ -1950,6 +1992,54 @@ def is_enabled(self):
19501992
return True
19511993
return False
19521994

1995+
class GdbOpenGlobalVariablePanel(sublime_plugin.TextCommand):
1996+
def run(self, edit):
1997+
global gdb_gvar_panel_list
1998+
1999+
fn = sublime.active_window().active_view().file_name()
2000+
if fn is None:
2001+
sublime.status_message("Don't display global variables panel in gdb view")
2002+
return
2003+
2004+
if len(gdb_gvar_panel_list) == 0:
2005+
# Retrieve all the global variables
2006+
run_cmd("info variables", True)
2007+
# Build the list for the panel
2008+
src = "empty"
2009+
pattern = re.compile("File (.*):")
2010+
for line in gdb_lastoutput.split('\n'):
2011+
if 'All defined variables' in line:
2012+
continue
2013+
if 'Non-debugging' in line:
2014+
# Next symbols without debugging info (dwarf). Skip them
2015+
break
2016+
if pattern.match(line):
2017+
src = line.split("File ")[1].split(":")[0]
2018+
continue
2019+
if line.replace(" ", "").replace("\t", "") == "":
2020+
continue
2021+
gdb_gvar_panel_list.append("%s (%s)" % (line, src))
2022+
2023+
# Show the panel
2024+
sublime.active_window().show_quick_panel(gdb_gvar_panel_list, self.on_done)
2025+
2026+
2027+
def on_done(self, index):
2028+
global gdb_gvar_panel_list
2029+
if index == -1:
2030+
return
2031+
line = gdb_gvar_panel_list[index]
2032+
2033+
# Many filter string to not consider fields of structure/enum/etc..
2034+
if line.startswith(" ") or "{" in line:
2035+
return
2036+
2037+
name = line.split(" ")[1].split(";")[0]
2038+
for var in gdb_variables_view.gvariables:
2039+
if name == var['exp']:
2040+
return
2041+
gdb_variables_view.add_variable(name, True)
2042+
gdb_variables_view.update_view()
19532043

19542044
class GdbEditVariable(sublime_plugin.TextCommand):
19552045
def run(self, edit):

0 commit comments

Comments
 (0)