Clean graph formatting
This commit is contained in:
parent
46d5e10279
commit
089ad6dc78
46
yjit.rb
46
yjit.rb
@ -58,28 +58,54 @@ module YJIT
|
|||||||
|
|
||||||
def self.graphviz_for(iseq)
|
def self.graphviz_for(iseq)
|
||||||
iseq = RubyVM::InstructionSequence.of(iseq)
|
iseq = RubyVM::InstructionSequence.of(iseq)
|
||||||
|
cs = YJIT::Disasm.new
|
||||||
|
|
||||||
|
highlight = ->(comment) { "<b>#{comment}</b>" }
|
||||||
|
linebreak = "<br align=\"left\"/>\n"
|
||||||
|
|
||||||
buff = ''
|
buff = ''
|
||||||
blocks = blocks_for(iseq)
|
blocks = blocks_for(iseq).sort_by(&:id)
|
||||||
buff << "digraph g {"
|
buff << "digraph g {\n"
|
||||||
buff << " node [shape=record];"
|
|
||||||
|
# Write the iseq info as a legend
|
||||||
|
buff << " legend [shape=record fontsize=\"30\" fillcolor=\"lightgrey\" style=\"filled\"];\n"
|
||||||
|
buff << " legend [label=\"{ Instruction Disassembly For: | {#{iseq.base_label}@#{iseq.absolute_path}:#{iseq.first_lineno}}}\"];\n"
|
||||||
|
|
||||||
|
# Subgraph contains disassembly
|
||||||
|
buff << " subgraph disasm {\n"
|
||||||
|
buff << " node [shape=record fontname=\"courier\"];\n"
|
||||||
blocks.each do |block|
|
blocks.each do |block|
|
||||||
buff << "b#{block.id} [label=\"#{disasm_block(block).gsub(/\n/, "\\l\n")}\"];"
|
disasm = disasm_block(cs, block, highlight)
|
||||||
block.outgoing_ids.each do |id|
|
|
||||||
buff << "b#{block.id} -> b#{id};"
|
# convert newlines to breaks that graphviz understands
|
||||||
end
|
disasm.gsub!(/\n/, linebreak)
|
||||||
|
|
||||||
|
# strip leading whitespace
|
||||||
|
disasm.gsub!(/^\s+/, '')
|
||||||
|
|
||||||
|
buff << "b#{block.id} [label=<#{disasm}>];\n"
|
||||||
|
buff << block.outgoing_ids.map { |id|
|
||||||
|
next_block = blocks.bsearch { |nb| id <=> nb.id }
|
||||||
|
if next_block.address == (block.address + block.code.length)
|
||||||
|
"b#{block.id} -> b#{id}[color=\"green\"];"
|
||||||
|
else
|
||||||
|
"b#{block.id} -> b#{id};"
|
||||||
|
end
|
||||||
|
}.join("\n")
|
||||||
|
buff << "\n"
|
||||||
end
|
end
|
||||||
|
buff << " }"
|
||||||
buff << "}"
|
buff << "}"
|
||||||
buff
|
buff
|
||||||
end
|
end
|
||||||
|
|
||||||
def self.disasm_block(block)
|
def self.disasm_block(cs, block, highlight)
|
||||||
cs = YJIT::Disasm.new
|
|
||||||
comments = comments_for(block.address, block.address + block.code.length)
|
comments = comments_for(block.address, block.address + block.code.length)
|
||||||
comment_idx = 0
|
comment_idx = 0
|
||||||
str = ''
|
str = ''
|
||||||
cs.disasm(block.code, block.address).each do |i|
|
cs.disasm(block.code, block.address).each do |i|
|
||||||
while (comment = comments[comment_idx]) && comment.address <= i.address
|
while (comment = comments[comment_idx]) && comment.address <= i.address
|
||||||
str << " ; #{comment.comment}\n"
|
str << " ; #{highlight.call(comment.comment)}\n"
|
||||||
comment_idx += 1
|
comment_idx += 1
|
||||||
end
|
end
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user