z80_disassembler 0.1.1 → 0.2.2

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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: e42aae94b0a155376a9908a01021170bc5c0ef1c585edf3e0fe29709800bd09b
4
- data.tar.gz: dc317870df745ae9e22e0f63529d87a55c576471d255e5b6c247d56315447684
3
+ metadata.gz: 6d345233ff0d5429ba5c05cdb82c304de2ef46b6ebe7761bda8b805c986c85e2
4
+ data.tar.gz: e43f8bf8fd592ec156d5bb6c942e6847691e853701a65e2b0afdaffd827c626e
5
5
  SHA512:
6
- metadata.gz: 870c6f6d8a9022a91b73c5b389c4ef14355287faac6e13addc3b9105a54b4a14759b7c3525146387d3eb41af0aa149b4e851cca425543de2ba50e8a3d2663d99
7
- data.tar.gz: f1dae199fb41fef2a94504e206ddc6e1a0909aa092d2d36662f097c10ee4b6b575f220fa1aac73b79f58de9a0afbb97a1c729afbb6ccb9d35aeac5e916ce8c22
6
+ metadata.gz: 991885755e9d4fbe5128b6b81fdb5e4804d6921850acbf9e07bc8c0c66fb290d293ea32be1fc56c1a9da06d55a64d4100b2558f488999812ba832d9a8ab2434c
7
+ data.tar.gz: db4bdd7cb73f1ba8bdf430c54578f02f1a74ca5de3373bf2b1e4dda855b400652fa0604ca6e1e7cd1b3b0a228f0f4aa79ffb22e9d1d4116c6a0663d625c73bc7
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- z80_disassembler (0.1.1)
4
+ z80_disassembler (0.2.0)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
data/README.md CHANGED
@@ -27,9 +27,10 @@ Or install it yourself as:
27
27
 
28
28
  - example: parse.C >> parse.C.txt and compare with parse.txt
29
29
  ```ruby
30
- Z80Disassembler::Disassembler.new(params[:file], params[:org]).start
30
+ z = Z80Disassembler::Disassembler.new(params[:file], 32768)
31
+ z.start # return [25114, "#621A", "LD IX,#6300", "DD 21 00 63", " ! c"
32
+ z.text # return asm text " LD IX,link_1 ; #621A / 25114 ; DD 21 00 63 ; ! c ;"
31
33
  ```
32
-
33
34
  ## Development
34
35
 
35
36
  After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake test` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
@@ -15,50 +15,84 @@ module Z80Disassembler
15
15
  T_RP = [ 'BC', 'DE', 'HL', 'SP'].freeze
16
16
  T_RP2 = [ 'BC', 'DE', 'HL', 'AF'].freeze
17
17
 
18
+ ASCII = [
19
+ ' ', '!', '"', '#', '$', '%', '&', "'", '(', ')', '*', '+', ',', '-', '.', '/',
20
+ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', ':', ';', '<', '=', '>', '?',
21
+ '@', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O',
22
+ 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '[', '\\',']', '^', '_',
23
+ '`', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o',
24
+ 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', '{', '|', '}', '~'
25
+ ].freeze
26
+
18
27
  def initialize(file_name, addr = 32_768)
19
28
  @file_name = file_name; @addr = addr.to_i
20
29
  @x = 0; @y = 0; @z = 0; @p = 0; @q = 0; @xx = nil
21
- @lambda = nil; @prefix = nil; @prev = nil, @bytes = []
30
+ @lambda = nil; @prefix = nil; @prev = nil
31
+ @bytes = []; @ascii = []; @result = []
22
32
  end
23
33
 
24
34
  def start
25
- result = {}
26
35
  File.open(@file_name).each_byte do |byte|
27
36
  load_vars(byte)
28
- str = case @prefix
29
- when 'cb' then @prefix = nil; cb_prefix
30
- when 'ed' then @prefix = nil; ed_prefix
31
- when 'dd' then @xx = 'IX'; xx_prefix(byte)
32
- when 'fd' then @xx = 'IY'; xx_prefix(byte)
33
- when 'xx' then temp = @temp; @temp = nil; displacement(byte, temp)
34
- when 2 then @prefix -= 1; @temp = byte.to_s(16).rjust(2, '0').upcase; nil
35
- when 1
36
- resp = @lambda.call(@arg, byte.to_s(16).rjust(2, '0').upcase)
37
- @prefix = nil; temp = @temp; @temp = nil
38
- if temp && resp.include?(')')
39
- resp = @xx ? displacement(temp.hex, resp) : resp.sub(')', "#{temp})").sub('(', '(#')
40
- elsif temp
41
- resp += temp
42
- end
43
- resp = hl_to_xx(resp, @xx) unless @xx.nil?
44
- @xx = nil
45
- resp
46
- else command
47
- end
37
+ str = command_from_byte(byte)
48
38
  @prev = byte.to_s(16)
49
- @bytes << @prev.rjust(2, '0')
39
+ @ascii << ((32..126).include?(byte) ? ASCII[byte - 32] : ' ')
40
+ @bytes << @prev.rjust(2, '0').upcase
50
41
  next unless str
