rasl 0.0.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,3 @@
1
+ module Rasl
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,29 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+ require 'rasl/version'
5
+
6
+ Gem::Specification.new do |spec|
7
+ spec.name = 'rasl'
8
+ spec.version = Rasl::VERSION
9
+ spec.author = 'akicho8'
10
+ spec.email = 'akicho8@gmail.com'
11
+ spec.homepage = 'https://github.com/akicho8/rasl'
12
+ spec.summary = 'CASL Assembler / Simulator'
13
+ spec.description = 'CASL Assembler / Simulator'
14
+ spec.platform = Gem::Platform::RUBY
15
+
16
+ spec.files = `git ls-files`.split($/)
17
+ spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
18
+ spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
+ spec.require_paths = ['lib']
20
+ spec.rdoc_options = ['--line-numbers', '--inline-source', '--charset=UTF-8', '--diagram', '--image-format=jpg']
21
+
22
+ spec.add_dependency 'activesupport'
23
+ spec.add_dependency 'activemodel'
24
+
25
+ spec.add_development_dependency 'bundler', '~> 1.3'
26
+ spec.add_development_dependency 'rake'
27
+ spec.add_development_dependency 'rspec'
28
+ spec.add_development_dependency 'byebug'
29
+ end
@@ -0,0 +1,700 @@
1
+ # -*- coding: utf-8 -*-
2
+
3
+ require "spec_helper"
4
+
5
+ describe Rasl do
6
+ before do
7
+ Rasl.configure do |config|
8
+ config.memory_size = 65536
9
+ config.bol_order = true
10
+ config.ds_init_value = -1
11
+ end
12
+
13
+ @p = Processor.new
14
+ end
15
+
16
+ it "regs_info" do
17
+ @p.regs_info.should == "GR0=0000 GR1=0000 GR2=0000 GR3=0000 GR4=0000 GR5=0000 GR6=0000 GR7=0000 PC=0000 SP=0000 FR=___(+)"
18
+ end
19
+
20
+ describe Value do
21
+ it "符号の有無はアクセサによって決まる" do
22
+ r = Value.new(-1)
23
+ [r.value, r.s_value, r.u_value].should == [65535, -1, 65535]
24
+ r = Value.new(65535)
25
+ [r.value, r.s_value, r.u_value].should == [65535, -1, 65535]
26
+ end
27
+ end
28
+
29
+ describe Register do
30
+ it do
31
+ r = Register.new(:ax, :pos => 0)
32
+ r.key.should == :ax
33
+ r.name.should == "AX"
34
+ r.pos.should == 0
35
+ r.to_s.should == "AX=0000"
36
+ end
37
+ end
38
+
39
+ describe Environment do
40
+ it "new" do
41
+ @p.code_size.should == 0
42
+ @p.boot_pc.should == 0
43
+ @p.gr[:sp].value == @p.memory.size
44
+ end
45
+ end
46
+
47
+ describe OperandPresets1 do
48
+ describe "基本命令" do
49
+ it "nop" do
50
+ asm " nop"
51
+ end
52
+
53
+ describe "ld" do
54
+ it "r_imm" do
55
+ asm "ld gr0, a", :dc => {:a => -77}
56
+ reg_is :gr0, -77
57
+ fire :sf
58
+ end
59
+ it "rix" do
60
+ asm "ld gr0, a, gr1", :dc => {:a => [-444, -77]}, :regs => {:gr1 => 1}
61
+ reg_is :gr0, -77
62
+ fire :sf
63
+ end
64
+ it "r1_r2" do
65
+ asm "ld gr1, gr0", :regs => {:gr0 => -77}
66
+ reg_is :gr1, -77
67
+ fire :sf
68
+ end
69
+ end
70
+
71
+ describe "st" do
72
+ it "r_imm" do
73
+ asm "st gr0, a", :dc => {:a => 0}, :regs => {:gr0 => -77}
74
+ var_check :a, -77
75
+ fr_blank
76
+ end
77
+ it "rix" do
78
+ asm "st gr0, a, gr1", :dc => {:a => 0, :b => 0}, :regs => {:gr0 => -77, :gr1 => 1}
79
+ var_check :b, -77
80
+ fr_blank
81
+ end
82
+ end
83
+
84
+ describe "lea" do
85
+ it "r_imm" do
86
+ asm "lea gr0, -77"
87
+ reg_is :gr0, -77
88
+ fire :sf
89
+ end
90
+ it "rix" do
91
+ asm "lea gr0, 1, gr1", :regs => {:gr1 => -77 - 1}
92
+ reg_is :gr0, -77
93
+ fire :sf
94
+ end
95
+ end
96
+
97
+ describe "adda" do
98
+ describe "r1_r2" do
99
+ describe "上限" do
100
+ it "of_true" do
101
+ asm "adda gr0, gr1", :regs => {:gr0 => 1, :gr1 => 32767}
102
+ reg_is :gr0, -32768
103
+ fire :of, :sf
104
+ end
105
+ it "of_false" do
106
+ asm "adda gr0, gr1", :regs => {:gr0 => 0, :gr1 => 32767}
107
+ reg_is :gr0, 32767
108
+ fire
109
+ end
110
+ end
111
+ describe "下限" do
112
+ it "of_true" do
113
+ asm "adda gr0, gr1", :regs => {:gr0 => -1, :gr1 => -32768}
114
+ reg_is :gr0, 32767
115
+ fire :of
116
+ end
117
+ it "of_false" do
118
+ asm "adda gr0, gr1", :regs => {:gr0 => 0, :gr1 => -32768}
119
+ reg_is :gr0, -32768
120
+ fire :sf
121
+ end
122
+ end
123
+ end
124
+ it "rix" do
125
+ asm "adda gr0, a, gr1", :dc => {:a => 0, :b => -66}, :regs => {:gr0 => -11, :gr1 => 1}
126
+ reg_is :gr0, -77
127
+ fire :sf
128
+ end
129
+ end
130
+
131
+ describe "addl" do
132
+ describe "r1_r2" do
133
+ describe "上限" do
134
+ it "of_true" do
135
+ asm "addl gr0, gr1", :regs => {:gr0 => 1, :gr1 => 65535}
136
+ reg_is :gr0, 0
137
+ fire :of, :zf
138
+ end
139
+ it "of_false" do
140
+ asm "addl gr0, gr1", :regs => {:gr0 => 0, :gr1 => 65535}
141
+ reg_is :gr0, -1
142
+ fire :sf
143
+ end
144
+ end
145
+ describe "下限" do
146
+ it "of_false" do
147
+ asm "addl gr0, gr1", :regs => {:gr0 => -1, :gr1 => 0}
148
+ reg_is :gr0, -1
149
+ fire :sf
150
+ end
151
+ end
152
+ end
153
+ end
154
+
155
+ describe "alias" do
156
+ it "add" do
157
+ asm "add gr0, a, gr1", :dc => {:a => 0, :b => -66}, :regs => {:gr0 => -11, :gr1 => 1}
158
+ reg_is :gr0, -77
159
+ fire :sf
160
+ end
161
+ it "sub" do
162
+ asm "sub gr0, a, gr1", :dc => {:a => 0, :b => 88}, :regs => {:gr0 => 11, :gr1 => 1}
163
+ reg_is :gr0, -77
164
+ fire :sf
165
+ end
166
+ it "eor" do
167
+ asm "eor gr0, a, gr1", :dc => {:a => 0, :b => 0x5500}, :regs => {:gr0 => 0xf0f0, :gr1 => 1}
168
+ @p.gr[:gr0].value.should == 0xa5f0
169
+ fire :sf
170
+ end
171
+ end
172
+
173
+ describe "論理演算" do
174
+ describe "r1_r2" do
175
+ it do
176
+ logic_check(:and, 0x5000)
177
+ logic_check(:or, 0xf5f0)
178
+ logic_check(:xor, 0xa5f0)
179
+ end
180
+
181
+ def logic_check(order, result)
182
+ asm "#{order} gr0, gr1", :regs => {:gr0 => 0xf0f0, :gr1 => 0x5500}
183
+ @p.gr[:gr0].value.should == result
184
+ end
185
+ end
186
+
187
+ describe "rix" do
188
+ it "xor" do
189
+ asm "xor gr0, a, gr1", :dc => {:a => 0, :b => 0x5500}, :regs => {:gr0 => 0xf0f0, :gr1 => 1}
190
+ @p.gr[:gr0].value.should == 0xa5f0
191
+ fire :sf
192
+ end
193
+ end
194
+ end
195
+
196
+ it "比較" do
197
+ compare_check(:cpa, 1, -1, [])
198
+ compare_check(:cpl, 1, -1, [:sf])
199
+ compare_check(:cpa, -1, 1, [:sf])
200
+ compare_check(:cpl, -1, 1, [])
201
+ end
202
+
203
+ def compare_check(order, a, b, flags)
204
+ @p.init_env
205
+ asm ["lea gr0, #{a}", "#{order} gr0, a"], :dc => {:a => b}
206
+ fire *flags
207
+ end
208
+
209
+ describe "シフト" do
210
+ it do
211
+ shift_check :sla, -1, 0b1000000000000000, [:of, :sf]
212
+ shift_check :sla, 0, 0b1010000000000001, [:sf]
213
+ shift_check :sla, 1, 0b1100000000000010, [:of, :sf]
214
+ shift_check :sla, 2, 0b1000000000000100, [:of, :sf]
215
+ shift_check :sla, 15, 0b1000000000000000, [:of, :sf]
216
+ shift_check :sla, 16, 0b1000000000000000, [:of, :sf]
217
+ shift_check :sla, 17, 0b1000000000000000, [:of, :sf]
218
+ shift_check :sla, 64, 0b1000000000000000, [:of, :sf]
219
+ shift_check :sra, -1, 0b1111111111111111, [:of, :sf]
220
+ shift_check :sra, 0, 0b1010000000000001, [:sf]
221
+ shift_check :sra, 1, 0b1101000000000000, [:of, :sf]
222
+ shift_check :sra, 2, 0b1110100000000000, [:sf]
223
+ shift_check :sra, 15, 0b1111111111111111, [:sf]
224
+ shift_check :sra, 16, 0b1111111111111111, [:of, :sf]
225
+ shift_check :sra, 17, 0b1111111111111111, [:of, :sf]
226
+ shift_check :sra, 64, 0b1111111111111111, [:of, :sf]
227
+ shift_check :sll, -1, 0b0000000000000000, [:of, :zf]
228
+ shift_check :sll, 0, 0b1010000000000001, [:sf]
229
+ shift_check :sll, 1, 0b0100000000000010, [:of]
230
+ shift_check :sll, 2, 0b1000000000000100, [:sf]
231
+ shift_check :sll, 15, 0b1000000000000000, [:sf]
232
+ shift_check :sll, 16, 0b0000000000000000, [:of, :zf]
233
+ shift_check :sll, 17, 0b0000000000000000, [:of, :zf]
234
+ shift_check :sll, 64, 0b0000000000000000, [:of, :zf]
235
+ shift_check :srl, -1, 0b0000000000000000, [:of, :zf]
236
+ shift_check :srl, 0, 0b1010000000000001, [:sf]
237
+ shift_check :srl, 1, 0b0101000000000000, [:of]
238
+ shift_check :srl, 2, 0b0010100000000000, []
239
+ shift_check :srl, 15, 0b0000000000000001, []
240
+ shift_check :srl, 16, 0b0000000000000000, [:of, :zf]
241
+ shift_check :srl, 17, 0b0000000000000000, [:of, :zf]
242
+ shift_check :srl, 64, 0b0000000000000000, [:of, :zf]
243
+ end
244
+
245
+ def shift_check(order, count, result_value, result_flgs)
246
+ @p.init_env
247
+ asm "#{order} gr0, count", :dc => {:count => count}, :regs => {:gr0 => 0b1010000000000001}
248
+ # p(["%016b" % @p.gr[:gr0].value, @p.gr[:fr].available_flags])
249
+ # [@p.gr[:gr0].value, @p.gr[:fr].available_flags]
250
+ @p.gr[:gr0].value.should == result_value
251
+ fire *result_flgs
252
+ end
253
+ end
254
+
255
+ describe "jmp" do
256
+ it do
257
+ jmp_check :jmp, [1, 1, 1]
258
+ jmp_check :jump, [1, 1, 1]
259
+ jmp_check :jpl, [0, 0, 1]
260
+ jmp_check :jpz, [0, 1, 1]
261
+ jmp_check :jmi, [1, 0, 0]
262
+ jmp_check :jnz, [1, 0, 1]
263
+ jmp_check :jze, [0, 1, 0]
264
+ end
265
+
266
+ def jmp_check(order, result)
267
+ [].tap do |gr0|
268
+ @p.init_env; asm ["lea gr0, -1", "#{order} a", "lea gr0, 0", "jmp b", "a lea gr0, 1", "b nop"]; gr0 << @p.gr[:gr0].s_value
269
+ @p.init_env; asm ["lea gr0, 0", "#{order} a", "lea gr0, 0", "jmp b", "a lea gr0, 1", "b nop"]; gr0 << @p.gr[:gr0].s_value
270
+ @p.init_env; asm ["lea gr0, 1", "#{order} a", "lea gr0, 0", "jmp b", "a lea gr0, 1", "b nop"]; gr0 << @p.gr[:gr0].s_value
271
+ end.should == result
272
+ end
273
+ end
274
+
275
+ describe "jov" do
276
+ it "of_true" do
277
+ asm ["jov a", "jmp e", "a lea gr0, 77", "e nop"], :flags => {:of => true}
278
+ reg_is :gr0, 77
279
+ end
280
+ it "of_false" do
281
+ asm ["jov a", "jmp e", "a lea gr0, 77", "e nop"], :flags => {:of => false}
282
+ reg_is :gr0, 0
283
+ end
284
+ end
285
+
286
+ it "push_pop" do
287
+ asm ["push 77", "pop gr0"]
288
+ reg_is :gr0, 77
289
+ end
290
+
291
+ it "call" do
292
+ asm ["call a", "a nop"]
293
+ @p.memory[@p.gr[:sp].value].should == 2
294
+ end
295
+
296
+ describe "ret" do
297
+ it do
298
+ asm ["call a", "lea gr1,77", "jmp e", "a lea gr0,77", "ret", "e nop"]
299
+ reg_is :gr0, 77
300
+ reg_is :gr1, 77
301
+ end
302
+
303
+ it "ret で正常に戻ったかどうかは exit_key でわかる" do
304
+ asm "RET"
305
+ @p.exit_key.should == :ret
306
+ end
307
+ end
308
+ end
309
+
310
+ describe "擬似命令" do
311
+ it "start" do
312
+ asm [" start a", " lea gr0, 444", " jmp e", "a lea gr0, 77", "e nop"]
313
+ reg_is :gr0, 77
314
+ end
315
+
316
+ # it "end" do
317
+ # @p.assemble(["start", "ld gr0,=77", " dc 0", "end"].join("\n"))
318
+ # @p.memory[@p.code_size - 1].should == 77
319
+ # end
320
+ #
321
+ # it "ds" do
322
+ # @p.assemble [" nop", "a ds a"].join("\n") # 個数がラベル
323
+ # @p.code_size.should == 2
324
+ #
325
+ # @p.assemble " ds 7"
326
+ # @p.code_size.should == 7
327
+ #
328
+ # @p.assemble " ds 0"
329
+ # @p.code_size.should == 0
330
+ # end
331
+ #
332
+ # describe "dc" do
333
+ # it do
334
+ # dc_check %{''}, ""
335
+ # dc_check %{'\;'}, ";"
336
+ # dc_check %{'a'}, "a"
337
+ # dc_check %{"a"}, "a"
338
+ # dc_check %{10}, "\x0a"
339
+ # dc_check %{'a', 'b', 0, 'c', 'd'}, "ab\x00cd"
340
+ # dc_check %{'a''b''c',0,'d''e''f'}, "a'b'c\x00d'e'f"
341
+ # dc_check %{"a""b""c",0,'d''e''f'}, %{a"b"c\x00d'e'f}
342
+ # end
343
+ #
344
+ # it "ラベルはアドレスに展開" do
345
+ # asm ["nop", "a nop"], :dc => {:b => :a}
346
+ # var_check :b, @p.labels[:a]
347
+ # end
348
+ #
349
+ # def dc_check(code, result)
350
+ # @p.assemble " dc #{code}"
351
+ # @p.memory[0...@p.code_size].pack("C*").should == result
352
+ # end
353
+ # end
354
+ end
355
+
356
+ describe "マクロ" do
357
+ describe "in" do
358
+ shared_examples_for "test" do
359
+ it do
360
+ asm "in buf,len", :ds => {:buf => 4}, :dc => {:len => 0}
361
+ @p.memory[@p.labels[:__global__]["buf"] + 0].should == "a".ord
362
+ @p.memory[@p.labels[:__global__]["buf"] + 1].should == "b".ord
363
+ var_check :len, 2
364
+ end
365
+ end
366
+
367
+ describe "@dataから" do
368
+ before { @p.data = ["ab"] }
369
+ it_behaves_like "test"
370
+ end
371
+
372
+ describe "標準入力" do
373
+ before do
374
+ @save_stdin = $stdin
375
+ $stdin = double("stdin", :gets => "ab")
376
+ end
377
+ after do
378
+ $stdin = @save_stdin
379
+ end
380
+ it_behaves_like "test"
381
+ end
382
+ end
383
+
384
+ it "out" do
385
+ # capture(:stdout) {
386
+ # asm ["out str,len", "out str,len"], :dc => {:str => "'abcd'", :len => 2}
387
+ # }.should == "ab\nab\n"
388
+ expect {
389
+ asm ["out str,len", "out str,len"], :dc => {:str => "'abcd'", :len => 2}
390
+ }.to output("ab\nab\n").to_stdout
391
+ end
392
+
393
+ it "exit" do
394
+ asm
395
+ end
396
+
397
+ it "rpush rpop" do
398
+ asm ["lea gr1, 77", "rpush", "lea gr1, 444", "rpop"]
399
+ reg_is :gr1, 77
400
+ end
401
+ end
402
+ end
403
+
404
+ describe Parser do
405
+ it "ラベル表記" do
406
+ @p.assemble("foo").labels.should == {:__global__ => {"foo" => 0}}
407
+ @p.assemble("foo:").labels.should == {:__global__ => {"foo" => 0}}
408
+ @p.assemble("Foo:").labels.should == {:__global__ => {"Foo" => 0}}
409
+ @p.assemble("lad:").labels.should == {:__global__ => {"lad" => 0}}
410
+ @p.assemble("@xx").labels.should == {:__global__ => {"@xx" => 0}}
411
+ @p.assemble("$xx").labels.should == {:__global__ => {"$xx" => 0}}
412
+ end
413
+
414
+ it "ローカルラベルとグローバルラベル" do
415
+ asm [
416
+ "a START", # global
417
+ "a NOP", # local
418
+ " RET",
419
+ " END",
420
+ "",
421
+ "b START", # global
422
+ "a NOP", # local
423
+ "$x NOP", # global
424
+ " RET",
425
+ " END",
426
+ ]
427
+ @p.labels.should == {
428
+ :__global__ => {"a" => 0, "b" => 2, "$x" => 3},
429
+ "a" => {"a" => 0},
430
+ "b" => {"a" => 2},
431
+ }
432
+ end
433
+
434
+ it "コメント" do
435
+ @p.assemble(" DC #77 ; comment").disassemble.should match "77"
436
+ @p.assemble("#DC #77").code_size.should == 0
437
+ @p.assemble(";DC #77").code_size.should == 0
438
+ end
439
+
440
+ it "インラインデータ" do
441
+ @p.assemble([" ld gr1, =1", " nop"].join("\n"))
442
+ @p.disassemble.should == <<-EOT
443
+ 0000 1010 0003 LD GR1, #0003
444
+ 0002 0900 NOP
445
+ 0003 0001 DC 1
446
+ EOT
447
+ @p.assemble([" dc ='abcd'", " nop"].join("\n"))
448
+ @p.disassemble.should == <<-EOT
449
+ 0000 0002 DC 2
450
+ 0001 0900 NOP
451
+ 0002 0061 DC 97 ; 'a'
452
+ 0003 0062 DC 98 ; 'b'
453
+ 0004 0063 DC 99 ; 'c'
454
+ 0005 0064 DC 100 ; 'd'
455
+ EOT
456
+ end
457
+
458
+ it "即値" do
459
+ value_format_check "010", 8
460
+ value_format_check "10", 10
461
+ value_format_check "#10", 0x10
462
+ value_format_check "0x10", 0x10
463
+ value_format_check "0b10", 2
464
+ end
465
+
466
+ def value_format_check(str, result)
467
+ @p.assemble(" DC #{str}")
468
+ @p.memory.first.should == result
469
+ end
470
+ end
471
+
472
+ describe RaslError do
473
+ before do
474
+ @bol_order = Rasl.config.bol_order
475
+ end
476
+ after do
477
+ Rasl.config.bol_order = @bol_order
478
+ end
479
+
480
+ it do
481
+ Rasl.config.bol_order = false; expect { @p.assemble "JPZ GR1, 1, GR2" }.to raise_error(InvalidOrder)
482
+ Rasl.config.bol_order = true; expect { @p.assemble "JPZ GR1, 1, GR2" }.to raise_error(LabelNotFound)
483
+ end
484
+
485
+ it do
486
+ expect { asm "JPZ GR1, 1, GR2" }.to raise_error(LabelNotFound)
487
+ end
488
+ end
489
+
490
+ describe Simulator do
491
+ describe "r" do
492
+ it "r" do
493
+ @p.command_init
494
+ expect { @p.post_command("r") }.to output(<<-EOT).to_stdout
495
+ GR0=0000 GR1=0000 GR2=0000 GR3=0000 GR4=0000 GR5=0000 GR6=0000 GR7=0000 PC=0000 SP=FFFF FR=___(+)
496
+ 0000 0000 DC 0
497
+ EOT
498
+ end
499
+
500
+ it "rGR=77" do
501
+ @p.command_init
502
+ @p.post_command("rGR0=77")
503
+ @p.gr[:gr0].value.should == 77
504
+ end
505
+
506
+ it "asm => r" do
507
+ asm "lea GR0,1"
508
+ expect { @p.post_command("r") }.to output(<<-EOT).to_stdout
509
+ GR0=0001 GR1=0000 GR2=0000 GR3=0000 GR4=0000 GR5=0000 GR6=0000 GR7=0000 PC=0004 SP=FFFF FR=___(+) [exit]
510
+ 0004 0000 DC 0
511
+ EOT
512
+ end
513
+ end
514
+
515
+ it "#disassemble" do
516
+ @p.assemble("ld gr0, 1").disassemble.should == "0000 1000 0001 LD GR0, #0001\n"
517
+ end
518
+ end
519
+
520
+ it "disassemble" do
521
+ @p.assemble <<-SOURCE
522
+ NOP
523
+ LD GR1, 1, GR2
524
+ ST GR1, 1, GR2
525
+ LAD GR1, 1, GR2
526
+ LD GR1, GR2
527
+ ADDA GR1, 1, GR2
528
+ SUBA GR1, 1, GR2
529
+ ADDA GR3, GR4
530
+ SUBA GR3, GR4
531
+ AND GR1, 1, GR2
532
+ OR GR1, 1, GR2
533
+ XOR GR1, 1, GR2
534
+ AND GR1, GR2
535
+ OR GR1, GR2
536
+ XOR GR1, GR2
537
+
538
+ CPA GR1, 1, GR2
539
+ CPL GR1, 1, GR2
540
+ CPA GR1, GR2
541
+ CPL GR1, GR2
542
+
543
+ SLA GR1, 1, GR2
544
+ SRA GR1, 1, GR2
545
+ SLL GR1, 1, GR2
546
+ SRL GR1, 1, GR2
547
+
548
+ JPZ 1, GR2
549
+ JMI 1, GR2
550
+ JNZ 1, GR2
551
+ JZE 1, GR2
552
+ JUMP 1, GR2
553
+ JPL 1, GR2
554
+ JOV 1, GR2
555
+
556
+ PUSH #0077, GR2
557
+ POP GR0
558
+ CALL #0077, GR2
559
+ RET
560
+
561
+ RPUSH
562
+ RPOP
563
+
564
+ IN 1, 2
565
+ OUT 3, 4
566
+ SVC 0, GR2
567
+ EXIT
568
+
569
+ JMP A
570
+ EOR GR0, A
571
+ ADD GR1, 1, GR2
572
+ SUB GR1, 1, GR2
573
+
574
+ A DC 'a''b','c'
575
+ B DS 0
576
+ C DS 3
577
+ SOURCE
578
+ @p.disassemble.should == <<-MAP
579
+ 0000 0900 NOP
580
+ 0001 1012 0001 LD GR1, #0001, GR2
581
+ 0003 1112 0001 ST GR1, #0001, GR2
582
+ 0005 1212 0001 LAD GR1, #0001, GR2
583
+ 0007 1412 LD GR1, GR2
584
+ 0008 2012 0001 ADDA GR1, #0001, GR2
585
+ 000A 2112 0001 SUBA GR1, #0001, GR2
586
+ 000C 2434 ADDA GR3, GR4
587
+ 000D 2534 SUBA GR3, GR4
588
+ 000E 3012 0001 AND GR1, #0001, GR2
589
+ 0010 3112 0001 OR GR1, #0001, GR2
590
+ 0012 3212 0001 XOR GR1, #0001, GR2
591
+ 0014 3412 AND GR1, GR2
592
+ 0015 3512 OR GR1, GR2
593
+ 0016 3612 XOR GR1, GR2
594
+ 0017 4012 0001 CPA GR1, #0001, GR2
595
+ 0019 4112 0001 CPL GR1, #0001, GR2
596
+ 001B 4412 CPA GR1, GR2
597
+ 001C 4512 CPL GR1, GR2
598
+ 001D 5012 0001 SLA GR1, #0001, GR2
599
+ 001F 5112 0001 SRA GR1, #0001, GR2
600
+ 0021 5212 0001 SLL GR1, #0001, GR2
601
+ 0023 5312 0001 SRL GR1, #0001, GR2
602
+ 0025 6002 0001 JPZ #0001, GR2
603
+ 0027 6102 0001 JMI #0001, GR2
604
+ 0029 6202 0001 JNZ #0001, GR2
605
+ 002B 6302 0001 JZE #0001, GR2
606
+ 002D 6402 0001 JUMP #0001, GR2
607
+ 002F 6502 0001 JPL #0001, GR2
608
+ 0031 6602 0001 JOV #0001, GR2
609
+ 0033 7002 0077 PUSH #0077, GR2
610
+ 0035 7100 POP GR0
611
+ 0036 8002 0077 CALL #0077, GR2
612
+ 0038 8100 RET
613
+ 0039 7001 0000 PUSH #0000, GR1
614
+ 003B 7002 0000 PUSH #0000, GR2
615
+ 003D 7003 0000 PUSH #0000, GR3
616
+ 003F 7004 0000 PUSH #0000, GR4
617
+ 0041 7005 0000 PUSH #0000, GR5
618
+ 0043 7006 0000 PUSH #0000, GR6
619
+ 0045 7007 0000 PUSH #0000, GR7
620
+ 0047 7170 POP GR7
621
+ 0048 7160 POP GR6
622
+ 0049 7150 POP GR5
623
+ 004A 7140 POP GR4
624
+ 004B 7130 POP GR3
625
+ 004C 7120 POP GR2
626
+ 004D 7110 POP GR1
627
+ 004E 7001 0000 PUSH #0000, GR1
628
+ 0050 7002 0000 PUSH #0000, GR2
629
+ 0052 1210 0001 LAD GR1, #0001
630
+ 0054 1220 0002 LAD GR2, #0002
631
+ 0056 F000 0000 SVC #0000
632
+ 0058 7120 POP GR2
633
+ 0059 7110 POP GR1
634
+ 005A 7001 0000 PUSH #0000, GR1
635
+ 005C 7002 0000 PUSH #0000, GR2
636
+ 005E 1210 0003 LAD GR1, #0003
637
+ 0060 1220 0004 LAD GR2, #0004
638
+ 0062 F000 0001 SVC #0001
639
+ 0064 7120 POP GR2
640
+ 0065 7110 POP GR1
641
+ 0066 F002 0000 SVC #0000, GR2
642
+ 0068 F000 0002 SVC #0002
643
+ 006A 6400 0072 JUMP #0072
644
+ 006C 3200 0072 XOR GR0, #0072
645
+ 006E 2012 0001 ADDA GR1, #0001, GR2
646
+ 0070 2112 0001 SUBA GR1, #0001, GR2
647
+ 0072 0061 DC 97 ; 'a'
648
+ 0073 0027 DC 39 ; '''
649
+ 0074 0062 DC 98 ; 'b'
650
+ 0075 0063 DC 99 ; 'c'
651
+ 0076 FFFF DC -1
652
+ 0077 FFFF DC -1
653
+ 0078 FFFF DC -1
654
+ MAP
655
+ end
656
+
657
+ private
658
+
659
+ def asm(order = nil, options = {})
660
+ options = {
661
+ :regs => {},
662
+ :flags => {},
663
+ :dc => {},
664
+ :ds => {},
665
+ }.merge(options)
666
+
667
+ options[:flags].each{|k, v|@p.gr[:fr].send("#{k}=", v)}
668
+ options[:regs].each{|k, v|@p.gr[k].value = v}
669
+
670
+ source = Array(order) + [" exit"]
671
+ source += options[:dc].collect{|k, v|"#{k} dc #{Array(v).join(',')}"}
672
+ source += options[:ds].collect{|k, v|"#{k} ds #{Array(v).join(',')}"}
673
+ source = source.join("\n")
674
+
675
+ @p.assemble_without_init_env(source)
676
+ @p.before_go
677
+ @p.command_go
678
+ @p
679
+ end
680
+
681
+ def var_check(name, value)
682
+ var(name).should == value
683
+ end
684
+
685
+ def var(name)
686
+ Value.new(@p.memory[@p.labels[:__global__].fetch(name.to_s)]).s_value
687
+ end
688
+
689
+ def reg_is(name, value)
690
+ @p.gr[name].s_value.should == value
691
+ end
692
+
693
+ def fire(*args)
694
+ @p.gr[:fr].available_flags.should == args
695
+ end
696
+
697
+ def fr_blank
698
+ fire
699
+ end
700
+ end