2022-11-05 16:48:47 +00:00
|
|
|
# frozen_string_literal: true
|
|
|
|
|
2022-11-16 10:30:13 +00:00
|
|
|
require_relative 'array'
|
2022-11-16 11:40:52 +00:00
|
|
|
require_relative 'string'
|
2022-11-16 10:30:13 +00:00
|
|
|
|
2022-10-29 10:09:10 +00:00
|
|
|
# turn byte array into hex string
|
|
|
|
def str_hex(data)
|
2022-11-05 16:19:05 +00:00
|
|
|
data.unpack1('H*').scan(/../).join(' ').upcase
|
2022-10-29 10:09:10 +00:00
|
|
|
end
|
|
|
|
|
2022-11-16 10:30:13 +00:00
|
|
|
def data_to_ascii(data)
|
|
|
|
ascii = ''
|
|
|
|
data.unpack('C*').each do |c|
|
|
|
|
ascii += c < 32 || c > 126 ? '.' : c.chr
|
|
|
|
end
|
|
|
|
ascii
|
|
|
|
end
|
|
|
|
|
2022-11-16 11:40:52 +00:00
|
|
|
def hexdump_lines(data, width = 2, notes = [], opts = {})
|
2022-11-16 10:30:13 +00:00
|
|
|
byte_groups = data.unpack1('H*').scan(/../).groups_of(4)
|
|
|
|
lines = []
|
|
|
|
hex = ''
|
|
|
|
ascii = ''
|
|
|
|
w = 0
|
2022-11-16 11:40:52 +00:00
|
|
|
byte = 0
|
|
|
|
legend = []
|
|
|
|
notes.each do |info|
|
|
|
|
color = info.first
|
|
|
|
raise "Invalid color '#{color}' valid ones: #{AVAILABLE_COLORS}" unless AVAILABLE_COLORS.include? color
|
|
|
|
|
|
|
|
legend.push([color, info.last.send(color)])
|
|
|
|
end
|
|
|
|
unless legend.empty?
|
|
|
|
if opts[:long_legend]
|
|
|
|
legend.each do |leg|
|
|
|
|
lines.push("#{leg.first}: #{leg.last}".send(leg.first))
|
|
|
|
end
|
|
|
|
else
|
|
|
|
lines.push(legend.map(&:last).join(' '))
|
|
|
|
end
|
|
|
|
end
|
2022-11-16 10:30:13 +00:00
|
|
|
byte_groups.each do |byte_group|
|
|
|
|
hex += ' ' unless hex.empty?
|
|
|
|
ascii += data_to_ascii(str_bytes(byte_group.join).pack('C*'))
|
|
|
|
w += 1
|
2022-11-16 11:40:52 +00:00
|
|
|
notes.each do |info|
|
|
|
|
color = info.first
|
|
|
|
# p color
|
|
|
|
# p info
|
|
|
|
from = info[1]
|
|
|
|
to = info[1] + (info[2] - 1)
|
|
|
|
|
|
|
|
if from > byte + 3
|
|
|
|
# puts "a"
|
|
|
|
next
|
|
|
|
end
|
|
|
|
if to < byte
|
|
|
|
# puts "to: #{to} < byte: #{byte}"
|
|
|
|
next
|
|
|
|
end
|
|
|
|
|
|
|
|
from -= byte
|
|
|
|
to -= byte
|
|
|
|
from = 0 if from.negative?
|
|
|
|
to = 3 if to > 3
|
|
|
|
|
|
|
|
# puts "from: #{from} to: #{to}"
|
|
|
|
(from..to).each do |i|
|
2022-11-16 13:13:02 +00:00
|
|
|
next if byte_group[i].nil?
|
|
|
|
|
2022-11-16 11:40:52 +00:00
|
|
|
byte_group[i] = byte_group[i].send(color)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
byte += 4
|
|
|
|
hex += byte_group.join(' ')
|
2022-11-16 10:30:13 +00:00
|
|
|
next unless w >= width
|
|
|
|
|
|
|
|
w = 0
|
|
|
|
lines.push("#{hex} #{ascii}")
|
|
|
|
hex = ''
|
|
|
|
ascii = ''
|
|
|
|
end
|
|
|
|
lines.push("#{hex} #{ascii}") unless hex.empty?
|
|
|
|
lines
|
|
|
|
end
|
|
|
|
|
2022-10-29 10:09:10 +00:00
|
|
|
# turn hex string to byte array
|
|
|
|
def str_bytes(str)
|
2022-11-05 16:19:05 +00:00
|
|
|
str.scan(/../).map { |b| b.to_i(16) }
|
2022-10-29 10:09:10 +00:00
|
|
|
end
|
|
|
|
|
|
|
|
def bytes_to_str(data)
|
2022-11-05 16:57:12 +00:00
|
|
|
data.unpack('H*').join
|
2022-10-29 10:09:10 +00:00
|
|
|
end
|
|
|
|
|
2022-11-13 10:42:46 +00:00
|
|
|
# TODO: remove?
|
2022-10-29 10:09:10 +00:00
|
|
|
def get_byte(data, start = 0, num = 1)
|
2022-11-05 16:57:12 +00:00
|
|
|
data[start...(start + num)].unpack('H*').join.upcase
|
2022-10-29 10:09:10 +00:00
|
|
|
end
|
2022-11-16 11:40:52 +00:00
|
|
|
|
|
|
|
def todo_make_this_a_unit_test
|
|
|
|
notes = [
|
|
|
|
[:red, 0, 1, 'foo'],
|
|
|
|
[:green, 1, 1, 'bar'],
|
|
|
|
[:yellow, 2, 1, 'baz'],
|
|
|
|
[:pink, 3, 1, 'bang'],
|
|
|
|
[:green, 4, 1, 'bär'],
|
|
|
|
[:yellow, 6, 6, 'yee']
|
|
|
|
]
|
|
|
|
|
|
|
|
hexdump_lines("\x01\x41\x02\x03\x03\x03\x03\x03\x03\x03\x03\x03\x03\xef", 40, notes).each do |l|
|
|
|
|
puts l
|
|
|
|
end
|
|
|
|
|
|
|
|
hexdump_lines("\x01\x41\x02\x03\x03\x03\x03\x03\x03\x03\x03\x03\x03\xef", 40, notes, long_legend: true).each do |l|
|
|
|
|
puts l
|
|
|
|
end
|
2022-11-16 13:13:02 +00:00
|
|
|
|
|
|
|
# should not crash when annotating bytes out of range
|
|
|
|
hexdump_lines("\x01\x41", 40, notes, long_legend: false).each do |l|
|
|
|
|
puts l
|
|
|
|
end
|
2022-11-16 11:40:52 +00:00
|
|
|
end
|