51
42
 
52
- result[@addr] = ["##{@addr.to_s(16)}".upcase, str, @bytes.join(' ')]
43
+ @result << [@addr, "##{@addr.to_s(16)}".upcase, str, @bytes.join(' '), @ascii.join]
53
44
  @addr += @bytes.size
54
45
  @bytes = []
46
+ @ascii = []
55
47
  end
48
+ @result
49
+ end
56
50
 
57
- result
51
+ def text
52
+ org = @addr - @file_name.size
53
+ hash_links = {}
54
+ link_num = 0
55
+ int_addrs = org..@addr
56
+ with_links = @result.select { |z| z[2] =~ /#[0-F]{4}/ && int_addrs.include?(z[2].split('#').last[0..3].hex) }
57
+ with_links.each { |x| hash_links["##{x[2].split('#').last[0..3]}"] = "link_#{link_num += 1}" }
58
+ [
59
+ " device zxspectrum48",
60
+ " ORG #{org}",
61
+ "begin_file:\n"
62
+ ].join("\n") +
63
+ @result.map do |addr, addr16, str, bytes, ascii|
64
+ link = (hash_links[addr16] || '').ljust(16, ' ')
65
+ adr = '#' + str.split('#').last[0..3]
66
+ string = hash_links.keys.include?(adr) ? str.sub(adr, hash_links[adr]) : str
67
+ "#{link} #{string.ljust(16, ' ')}; #{addr16.ljust(5, ' ')} / #{addr.to_s.ljust(5, ' ')} ; #{bytes.ljust(14, ' ')} ; #{ascii.ljust(4, ' ')} ;"
68
+ end.join("\n")
58
69
  end
59
70
 
60
71
  private
61
72
 
73
+ def command_from_byte(byte)
74
+ case @prefix
75
+ when 'cb' then @prefix = nil; cb_prefix
76
+ when 'ed' then @prefix = nil; ed_prefix
77
+ when 'dd' then @xx = 'IX'; xx_prefix(byte)
78
+ when 'fd' then @xx = 'IY'; xx_prefix(byte)
79
+ when 'xx' then temp = @temp; @temp = nil; displacement(byte, temp)
80
+ when 2 then @prefix -= 1; @temp = byte.to_s(16).rjust(2, '0').upcase; nil
81
+ when 1
82
+ resp = @lambda.call(@arg, byte.to_s(16).rjust(2, '0').upcase)
83
+ @prefix = nil; temp = @temp; @temp = nil
84
+ if temp && resp.include?(')')
85
+ resp = @xx ? displacement(temp.hex, resp) : resp.sub(')', "#{temp})").sub('(', '(#')
86
+ elsif temp
87
+ resp += temp
88
+ end
89
+ resp = hl_to_xx(resp, @xx) unless @xx.nil?
90
+ @xx = nil
91
+ resp
92
+ else command
93
+ end
94
+ end
95
+
62
96
  def hl_to_xx(temp, reg)
63
97
  if temp.include?('HL')
64
98
  temp.sub('HL', reg)
@@ -70,6 +104,8 @@ module Z80Disassembler
70
104
  temp.sub(' H', " #{reg}H")
71
105
  elsif temp.include?(',H')
72
106
  temp.sub(',H', ",#{reg}H")
107
+ else
108
+ temp
73
109
  end
74
110
  end
75
111
 
@@ -97,8 +133,8 @@ module Z80Disassembler
97
133
  case @y
98
134
  when 0 then 'NOP'
99
135
  when 1 then 'EX AF, AF\''
100
- when 2 then calc_bytes(->(a, b){ "DJNZ ##{b}" }, nil, 1)
101
- when 3 then calc_bytes(->(a, b){ "JR ##{b}" }, nil, 1)
136
+ when 2 then calc_bytes(->(a, b){ "DJNZ ##{b}" }, nil, 1)
137
+ when 3 then calc_bytes(->(a, b){ "JR ##{b}" }, nil, 1)
102
138
  else calc_bytes(->(a, b){ "JR #{a},##{b}" }, T_CC[@y - 4], 1)
103
139
  end
104
140
  when 1 then @q ? "ADD HL,#{T_RP[@p]}" : calc_bytes(->(a, b){ "LD #{a},##{b}" }, T_RP[@p], 2)
@@ -163,7 +199,7 @@ module Z80Disassembler
163
199
  elsif ['dd', 'fd'].include?(@prev) && @temp
164
200
  temp = @temp; @temp = nil; @prefix = nil; xx = @xx; @xx = nil
165
201
  hl_to_xx(temp, xx)
166
- elsif @lambda && !@arg.include?('HL')
202
+ elsif @lambda && !@arg&.include?('HL')
167
203
  @prefix = 1; @temp
168
204
  else
169
205
  @prefix = 2; @temp
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Z80Disassembler
4
- VERSION = '0.1.1'
4
+ VERSION = '0.2.2'
5
5
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: z80_disassembler
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.1
4
+ version: 0.2.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - dvitvitskiy
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-06-03 00:00:00.000000000 Z
11
+ date: 2021-06-06 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description:
14
14
  email: