vm2gol v2 製作メモ(1) 最初のVM



とにかく始める

とにかくやるのだぁ

(『30日でできる! OS自作入門』 p14)


とりあえずアレですよね? レジスタとメモリがあるんですよね? などといって適当に書き始めます。 慣れていてサッと始められるので Ruby です。 サッと始められるの大事です。

# coding: utf-8
require "pp"

class Vm
  def initialize
    # register
    @reg_a = 0
    @reg_b = 0
    @reg_c = 0

    @mem = Array.new(8, 0) # サイズ8、0で初期化
  end

  def set_mem(addr, n)
    @mem[addr] = n
  end

  def copy_mem_to_reg_a(addr)
    @reg_a = @mem[addr]
  end

  def copy_mem_to_reg_b(addr)
    @reg_b = @mem[addr]
  end

  def copy_reg_c_to_mem(addr)
    @mem[addr] = @reg_c
  end

  def add_ab
    @reg_c = @reg_a + @reg_b
  end
end

vm = Vm.new
pp vm # 初期状態

vm.set_mem(0, 1)
vm.set_mem(1, 2)
pp vm # ★1

vm.copy_mem_to_reg_a(0)
vm.copy_mem_to_reg_b(1)
pp vm # ★2

vm.add_ab
vm.copy_reg_c_to_mem(2)
pp vm # ★3

★1 なにはともあれメモリに値をセットする。 0番地に 1 が、1番地に 2 が入っていればOK。

★2 メモリの値をレジスタにコピーしてみる。 reg_a が 1 に、reg_b が 2 になっていればOK。

★3 足し算して結果を reg_c に入れて、それをメモリにコピーする、というのをやってみる。 reg_c とメモリの 2番地に 3 が入っていればOK。

$ ruby vgvm.rb
#<Vm:0x005650ed9eaa40
     @mem=[0, 0, 0, 0, 0, 0, 0, 0],
     @reg_a=0,
     @reg_b=0,
     @reg_c=0> ... 初期状態
#<Vm:0x005650ed9eaa40
     @mem=[1, 2, 0, 0, 0, 0, 0, 0],
     @reg_a=0,
     @reg_b=0,
     @reg_c=0> ... ★1
#<Vm:0x005650ed9eaa40
     @mem=[1, 2, 0, 0, 0, 0, 0, 0],
     @reg_a=1,
     @reg_b=2,
     @reg_c=0> ... ★2
#<Vm:0x005650ed9eaa40
     @mem=[1, 2, 3, 0, 0, 0, 0, 0],
     @reg_a=1,
     @reg_b=2,
     @reg_c=3> ... ★3

はい。

ちょっとあっさりしすぎですがこんな感じで始めました。 最初なのでこんなもんで。

余談

足し算のところは、下記のようにして桁あふれのエミュレーションもやってましたが 最終的に使わなくなったので消しました。

sum = @reg_a + @reg_b
if sum >= 16
  @reg_c = sum - 16
  @of = 1 # オーバーフローフラグ
else
  @reg_c = sum
end