rb8-trepanning 0.1.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +3 -0
- data/CHANGES +34 -0
- data/ChangeLog +875 -0
- data/README.textile +59 -0
- data/Rakefile +215 -0
- data/app/.gitignore +1 -0
- data/app/cmd_parse.kpeg +241 -0
- data/app/cmd_parse.rb +212 -0
- data/app/cmd_parser.rb +1948 -0
- data/app/complete.rb +79 -0
- data/app/default.rb +90 -0
- data/app/display.rb +148 -0
- data/app/eventbuffer.rb +147 -0
- data/app/frame.rb +166 -0
- data/app/irb.rb +114 -0
- data/app/options.rb +200 -0
- data/app/run.rb +74 -0
- data/app/util.rb +65 -0
- data/bin/.gitignore +1 -0
- data/bin/trepan8 +115 -0
- data/data/.gitignore +1 -0
- data/data/irbrc +41 -0
- data/interface/.gitignore +1 -0
- data/interface/base_intf.rb +109 -0
- data/interface/client.rb +82 -0
- data/interface/comcodes.rb +20 -0
- data/interface/script.rb +110 -0
- data/interface/server.rb +147 -0
- data/interface/user.rb +165 -0
- data/io/base_io.rb +148 -0
- data/io/input.rb +158 -0
- data/io/null_output.rb +46 -0
- data/io/string_array.rb +156 -0
- data/io/tcpclient.rb +129 -0
- data/io/tcpfns.rb +33 -0
- data/io/tcpserver.rb +141 -0
- data/lib/debugger.rb +8 -0
- data/lib/trepanning.rb +283 -0
- data/processor/.gitignore +1 -0
- data/processor/command-ruby-debug/breakpoints.rb +155 -0
- data/processor/command-ruby-debug/catchpoint.rb +55 -0
- data/processor/command-ruby-debug/condition.rb +49 -0
- data/processor/command-ruby-debug/control.rb +31 -0
- data/processor/command-ruby-debug/display.rb +120 -0
- data/processor/command-ruby-debug/enable.rb +202 -0
- data/processor/command-ruby-debug/frame.rb +199 -0
- data/processor/command-ruby-debug/help.rb +63 -0
- data/processor/command-ruby-debug/info.rb +359 -0
- data/processor/command-ruby-debug/method.rb +84 -0
- data/processor/command-ruby-debug/reload.rb +40 -0
- data/processor/command-ruby-debug/save.rb +90 -0
- data/processor/command-ruby-debug/set.rb +237 -0
- data/processor/command-ruby-debug/show.rb +251 -0
- data/processor/command-ruby-debug/source.rb +36 -0
- data/processor/command-ruby-debug/threads.rb +189 -0
- data/processor/command-ruby-debug/trace.rb +57 -0
- data/processor/command-ruby-debug/variables.rb +199 -0
- data/processor/command.rb +270 -0
- data/processor/command/.gitignore +1 -0
- data/processor/command/alias.rb +54 -0
- data/processor/command/backtrace.rb +123 -0
- data/processor/command/base/cmd.rb +177 -0
- data/processor/command/base/subcmd.rb +230 -0
- data/processor/command/base/submgr.rb +188 -0
- data/processor/command/base/subsubcmd.rb +128 -0
- data/processor/command/base/subsubmgr.rb +199 -0
- data/processor/command/break.rb +114 -0
- data/processor/command/catch.rb +71 -0
- data/processor/command/complete.rb +39 -0
- data/processor/command/continue.rb +57 -0
- data/processor/command/directory.rb +50 -0
- data/processor/command/disable.rb +85 -0
- data/processor/command/display.rb +78 -0
- data/processor/command/down.rb +54 -0
- data/processor/command/edit.rb +79 -0
- data/processor/command/enable.rb +48 -0
- data/processor/command/eval.rb +90 -0
- data/processor/command/exit.rb +66 -0
- data/processor/command/finish.rb +59 -0
- data/processor/command/frame.rb +97 -0
- data/processor/command/help.rb +230 -0
- data/processor/command/help/.gitignore +1 -0
- data/processor/command/help/README +10 -0
- data/processor/command/help/command.txt +58 -0
- data/processor/command/help/examples.txt +16 -0
- data/processor/command/help/filename.txt +40 -0
- data/processor/command/help/location.txt +37 -0
- data/processor/command/help/suffixes.txt +17 -0
- data/processor/command/info.rb +28 -0
- data/processor/command/info_subcmd/.gitignore +1 -0
- data/processor/command/info_subcmd/args.rb +39 -0
- data/processor/command/info_subcmd/breakpoints.rb +80 -0
- data/processor/command/info_subcmd/catch.rb +36 -0
- data/processor/command/info_subcmd/files.rb +39 -0
- data/processor/command/info_subcmd/globals.rb +64 -0
- data/processor/command/info_subcmd/line.rb +30 -0
- data/processor/command/info_subcmd/locals.rb +69 -0
- data/processor/command/info_subcmd/macro.rb +62 -0
- data/processor/command/info_subcmd/program.rb +51 -0
- data/processor/command/info_subcmd/ruby.rb +57 -0
- data/processor/command/info_subcmd/source.rb +74 -0
- data/processor/command/info_subcmd/stack.rb +25 -0
- data/processor/command/info_subcmd/threads.rb +75 -0
- data/processor/command/kill.rb +78 -0
- data/processor/command/list.rb +117 -0
- data/processor/command/macro.rb +68 -0
- data/processor/command/next.rb +79 -0
- data/processor/command/parsetree.rb +56 -0
- data/processor/command/pp.rb +40 -0
- data/processor/command/pr.rb +37 -0
- data/processor/command/ps.rb +40 -0
- data/processor/command/restart.rb +86 -0
- data/processor/command/save.rb +58 -0
- data/processor/command/set.rb +47 -0
- data/processor/command/set_subcmd/.gitignore +1 -0
- data/processor/command/set_subcmd/abbrev.rb +25 -0
- data/processor/command/set_subcmd/auto.rb +27 -0
- data/processor/command/set_subcmd/auto_subcmd/.gitignore +1 -0
- data/processor/command/set_subcmd/auto_subcmd/eval.rb +53 -0
- data/processor/command/set_subcmd/auto_subcmd/irb.rb +33 -0
- data/processor/command/set_subcmd/auto_subcmd/list.rb +33 -0
- data/processor/command/set_subcmd/basename.rb +25 -0
- data/processor/command/set_subcmd/callstyle.rb +46 -0
- data/processor/command/set_subcmd/confirm.rb +24 -0
- data/processor/command/set_subcmd/debug.rb +47 -0
- data/processor/command/set_subcmd/different.rb +61 -0
- data/processor/command/set_subcmd/highlight.rb +43 -0
- data/processor/command/set_subcmd/max.rb +26 -0
- data/processor/command/set_subcmd/max_subcmd/list.rb +49 -0
- data/processor/command/set_subcmd/max_subcmd/stack.rb +50 -0
- data/processor/command/set_subcmd/max_subcmd/string.rb +76 -0
- data/processor/command/set_subcmd/max_subcmd/width.rb +49 -0
- data/processor/command/set_subcmd/reload.rb +42 -0
- data/processor/command/set_subcmd/timer.rb +58 -0
- data/processor/command/set_subcmd/trace.rb +37 -0
- data/processor/command/set_subcmd/trace_subcmd/buffer.rb +42 -0
- data/processor/command/set_subcmd/trace_subcmd/print.rb +41 -0
- data/processor/command/shell.rb +139 -0
- data/processor/command/show.rb +39 -0
- data/processor/command/show_subcmd/.gitignore +1 -0
- data/processor/command/show_subcmd/abbrev.rb +20 -0
- data/processor/command/show_subcmd/alias.rb +46 -0
- data/processor/command/show_subcmd/args.rb +34 -0
- data/processor/command/show_subcmd/auto.rb +28 -0
- data/processor/command/show_subcmd/auto_subcmd/eval.rb +27 -0
- data/processor/command/show_subcmd/auto_subcmd/irb.rb +23 -0
- data/processor/command/show_subcmd/auto_subcmd/list.rb +22 -0
- data/processor/command/show_subcmd/basename.rb +20 -0
- data/processor/command/show_subcmd/callstyle.rb +22 -0
- data/processor/command/show_subcmd/confirm.rb +18 -0
- data/processor/command/show_subcmd/debug.rb +26 -0
- data/processor/command/show_subcmd/debug_subcmd/dbgr.rb +21 -0
- data/processor/command/show_subcmd/debug_subcmd/skip.rb +22 -0
- data/processor/command/show_subcmd/debug_subcmd/step.rb +22 -0
- data/processor/command/show_subcmd/different.rb +26 -0
- data/processor/command/show_subcmd/directories.rb +22 -0
- data/processor/command/show_subcmd/highlight.rb +24 -0
- data/processor/command/show_subcmd/max.rb +27 -0
- data/processor/command/show_subcmd/max_subcmd/list.rb +38 -0
- data/processor/command/show_subcmd/max_subcmd/stack.rb +36 -0
- data/processor/command/show_subcmd/max_subcmd/string.rb +42 -0
- data/processor/command/show_subcmd/max_subcmd/width.rb +37 -0
- data/processor/command/show_subcmd/reload.rb +18 -0
- data/processor/command/show_subcmd/timer.rb +18 -0
- data/processor/command/show_subcmd/trace.rb +29 -0
- data/processor/command/show_subcmd/trace_subcmd/buffer.rb +65 -0
- data/processor/command/show_subcmd/trace_subcmd/print.rb +23 -0
- data/processor/command/show_subcmd/version.rb +23 -0
- data/processor/command/source.rb +134 -0
- data/processor/command/step.rb +81 -0
- data/processor/command/tbreak.rb +19 -0
- data/processor/command/unalias.rb +44 -0
- data/processor/command/undisplay.rb +59 -0
- data/processor/command/up.rb +72 -0
- data/processor/default.rb +56 -0
- data/processor/display.rb +17 -0
- data/processor/eval.rb +113 -0
- data/processor/eventbuf.rb +105 -0
- data/processor/frame.rb +172 -0
- data/processor/help.rb +92 -0
- data/processor/helper.rb +76 -0
- data/processor/hook.rb +134 -0
- data/processor/load_cmds.rb +258 -0
- data/processor/location.rb +174 -0
- data/processor/main.rb +455 -0
- data/processor/mock.rb +136 -0
- data/processor/msg.rb +61 -0
- data/processor/processor.rb +674 -0
- data/processor/running.rb +168 -0
- data/processor/stepping.rb +18 -0
- data/processor/subcmd.rb +161 -0
- data/processor/validate.rb +355 -0
- data/processor/virtual.rb +34 -0
- data/test/data/.gitignore +1 -0
- data/test/data/break_bad.cmd +19 -0
- data/test/data/break_bad.right +29 -0
- data/test/data/break_loop_bug.cmd +5 -0
- data/test/data/break_loop_bug.right +15 -0
- data/test/data/dollar-0.right +2 -0
- data/test/data/dollar-0a.right +2 -0
- data/test/data/dollar-0b.right +2 -0
- data/test/data/edit.cmd +14 -0
- data/test/data/edit.right +24 -0
- data/test/data/file-with-space.cmd +6 -0
- data/test/data/file-with-space.right +4 -0
- data/test/data/printvar.cmd +17 -0
- data/test/data/printvar.right +31 -0
- data/test/data/raise.cmd +11 -0
- data/test/data/raise.right +19 -0
- data/test/data/source.cmd +5 -0
- data/test/data/source.right +18 -0
- data/test/data/stepping-1.9.right +50 -0
- data/test/data/stepping.cmd +21 -0
- data/test/data/stepping.right +48 -0
- data/test/data/trepan8-save.1 +6 -0
- data/test/example/bp_loop_issue.rb +3 -0
- data/test/example/break-bug.rb +7 -0
- data/test/example/brkpt-class-bug.rb +8 -0
- data/test/example/classes.rb +11 -0
- data/test/example/dollar-0.rb +5 -0
- data/test/example/except-bug1.rb +4 -0
- data/test/example/except-bug2.rb +7 -0
- data/test/example/file with space.rb +1 -0
- data/test/example/gcd.rb +18 -0
- data/test/example/info-var-bug.rb +47 -0
- data/test/example/info-var-bug2.rb +2 -0
- data/test/example/null.rb +1 -0
- data/test/example/pm-bug.rb +3 -0
- data/test/example/pm.rb +11 -0
- data/test/example/raise.rb +3 -0
- data/test/integration/.gitignore +4 -0
- data/test/integration/config.yaml +8 -0
- data/test/integration/helper.rb +154 -0
- data/test/integration/test-break_bad.rb +26 -0
- data/test/integration/test-dollar-0.rb +31 -0
- data/test/integration/test-edit.rb +17 -0
- data/test/integration/test-file-with-space.rb +26 -0
- data/test/integration/test-printvar.rb +17 -0
- data/test/integration/test-raise.rb +21 -0
- data/test/integration/test-source.rb +16 -0
- data/test/integration/test-stepping.rb +24 -0
- data/test/unit/.gitignore +1 -0
- data/test/unit/cmd-helper.rb +52 -0
- data/test/unit/mock-helper.rb +12 -0
- data/test/unit/test-app-cmd_parse.rb +97 -0
- data/test/unit/test-app-cmd_parser.rb +23 -0
- data/test/unit/test-app-complete.rb +39 -0
- data/test/unit/test-app-frame.rb +32 -0
- data/test/unit/test-app-options.rb +92 -0
- data/test/unit/test-app-run.rb +14 -0
- data/test/unit/test-app-util.rb +44 -0
- data/test/unit/test-base-cmd.rb +45 -0
- data/test/unit/test-base-subcmd.rb +57 -0
- data/test/unit/test-base-submgr.rb +23 -0
- data/test/unit/test-base-subsubcmd.rb +17 -0
- data/test/unit/test-cmd-alias.rb +48 -0
- data/test/unit/test-cmd-exit.rb +27 -0
- data/test/unit/test-cmd-help.rb +104 -0
- data/test/unit/test-cmd-kill.rb +46 -0
- data/test/unit/test-cmd-source.rb +34 -0
- data/test/unit/test-completion.rb +42 -0
- data/test/unit/test-intf-user.rb +46 -0
- data/test/unit/test-io-input.rb +27 -0
- data/test/unit/test-io-tcp.rb +33 -0
- data/test/unit/test-io-tcpclient.rb +54 -0
- data/test/unit/test-io-tcpfns.rb +17 -0
- data/test/unit/test-io-tcpserver.rb +50 -0
- data/test/unit/test-proc-eval.rb +36 -0
- data/test/unit/test-proc-hook.rb +30 -0
- data/test/unit/test-proc-load_cmds.rb +50 -0
- data/test/unit/test-proc-location.rb +79 -0
- data/test/unit/test-subcmd-help.rb +44 -0
- data/trepan8.gemspec +52 -0
- metadata +391 -0
|
@@ -0,0 +1 @@
|
|
|
1
|
+
/*~
|
|
@@ -0,0 +1,155 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
|
|
3
|
+
# Implements debugger "break" command.
|
|
4
|
+
class AddBreakpoint < OldCommand
|
|
5
|
+
self.allow_in_control = true
|
|
6
|
+
|
|
7
|
+
def regexp
|
|
8
|
+
/ ^\s*
|
|
9
|
+
b(?:reak)?
|
|
10
|
+
(?: \s+ #{Position_regexp})? \s*
|
|
11
|
+
(?: \s+ (.*))? \s*
|
|
12
|
+
$
|
|
13
|
+
/x
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def execute
|
|
17
|
+
if @match[1]
|
|
18
|
+
line, _, _, expr = @match.captures
|
|
19
|
+
else
|
|
20
|
+
_, file, line, expr = @match.captures
|
|
21
|
+
end
|
|
22
|
+
if expr
|
|
23
|
+
if expr !~ /^\s*if\s+(.+)/
|
|
24
|
+
if file or line
|
|
25
|
+
errmsg "Expecting 'if' in breakpoint condition; got: #{expr}.\n"
|
|
26
|
+
else
|
|
27
|
+
errmsg "Invalid breakpoint location: #{expr}.\n"
|
|
28
|
+
end
|
|
29
|
+
return
|
|
30
|
+
else
|
|
31
|
+
expr = $1
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
brkpt_filename = nil
|
|
36
|
+
if file.nil?
|
|
37
|
+
unless @state.context
|
|
38
|
+
errmsg "We are not in a state that has an associated file.\n"
|
|
39
|
+
return
|
|
40
|
+
end
|
|
41
|
+
brkpt_filename = @state.file
|
|
42
|
+
file = File.basename(@state.file)
|
|
43
|
+
if line.nil?
|
|
44
|
+
# Set breakpoint at current line
|
|
45
|
+
line = @state.line.to_s
|
|
46
|
+
end
|
|
47
|
+
elsif line !~ /^\d+$/
|
|
48
|
+
# See if "line" is a method/function name
|
|
49
|
+
klass = debug_silent_eval(file)
|
|
50
|
+
if klass && klass.kind_of?(Module)
|
|
51
|
+
class_name = klass.name if klass
|
|
52
|
+
else
|
|
53
|
+
errmsg "Unknown class #{file}.\n"
|
|
54
|
+
throw :debug_error
|
|
55
|
+
end
|
|
56
|
+
else
|
|
57
|
+
# FIXME: This should be done in LineCache.
|
|
58
|
+
file = File.expand_path(file) if file.index(File::SEPARATOR) || \
|
|
59
|
+
File::ALT_SEPARATOR && file.index(File::ALT_SEPARATOR)
|
|
60
|
+
brkpt_filename = file
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
if line =~ /^\d+$/
|
|
64
|
+
line = line.to_i
|
|
65
|
+
if LineCache.cache(brkpt_filename, OldCommand.settings[:reload_source_on_change])
|
|
66
|
+
last_line = LineCache.size(brkpt_filename)
|
|
67
|
+
if line > last_line
|
|
68
|
+
errmsg("There are only %d lines in file \"%s\".\n", last_line, file)
|
|
69
|
+
return
|
|
70
|
+
end
|
|
71
|
+
unless LineCache.trace_line_numbers(brkpt_filename).member?(line)
|
|
72
|
+
errmsg("Line %d is not a stopping point in file \"%s\".\n", line, file)
|
|
73
|
+
return
|
|
74
|
+
end
|
|
75
|
+
else
|
|
76
|
+
errmsg("No source file named %s\n" % file)
|
|
77
|
+
return unless confirm("Set breakpoint anyway? (y/n) ")
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
unless @state.context
|
|
81
|
+
errmsg "We are not in a state we can add breakpoints.\n"
|
|
82
|
+
return
|
|
83
|
+
end
|
|
84
|
+
brkpt_filename = File.basename(brkpt_filename) if
|
|
85
|
+
OldCommand.settings[:basename]
|
|
86
|
+
b = Debugger.add_breakpoint brkpt_filename, line, expr
|
|
87
|
+
print "Breakpoint %d file %s, line %s\n", b.id, brkpt_filename, line.to_s
|
|
88
|
+
unless syntax_valid?(expr)
|
|
89
|
+
errmsg("Expression \"#{expr}\" syntactically incorrect; breakpoint disabled.\n")
|
|
90
|
+
b.enabled = false
|
|
91
|
+
end
|
|
92
|
+
else
|
|
93
|
+
method = line.intern.id2name
|
|
94
|
+
b = Debugger.add_breakpoint class_name, method, expr
|
|
95
|
+
print "Breakpoint %d at %s::%s\n", b.id, class_name, method.to_s
|
|
96
|
+
end
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
class << self
|
|
100
|
+
def help_command
|
|
101
|
+
'break'
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
def help(cmd)
|
|
105
|
+
%{
|
|
106
|
+
b[reak] file:line [if expr]
|
|
107
|
+
b[reak] class(.|#)method [if expr]
|
|
108
|
+
\tset breakpoint to some position, (optionally) if expr == true
|
|
109
|
+
}
|
|
110
|
+
end
|
|
111
|
+
end
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
# Implements debugger "delete" command.
|
|
115
|
+
class DeleteBreakpointCommand < OldCommand
|
|
116
|
+
self.allow_in_control = true
|
|
117
|
+
|
|
118
|
+
def regexp
|
|
119
|
+
/^\s *del(?:ete)? (?:\s+(.*))?$/ix
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
def execute
|
|
123
|
+
unless @state.context
|
|
124
|
+
errmsg "We are not in a state we can delete breakpoints.\n"
|
|
125
|
+
return
|
|
126
|
+
end
|
|
127
|
+
brkpts = @match[1]
|
|
128
|
+
unless brkpts
|
|
129
|
+
if confirm("Delete all breakpoints? (y or n) ")
|
|
130
|
+
Debugger.breakpoints.clear
|
|
131
|
+
end
|
|
132
|
+
else
|
|
133
|
+
brkpts.split(/[ \t]+/).each do |pos|
|
|
134
|
+
pos = get_int(pos, "Delete", 1)
|
|
135
|
+
return unless pos
|
|
136
|
+
unless Debugger.remove_breakpoint(pos)
|
|
137
|
+
errmsg "No breakpoint number %d\n", pos
|
|
138
|
+
end
|
|
139
|
+
end
|
|
140
|
+
end
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
class << self
|
|
144
|
+
def help_command
|
|
145
|
+
'delete'
|
|
146
|
+
end
|
|
147
|
+
|
|
148
|
+
def help(cmd)
|
|
149
|
+
%{
|
|
150
|
+
del[ete][ nnn...]\tdelete some or all breakpoints
|
|
151
|
+
}
|
|
152
|
+
end
|
|
153
|
+
end
|
|
154
|
+
end
|
|
155
|
+
end
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
class CatchCommand < OldCommand # :nodoc:
|
|
3
|
+
self.allow_in_control = true
|
|
4
|
+
|
|
5
|
+
def regexp
|
|
6
|
+
/^\s* cat(?:ch)?
|
|
7
|
+
(?:\s+ (\S+))?
|
|
8
|
+
(?:\s+ (off))? \s* $/ix
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def execute
|
|
12
|
+
excn = @match[1]
|
|
13
|
+
if not excn
|
|
14
|
+
# No args given.
|
|
15
|
+
info_catch
|
|
16
|
+
elsif not @match[2]
|
|
17
|
+
# One arg given.
|
|
18
|
+
if 'off' == excn
|
|
19
|
+
Debugger.catchpoints.clear if
|
|
20
|
+
confirm("Delete all catchpoints? (y or n) ")
|
|
21
|
+
else
|
|
22
|
+
binding = @state.context ? get_binding : TOPLEVEL_BINDING
|
|
23
|
+
unless debug_eval("#{excn}.is_a?(Class)", binding)
|
|
24
|
+
print "Warning #{excn} is not known to be a Class\n"
|
|
25
|
+
end
|
|
26
|
+
Debugger.add_catchpoint(excn)
|
|
27
|
+
print "Catch exception %s.\n", excn
|
|
28
|
+
end
|
|
29
|
+
elsif @match[2] != 'off'
|
|
30
|
+
errmsg "Off expected. Got %s\n", @match[2]
|
|
31
|
+
elsif Debugger.catchpoints.member?(excn)
|
|
32
|
+
Debugger.catchpoints.delete(excn)
|
|
33
|
+
print "Catch for exception %s removed.\n", excn
|
|
34
|
+
else
|
|
35
|
+
errmsg "Catch for exception %s not found.\n", excn
|
|
36
|
+
end
|
|
37
|
+
end
|
|
38
|
+
|
|
39
|
+
class << self
|
|
40
|
+
def help_command
|
|
41
|
+
'catch'
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def help(cmd)
|
|
45
|
+
%{
|
|
46
|
+
cat[ch]\t\tsame as "info catch"
|
|
47
|
+
cat[ch] <exception-name> [on|off]
|
|
48
|
+
\tIntercept <exception-name> when there would otherwise be no handler.
|
|
49
|
+
\tWith an "on" or "off", turn handling the exception on or off.
|
|
50
|
+
cat[ch] off\tdelete all catchpoints
|
|
51
|
+
}
|
|
52
|
+
end
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
end
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
|
|
3
|
+
class ConditionCommand < OldCommand # :nodoc:
|
|
4
|
+
|
|
5
|
+
def regexp
|
|
6
|
+
/^\s* cond(?:ition)? (?:\s+(\d+)\s*(.*))?$/ix
|
|
7
|
+
end
|
|
8
|
+
|
|
9
|
+
def execute
|
|
10
|
+
if not @match[1]
|
|
11
|
+
errmsg "\"condition\" must be followed a breakpoint number and expression\n"
|
|
12
|
+
else
|
|
13
|
+
breakpoints = Debugger.breakpoints.sort_by{|b| b.id }
|
|
14
|
+
largest = breakpoints.inject(0) do |largest, b|
|
|
15
|
+
largest = b.id if b.id > largest
|
|
16
|
+
end
|
|
17
|
+
if 0 == largest
|
|
18
|
+
print "No breakpoints have been set.\n"
|
|
19
|
+
return
|
|
20
|
+
end
|
|
21
|
+
pos = get_int(@match[1], "Condition", 1, largest)
|
|
22
|
+
return unless pos
|
|
23
|
+
breakpoints.each do |b|
|
|
24
|
+
if b.id == pos
|
|
25
|
+
b.expr = @match[2].empty? ? nil : @match[2]
|
|
26
|
+
break
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
class << self
|
|
34
|
+
def help_command
|
|
35
|
+
'condition'
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def help(cmd)
|
|
39
|
+
%{
|
|
40
|
+
Condition breakpoint-number expression
|
|
41
|
+
Specify breakpoint number N to break only if COND is true.
|
|
42
|
+
N is an integer and COND is an expression to be evaluated whenever
|
|
43
|
+
breakpoint N is reached. If the empty string is used, the condition is removed.
|
|
44
|
+
}
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
end # module Debugger
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
class InterruptCommand < OldCommand # :nodoc:
|
|
3
|
+
self.allow_in_control = true
|
|
4
|
+
self.allow_in_post_mortem = false
|
|
5
|
+
self.event = false
|
|
6
|
+
self.need_context = true
|
|
7
|
+
|
|
8
|
+
def regexp
|
|
9
|
+
/^\s*i(?:nterrupt)?\s*$/
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def execute
|
|
13
|
+
unless Debugger.interrupt_last
|
|
14
|
+
context = Debugger.thread_context(Thread.main)
|
|
15
|
+
context.interrupt
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
class << self
|
|
20
|
+
def help_command
|
|
21
|
+
'interrupt'
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def help(cmd)
|
|
25
|
+
%{
|
|
26
|
+
i[nterrupt]\tinterrupt the program
|
|
27
|
+
}
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
end
|
|
@@ -0,0 +1,120 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
module DisplayFunctions # :nodoc:
|
|
3
|
+
def display_expression(exp)
|
|
4
|
+
print "%s = %s\n", exp, debug_silent_eval(exp).to_s
|
|
5
|
+
end
|
|
6
|
+
|
|
7
|
+
def active_display_expressions?
|
|
8
|
+
@state.display.select{|d| d[0]}.size > 0
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def print_display_expressions
|
|
12
|
+
n = 1
|
|
13
|
+
for d in @state.display
|
|
14
|
+
if d[0]
|
|
15
|
+
print "%d: ", n
|
|
16
|
+
display_expression(d[1])
|
|
17
|
+
end
|
|
18
|
+
n += 1
|
|
19
|
+
end
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
class AddDisplayCommand < OldCommand # :nodoc:
|
|
24
|
+
def regexp
|
|
25
|
+
/^\s*disp(?:lay)?\s+(.+)$/
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def execute
|
|
29
|
+
exp = @match[1]
|
|
30
|
+
@state.display.push [true, exp]
|
|
31
|
+
print "%d: ", @state.display.size
|
|
32
|
+
display_expression(exp)
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
class << self
|
|
36
|
+
def help_command
|
|
37
|
+
'display'
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def help(cmd)
|
|
41
|
+
%{
|
|
42
|
+
disp[lay] <expression>\tadd expression into display expression list
|
|
43
|
+
}
|
|
44
|
+
end
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
class DisplayCommand < OldCommand # :nodoc:
|
|
49
|
+
def self.always_run
|
|
50
|
+
Trepan.annotate = 0 unless Trepan.annotate
|
|
51
|
+
if Trepan.annotate > 1
|
|
52
|
+
0
|
|
53
|
+
else
|
|
54
|
+
2
|
|
55
|
+
end
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
def regexp
|
|
59
|
+
/^\s*disp(?:lay)?$/
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def execute
|
|
63
|
+
print_display_expressions
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
class << self
|
|
67
|
+
def help_command
|
|
68
|
+
'display'
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def help(cmd)
|
|
72
|
+
%{
|
|
73
|
+
disp[lay]\t\tdisplay expression list
|
|
74
|
+
}
|
|
75
|
+
end
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
class DeleteDisplayCommand < OldCommand # :nodoc:
|
|
80
|
+
|
|
81
|
+
def regexp
|
|
82
|
+
/^\s* undisp(?:lay)? \s* (?:(\S+))?$/x
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
def execute
|
|
86
|
+
unless pos = @match[1]
|
|
87
|
+
if confirm("Clear all expressions? (y/n) ")
|
|
88
|
+
for d in @state.display
|
|
89
|
+
d[0] = false
|
|
90
|
+
end
|
|
91
|
+
end
|
|
92
|
+
else
|
|
93
|
+
pos = get_int(pos, "Undisplay")
|
|
94
|
+
return unless pos
|
|
95
|
+
if @state.display[pos-1]
|
|
96
|
+
@state.display[pos-1][0] = nil
|
|
97
|
+
else
|
|
98
|
+
errmsg "Display expression %d is not defined.\n", pos
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
class << self
|
|
104
|
+
def help_command
|
|
105
|
+
'undisplay'
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
def help(cmd)
|
|
109
|
+
%{
|
|
110
|
+
undisp[lay][ nnn]
|
|
111
|
+
Cancel some expressions to be displayed when program stops.
|
|
112
|
+
Arguments are the code numbers of the expressions to stop displaying.
|
|
113
|
+
No argument means cancel all automatic-display expressions.
|
|
114
|
+
"delete display" has the same effect as this command.
|
|
115
|
+
Do "info display" to see current list of code numbers.
|
|
116
|
+
}
|
|
117
|
+
end
|
|
118
|
+
end
|
|
119
|
+
end
|
|
120
|
+
end
|
|
@@ -0,0 +1,202 @@
|
|
|
1
|
+
module Trepan
|
|
2
|
+
# Mix-in module to assist in command parsing.
|
|
3
|
+
module EnableDisableFunctions # :nodoc:
|
|
4
|
+
def enable_disable_breakpoints(is_enable, args)
|
|
5
|
+
breakpoints = Debugger.breakpoints.sort_by{|b| b.id }
|
|
6
|
+
largest = breakpoints.inject(0) do |largest, b|
|
|
7
|
+
largest = b.id if b.id > largest
|
|
8
|
+
end
|
|
9
|
+
if 0 == largest
|
|
10
|
+
errmsg "No breakpoints have been set.\n"
|
|
11
|
+
return
|
|
12
|
+
end
|
|
13
|
+
args.each do |pos|
|
|
14
|
+
pos = get_int(pos, "#{is_enable} breakpoints", 1, largest)
|
|
15
|
+
return nil unless pos
|
|
16
|
+
breakpoints.each do |b|
|
|
17
|
+
if b.id == pos
|
|
18
|
+
enabled = ("Enable" == is_enable)
|
|
19
|
+
if enabled
|
|
20
|
+
unless syntax_valid?(b.expr)
|
|
21
|
+
errmsg("Expression \"#{b.expr}\" syntactically incorrect; breakpoint remains disabled.\n")
|
|
22
|
+
break
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
b.enabled = ("Enable" == is_enable)
|
|
26
|
+
break
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def enable_disable_display(is_enable, args)
|
|
33
|
+
if 0 == @state.display.size
|
|
34
|
+
errmsg "No display expressions have been set.\n"
|
|
35
|
+
return
|
|
36
|
+
end
|
|
37
|
+
args.each do |pos|
|
|
38
|
+
pos = get_int(pos, "#{is_enable} display", 1, @state.display.size)
|
|
39
|
+
return nil unless pos
|
|
40
|
+
@state.display[pos-1][0] = ("Enable" == is_enable)
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
class EnableCommand < OldCommand # :nodoc:
|
|
47
|
+
Subcommands =
|
|
48
|
+
[
|
|
49
|
+
['breakpoints', 2, "Enable specified breakpoints",
|
|
50
|
+
"Give breakpoint numbers (separated by spaces) as arguments.
|
|
51
|
+
This is used to cancel the effect of the \"disable\" command."
|
|
52
|
+
],
|
|
53
|
+
['display', 2,
|
|
54
|
+
"Enable some expressions to be displayed when program stops",
|
|
55
|
+
"Arguments are the code numbers of the expressions to resume displaying.
|
|
56
|
+
Do \"info display\" to see current list of code numbers."],
|
|
57
|
+
].map do |name, min, short_help, long_help|
|
|
58
|
+
SubcmdStruct.new(name, min, short_help, long_help)
|
|
59
|
+
end unless defined?(Subcommands)
|
|
60
|
+
|
|
61
|
+
def regexp
|
|
62
|
+
/^\s* en(?:able)? (?:\s+(.*))?$/ix
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
def execute
|
|
66
|
+
if not @match[1]
|
|
67
|
+
errmsg "\"enable\" must be followed \"display\", \"breakpoints\"" +
|
|
68
|
+
" or breakpoint numbers.\n"
|
|
69
|
+
else
|
|
70
|
+
args = @match[1].split(/[ \t]+/)
|
|
71
|
+
param = args.shift
|
|
72
|
+
subcmd = find(Subcommands, param)
|
|
73
|
+
if subcmd
|
|
74
|
+
send("enable_#{subcmd.name}", args)
|
|
75
|
+
else
|
|
76
|
+
send("enable_breakpoints", args.unshift(param))
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def enable_breakpoints(args)
|
|
82
|
+
enable_disable_breakpoints("Enable", args)
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
def enable_display(args)
|
|
86
|
+
enable_disable_display("Enable", args)
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
class << self
|
|
90
|
+
def help_command
|
|
91
|
+
'enable'
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
def help(args)
|
|
95
|
+
if args[1]
|
|
96
|
+
s = args[1]
|
|
97
|
+
subcmd = Subcommands.find do |try_subcmd|
|
|
98
|
+
(s.size >= try_subcmd.min) and
|
|
99
|
+
(try_subcmd.name[0..s.size-1] == s)
|
|
100
|
+
end
|
|
101
|
+
if subcmd
|
|
102
|
+
str = subcmd.short_help + '.'
|
|
103
|
+
str += "\n" + subcmd.long_help if subcmd.long_help
|
|
104
|
+
return str
|
|
105
|
+
else
|
|
106
|
+
return "Invalid 'enable' subcommand '#{args[1]}'."
|
|
107
|
+
end
|
|
108
|
+
end
|
|
109
|
+
s = %{
|
|
110
|
+
Enable some things.
|
|
111
|
+
This is used to cancel the effect of the "disable" command.
|
|
112
|
+
--
|
|
113
|
+
List of enable subcommands:
|
|
114
|
+
--
|
|
115
|
+
}
|
|
116
|
+
for subcmd in Subcommands do
|
|
117
|
+
s += "enable #{subcmd.name} -- #{subcmd.short_help}\n"
|
|
118
|
+
end
|
|
119
|
+
return s
|
|
120
|
+
end
|
|
121
|
+
end
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
class DisableCommand < OldCommand # :nodoc:
|
|
125
|
+
Subcommands =
|
|
126
|
+
[
|
|
127
|
+
['breakpoints', 1, "Disable some breakpoints",
|
|
128
|
+
"Arguments are breakpoint numbers with spaces in between.
|
|
129
|
+
A disabled breakpoint is not forgotten, but has no effect until reenabled."],
|
|
130
|
+
['display', 1, "Disable some display expressions when program stops",
|
|
131
|
+
"Arguments are the code numbers of the expressions to stop displaying.
|
|
132
|
+
Do \"info display\" to see current list of code numbers."],
|
|
133
|
+
].map do |name, min, short_help, long_help|
|
|
134
|
+
SubcmdStruct.new(name, min, short_help, long_help)
|
|
135
|
+
end unless defined?(Subcommands)
|
|
136
|
+
|
|
137
|
+
def regexp
|
|
138
|
+
/^\s* dis(?:able)? (?:\s+(.*))?$/ix
|
|
139
|
+
end
|
|
140
|
+
|
|
141
|
+
def execute
|
|
142
|
+
if not @match[1]
|
|
143
|
+
errmsg "\"disable\" must be followed \"display\", \"breakpoints\"" +
|
|
144
|
+
" or breakpoint numbers.\n"
|
|
145
|
+
else
|
|
146
|
+
args = @match[1].split(/[ \t]+/)
|
|
147
|
+
param = args.shift
|
|
148
|
+
subcmd = find(Subcommands, param)
|
|
149
|
+
if subcmd
|
|
150
|
+
send("disable_#{subcmd.name}", args)
|
|
151
|
+
else
|
|
152
|
+
send("disable_breakpoints", args.unshift(param))
|
|
153
|
+
end
|
|
154
|
+
end
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
def disable_breakpoints(args)
|
|
158
|
+
enable_disable_breakpoints("Disable", args)
|
|
159
|
+
end
|
|
160
|
+
|
|
161
|
+
def disable_display(args)
|
|
162
|
+
enable_disable_display("Disable", args)
|
|
163
|
+
end
|
|
164
|
+
|
|
165
|
+
class << self
|
|
166
|
+
def help_command
|
|
167
|
+
'disable'
|
|
168
|
+
end
|
|
169
|
+
|
|
170
|
+
def help(args)
|
|
171
|
+
if args[1]
|
|
172
|
+
s = args[1]
|
|
173
|
+
subcmd = Subcommands.find do |try_subcmd|
|
|
174
|
+
(s.size >= try_subcmd.min) and
|
|
175
|
+
(try_subcmd.name[0..s.size-1] == s)
|
|
176
|
+
end
|
|
177
|
+
if subcmd
|
|
178
|
+
str = subcmd.short_help + '.'
|
|
179
|
+
str += "\n" + subcmd.long_help if subcmd.long_help
|
|
180
|
+
return str
|
|
181
|
+
else
|
|
182
|
+
return "Invalid 'disable' subcommand '#{args[1]}'."
|
|
183
|
+
end
|
|
184
|
+
end
|
|
185
|
+
s = %{
|
|
186
|
+
Disable some things.
|
|
187
|
+
|
|
188
|
+
A disabled item is not forgotten, but has no effect until reenabled.
|
|
189
|
+
Use the "enable" command to have it take effect again.
|
|
190
|
+
--
|
|
191
|
+
List of disable subcommands:
|
|
192
|
+
--
|
|
193
|
+
}
|
|
194
|
+
for subcmd in Subcommands do
|
|
195
|
+
s += "disable #{subcmd.name} -- #{subcmd.short_help}\n"
|
|
196
|
+
end
|
|
197
|
+
return s
|
|
198
|
+
end
|
|
199
|
+
end
|
|
200
|
+
end
|
|
201
|
+
|
|
202
|
+
end # module Debugger
|