asmrb 0.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (3) hide show
  1. checksums.yaml +7 -0
  2. data/lib/asm.rb +251 -0
  3. metadata +45 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 792de4bbafddedb38b68b7d00165beafd20cb176
4
+ data.tar.gz: 8a7a97aead79fdd91dad623865cd0341a984bcb9
5
+ SHA512:
6
+ metadata.gz: 3459ccc9f2b3610cbb3fa2b3fe1a4bfaa317f4c2f1276de722be47dbd2fa326d9dcf83fcf224196785df33f277974a66617d4710e1f83b7cb6ff72b124106cae
7
+ data.tar.gz: f2ddfc22f474096eca16109ad2da68a8341997dd018f94dc191f71e0c8f40e3a3acdf5b95f15e2d58e432de3d07efbdddc19f36cdac9ad036b7ebf5bb3e8a5b3
data/lib/asm.rb ADDED
@@ -0,0 +1,251 @@
1
+ require 'colorize'
2
+ require 'pry'
3
+
4
+ class Asm
5
+ attr_reader :variables, :function, :stack, :name
6
+
7
+ def initialize
8
+ @@function = []
9
+ @variables = { }
10
+ @program = []
11
+ @labels = {}
12
+ @stack = []
13
+ @name = "undefined"
14
+ end
15
+
16
+ def new_var(dest)
17
+ eval("def #{dest}; #{@variables[dest]}; end")
18
+ end
19
+
20
+ def refvar(val)
21
+ val.is_a?(Symbol) ? @variables[val] : val
22
+ end
23
+
24
+ def req_args(func,amount)
25
+ raise Exception.new "[#{func}]: require #{amount} args to compare." if @stack.length < amount
26
+ end
27
+
28
+ OPS = {
29
+ "rdu" => lambda { | ops |
30
+ e = eval "@stack.reduce(&:#{ops})"
31
+ @stack.push e
32
+ },
33
+
34
+ "add" => lambda { | a , b |
35
+ @stack.push(refvar(a) + refvar(b))
36
+ },
37
+
38
+ "sub" => lambda { | a , b |
39
+ @stack.push(refvar(a) - refvar(b))
40
+ },
41
+
42
+ "mul" => lambda { | a , b |
43
+ @stack.push(refvar(a) * refvar(b))
44
+ },
45
+
46
+ "div" => lambda { | a , b |
47
+ @stack.push(refvar(a) / refvar(b))
48
+ },
49
+
50
+ "incr" => lambda { |dest, incval = 1|
51
+ @variables[dest] += incval
52
+ },
53
+
54
+ "decr" => lambda { |dest, decrval = 1|
55
+ @variables[dest] -= decrval
56
+ },
57
+
58
+ "mov" => lambda { | src , dest |
59
+ @variables[dest] =
60
+ src.is_a?(Symbol) ?
61
+ @variables[src] : src
62
+ #new_var dest
63
+ },
64
+
65
+ "jlt" => lambda { |less, more|
66
+ req_args "jlt", 2
67
+ @@pc = @labels[name] if @stack[@stack.length - 1] < @stack[@stack.length - 2]
68
+ @stack.drop 2
69
+ },
70
+
71
+ "jge" => lambda { |name|
72
+ req_args "jge", 1
73
+ x = @stack.pop
74
+ y = @stack.pop
75
+ @@pc = @labels[name] if x >= y
76
+ },
77
+
78
+ "lt" => lambda { |a, b|
79
+ req_args "lt", 2
80
+ @stack.push (a > b)
81
+ },
82
+
83
+
84
+ "jmp" => lambda { |name|
85
+ @@pc = @labels[name]
86
+ },
87
+
88
+ "pop" => lambda {|val|
89
+ @variables[val] = @stack.pop
90
+ #new_var val
91
+ },
92
+
93
+ "push" => lambda {|src|
94
+ @stack.push(
95
+ src.is_a?(Symbol) ? @variables[src] : src )
96
+ },
97
+
98
+ "arg" => lambda { |*args|
99
+ if @stack.length != args.length
100
+ raise Exception.new "require: #{args}"
101
+ else
102
+ args.reverse.each do | arg |
103
+ @variables[arg] = @stack.pop
104
+ end
105
+ end
106
+ },
107
+
108
+ "req" => lambda {|amount|
109
+ raise Exception.new "require #{amount} #{ pluralize(amount, "argument") }." if @stack.length != amount
110
+ },
111
+
112
+ "dbg" => lambda {
113
+ puts @stack
114
+ },
115
+
116
+ "func" => lambda {|&block|
117
+ @stack.push block
118
+ },
119
+
120
+ "call" => lambda {|fname|
121
+ _method = method(fname)
122
+ if _method.parameters.length > 0
123
+ args = []
124
+ _method.parameters.length.times do
125
+ args.push @stack.pop
126
+ end
127
+ invoke = _method.call(args)
128
+ else
129
+ invoke = _method.call
130
+ end
131
+ #binding.pry
132
+ @stack.push invoke if !invoke.nil?
133
+ },
134
+
135
+ "exit" => lambda {
136
+ exit
137
+ }
138
+
139
+ #and so on
140
+ }
141
+
142
+ def create_label(lbl)
143
+ @labels[lbl] = @program.length-1
144
+ end
145
+
146
+ def method_missing(name, *args)
147
+
148
+ sname = name.to_s
149
+
150
+ if OPS.keys.include?(sname)
151
+ @program << [sname, args]
152
+
153
+ # TESTING FEATURE:
154
+ elsif @@function.include?(name)
155
+ @program << [sname, @@function[name].execute]
156
+
157
+ else
158
+
159
+ case sname
160
+
161
+ when "label"
162
+ create_label args.first
163
+
164
+ when "defn"
165
+ @name = args.first
166
+ create_label args.first
167
+
168
+ else
169
+ return name
170
+
171
+ end
172
+ end
173
+ end
174
+
175
+ def load_program(&block)
176
+ self.instance_exec(&block)
177
+ end
178
+
179
+ def execute(debug=false)
180
+ puts "function: #{@name}".white
181
+ begin
182
+ @@pc = 0
183
+ until(@@pc == @program.length)
184
+ # get instruction:
185
+ instr = @program[@@pc]
186
+ puts "#{instr}".light_green if debug
187
+ # execute proc:
188
+ self.instance_exec(*instr[1], &OPS[instr[0]])
189
+ #binding.pry if debug
190
+ @@pc += 1
191
+ end
192
+ @stack.last
193
+ rescue Exception => e
194
+ debug e, instr
195
+ end
196
+ end
197
+
198
+ def debug(e,instr)
199
+ # error scope:
200
+ debug_start = @@pc >= 1 ? @@pc - 1 : 0
201
+ debug_end = @@pc <= @program.length - 2 ?
202
+ @@pc + 2
203
+ : @program.length < 4 ? @program.length : @@pc + 4
204
+
205
+ # ranging...
206
+ (debug_start..debug_end).each do | i |
207
+ line = " #{i+1}: #{@program[i]}"
208
+ color = i != @@pc ? :light_green : :magenta
209
+ puts line.colorize color
210
+ end
211
+
212
+ puts "\nline #{@@pc+1}: #{ops_info(instr[0])}: #{e.message}".colorize(:magenta)
213
+ #puts e.backtrace
214
+
215
+ # test via pry:
216
+ binding.pry
217
+ end
218
+
219
+ def ops_info(name)
220
+ parameters = []
221
+ OPS[name].parameters.each {|pair| parameters << pair.last }
222
+ "#{name} [#{parameters.join(', ')}]"
223
+ end
224
+
225
+ def arguments(args=[])
226
+ args.each do | arg |
227
+ @stack << arg
228
+ end
229
+ end
230
+
231
+ def invoke(args=[],debug=false)
232
+ arguments args
233
+ execute debug
234
+ end
235
+
236
+ def clear
237
+ @variables = { }
238
+ @stack = []
239
+ end
240
+
241
+ def self.assemble (&block)
242
+ Asm.new.assemble &block
243
+ end
244
+
245
+ def assemble(&block)
246
+ load_program(&block)
247
+ self.dup
248
+ end
249
+ end
250
+
251
+
metadata ADDED
@@ -0,0 +1,45 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: asmrb
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.0
5
+ platform: ruby
6
+ authors:
7
+ - The Trung
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+ date: 2015-01-31 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: Inteprete your assembly style code inside ruby.
14
+ email: deulamco@gmail.com
15
+ executables: []
16
+ extensions: []
17
+ extra_rdoc_files: []
18
+ files:
19
+ - lib/asm.rb
20
+ homepage: http://github.com/thetrung/asmrb.git
21
+ licenses:
22
+ - MIT
23
+ metadata: {}
24
+ post_install_message:
25
+ rdoc_options: []
26
+ require_paths:
27
+ - lib
28
+ required_ruby_version: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - ">="
31
+ - !ruby/object:Gem::Version
32
+ version: '0'
33
+ required_rubygems_version: !ruby/object:Gem::Requirement
34
+ requirements:
35
+ - - ">="
36
+ - !ruby/object:Gem::Version
37
+ version: '0'
38
+ requirements: []
39
+ rubyforge_project:
40
+ rubygems_version: 2.4.5
41
+ signing_key:
42
+ specification_version: 4
43
+ summary: assembly-like DSL in ruby
44
+ test_files: []
45
+ has_rdoc: