class Metasm::Gui::DbgRegWidget
a widget that displays values of registers of a Debugger
also controls the Debugger
and commands slave windows (showing listing & memory)
Attributes
dbg[RW]
Public Instance Methods
click(ex, ey)
click to toggle source
# File metasm/gui/debug.rb, line 272 def click(ex, ey) if p = @reg_pos.find { |x, y, w, h, vx| x <= ex and x+w >= ex and y <= ey and y+h >= ey } @caret_reg = @reg_pos.index(p) @caret_x = ((ex - p[4]) / @font_width).to_i rs = @register_size[@registers[@caret_reg]] @caret_x = rs-1 if @caret_x > rs-1 @caret_x = 0 if @caret_x < 0 update_caret end end
commit_writes()
click to toggle source
# File metasm/gui/debug.rb, line 454 def commit_writes @write_pending.each { |k, v| if @registers.index(k) @dbg.set_reg_value(k, v) else @dbg.set_flag_value(k, v) end @reg_cache[k] = v } @write_pending.clear end
doubleclick(x, y)
click to toggle source
# File metasm/gui/debug.rb, line 287 def doubleclick(x, y) gui_update # XXX end
gui_update()
click to toggle source
# File metasm/gui/debug.rb, line 466 def gui_update @reg_cache.replace @registers.inject({}) { |h, r| h.update r => @dbg.get_reg_value(r) } @flags.each { |f| @reg_cache[f] = @dbg.get_flag_value(f) } redraw end
initialize_visible()
click to toggle source
# File metasm/gui/debug.rb, line 268 def initialize_visible gui_update end
initialize_widget(dbg, parent_widget)
click to toggle source
# File metasm/gui/debug.rb, line 241 def initialize_widget(dbg, parent_widget) @dbg = dbg @parent_widget = parent_widget @caret_x = @caret_reg = 0 @oldcaret_x = @oldcaret_reg = 42 @tid_stuff = {} swapin_tid @reg_pos = [] # list of x y w h vx of the reg drawing on widget, vx is x of value @default_color_association = ColorTheme.merge :label => :text, :data => :blue, :write_pending => :darkred, :changed => :darkgreen, :caret => :text, :inactive => :palegrey end
keypress(key)
click to toggle source
keyboard binding basic navigation (arrows, pgup etc)
# File metasm/gui/debug.rb, line 352 def keypress(key) case key when :left if @caret_x > 0 @caret_x -= 1 update_caret end when :right if @caret_x < @register_size[@registers[@caret_reg]]-1 @caret_x += 1 update_caret end when :up if @caret_reg > 0 @caret_reg -= 1 else @caret_reg = @registers.length+@flags.length-1 end @caret_x = 0 update_caret when :down if @caret_reg < @registers.length+@flags.length-1 @caret_reg += 1 else @caret_reg = 0 end @caret_x = 0 update_caret when :home @caret_x = 0 update_caret when :end @caret_x = @register_size[@registers[@caret_reg]]-1 update_caret when :tab if @caret_reg < @registers.length+@flags.length-1 @caret_reg += 1 else @caret_reg = 0 end @caret_x = 0 update_caret when :backspace # TODO when :enter commit_writes redraw when :esc @write_pending.clear redraw when ?\x20..?\x7e if ?a.kind_of?(String) v = key.ord case key when ?\x20; v = nil # keep current value when ?0..?9; v -= ?0.ord when ?a..?f; v -= ?a.ord-10 when ?A..?F; v -= ?A.ord-10 else return false end else case v = key when ?\x20; v = nil when ?0..?9; v -= ?0 when ?a..?f; v -= ?a - 10 when ?A..?F; v -= ?A - 10 else return false end end reg = @registers[@caret_reg] || @flags[@caret_reg-@registers.length] rsz = @register_size[reg] if v and rsz != 1 oo = 4*(rsz-@caret_x-1) ov = @write_pending[reg] || @reg_cache[reg] ov &= ~(0xf << oo) ov |= v << oo @write_pending[reg] = ov elsif v and (v == 0 or v == 1) # TODO change z flag by typing 'z' or 'Z' @write_pending[reg] = v rsz = 1 end if rsz == 1 @caret_reg += 1 @caret_reg = @registers.length if @caret_reg >= @registers.length + @flags.length elsif @caret_x < rsz-1 @caret_x += 1 else @caret_x = 0 end redraw else return false end true end
paint()
click to toggle source
# File metasm/gui/debug.rb, line 291 def paint x = 1 y = 0 w_w = width render = lambda { |str, color| draw_string_color(color, x, y, str) x += str.length * @font_width } @reg_pos = [] running = (@dbg.state != :stopped) regstrlen = @registers.map { |reg| reg.to_s.length + 1 }.max @registers.each { |reg| strlen = regstrlen + @register_size[reg] if x + strlen*@font_width >= w_w x = 1 y += @font_height end @reg_pos << [x, y, (strlen+1)*@font_width, @font_height, x+regstrlen*@font_width] render["#{reg}=".ljust(regstrlen), :label] v = @write_pending[reg] || @reg_cache[reg] col = running ? :inactive : @write_pending[reg] ? :write_pending : @reg_cache_old.fetch(reg, v) != v ? :changed : :data if v.kind_of?(::Integer) render["%0#{@register_size[reg]}x " % v, col] else render[v.to_s, col] end x += @font_width # space } @flags.each { |reg| if x + @font_width >= w_w # XXX nowrap flags ? x = 1 y += @font_height end @reg_pos << [x, y, @font_width, @font_height, x] v = @write_pending[reg] || @reg_cache[reg] col = running ? :inactive : @write_pending[reg] ? :write_pending : @reg_cache_old.fetch(reg, v) != v ? :changed : :data v = v == 0 ? reg.to_s.downcase : reg.to_s.upcase render[v, col] x += @font_width # space } if focus? # draw caret cx = @reg_pos[@caret_reg][4] + @caret_x*@font_width cy = @reg_pos[@caret_reg][1] draw_line_color(:caret, cx, cy, cx, cy+@font_height-1) end @oldcaret_x, @oldcaret_reg = @caret_x, @caret_reg @parent_widget.resize_child(self, width, y+@font_height) end
pre_dbg_run()
click to toggle source
# File metasm/gui/debug.rb, line 450 def pre_dbg_run @reg_cache_old.replace @reg_cache if @reg_cache end
rightclick(x, y)
click to toggle source
# File metasm/gui/debug.rb, line 283 def rightclick(x, y) doubleclick(x, y) # XXX end
swapin_tid()
click to toggle source
# File metasm/gui/debug.rb, line 257 def swapin_tid stf = @tid_stuff[[@dbg.pid, @dbg.tid]] ||= {} return if not @dbg.cpu @write_pending = stf[:write_pending] ||= {} # addr -> newvalue (bytewise) @registers = stf[:registers] ||= @dbg.register_list @flags = stf[:flags] ||= @dbg.flag_list @register_size = stf[:reg_sz] ||= @registers.inject(Hash.new(1)) { |h, r| h.update r => @dbg.register_size[r]/4 } @reg_cache = stf[:reg_cache] ||= Hash.new(0) @reg_cache_old = stf[:reg_cache_old] ||= {} end
update_caret()
click to toggle source
hint that the caret moved
# File metasm/gui/debug.rb, line 473 def update_caret return if @oldcaret_x == @caret_x and @oldcaret_reg == @caret_reg invalidate_caret(@oldcaret_x, 0, *@reg_pos[@oldcaret_reg].values_at(4, 1)) invalidate_caret(@caret_x, 0, *@reg_pos[@caret_reg].values_at(4, 1)) @oldcaret_x, @oldcaret_reg = @caret_x, @caret_reg end