Class: KoiVMRuby::VM

Inherits:
Object
  • Object
show all
Defined in:
lib/koi-vm-ruby/core.rb,
lib/koi-vm-ruby/helpers.rb,
lib/koi-vm-ruby/accessors.rb,
lib/koi-vm-ruby/opcodes/io_operations/gets.rb,
lib/koi-vm-ruby/opcodes/io_operations/print.rb,
lib/koi-vm-ruby/opcodes/math_operations/add.rb,
lib/koi-vm-ruby/opcodes/stack_operations/dup.rb,
lib/koi-vm-ruby/opcodes/stack_operations/pop.rb,
lib/koi-vm-ruby/opcodes/stack_operations/top.rb,
lib/koi-vm-ruby/opcodes/hash_operations/pairs.rb,
lib/koi-vm-ruby/opcodes/stack_operations/swap.rb,
lib/koi-vm-ruby/opcodes/hash_operations/length.rb,
lib/koi-vm-ruby/opcodes/math_operations/divide.rb,
lib/koi-vm-ruby/opcodes/control_operations/exit.rb,
lib/koi-vm-ruby/opcodes/hash_operations/get_key.rb,
lib/koi-vm-ruby/opcodes/hash_operations/has_key.rb,
lib/koi-vm-ruby/opcodes/hash_operations/set_key.rb,
lib/koi-vm-ruby/opcodes/stack_operations/typeof.rb,
lib/koi-vm-ruby/opcodes/control_operations/no_op.rb,
lib/koi-vm-ruby/opcodes/function_operations/call.rb,
lib/koi-vm-ruby/opcodes/math_operations/multiply.rb,
lib/koi-vm-ruby/opcodes/math_operations/subtract.rb,
lib/koi-vm-ruby/opcodes/push_operations/push_int.rb,
lib/koi-vm-ruby/opcodes/push_operations/push_nil.rb,
lib/koi-vm-ruby/opcodes/stack_operations/stksize.rb,
lib/koi-vm-ruby/opcodes/string_operations/concat.rb,
lib/koi-vm-ruby/opcodes/string_operations/strlen.rb,
lib/koi-vm-ruby/opcodes/hash_operations/num_pairs.rb,
lib/koi-vm-ruby/opcodes/hash_operations/push_hash.rb,
lib/koi-vm-ruby/opcodes/push_operations/push_bool.rb,
lib/koi-vm-ruby/opcodes/function_operations/return.rb,
lib/koi-vm-ruby/opcodes/push_operations/push_float.rb,
lib/koi-vm-ruby/opcodes/push_operations/push_string.rb,
lib/koi-vm-ruby/opcodes/string_operations/to_string.rb,
lib/koi-vm-ruby/opcodes/comparative_operations/equal.rb,
lib/koi-vm-ruby/opcodes/flow_control_operations/jump.rb,
lib/koi-vm-ruby/opcodes/function_operations/tailcall.rb,
lib/koi-vm-ruby/opcodes/comparative_operations/invert.rb,
lib/koi-vm-ruby/opcodes/variable_operations/get_local.rb,
lib/koi-vm-ruby/opcodes/variable_operations/set_local.rb,
lib/koi-vm-ruby/opcodes/variable_operations/get_global.rb,
lib/koi-vm-ruby/opcodes/variable_operations/set_global.rb,
lib/koi-vm-ruby/opcodes/flow_control_operations/jump_if.rb,
lib/koi-vm-ruby/opcodes/comparative_operations/less_than.rb,
lib/koi-vm-ruby/opcodes/function_operations/push_function.rb,
lib/koi-vm-ruby/opcodes/comparative_operations/greater_than.rb,
lib/koi-vm-ruby/opcodes/flow_control_operations/jump_unless.rb

Constant Summary collapse

@@instruction =
[]

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(state = {}, opcodes = []) ⇒ VM

Returns a new instance of VM.

Raises:

  • (ArgumentError)


8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
# File 'lib/koi-vm-ruby/core.rb', line 8

def initialize(state = {}, opcodes = [])
  default_state = {
    :opcodes => opcodes,
    :globals => {},
    :fiber => {
      :data_stack => [],
      :return_stack => [],
      :locals => [{}],
      :instruction_pointer => 0,
      :level => 0
    }
  }
  @state = default_state.merge(state)
  @files = {} 
  raise ArgumentError, "state[:fibers][x] must be a hash" unless(@state[:fiber].is_a?(Hash))
  raise ArgumentError, "state[:fibers][x][:stack] must be an Array" unless(@state[:fiber][:data_stack].is_a?(Array))
  raise ArgumentError, "state[:fibers][x][:stack] must be an Array" unless(@state[:fiber][:return_stack].is_a?(Array))
  raise ArgumentError, "state[:fibers][x][:instruction_pointer] must be an Integer" unless(@state[:fiber][:instruction_pointer].is_a?(Integer))
  raise ArgumentError, "state[:fibers][x][:level] must be an Integer" unless(@state[:fiber][:level].is_a?(Integer))
  raise ArgumentError, "state[:globals] must be a hash" unless(@state[:globals].is_a?(Hash))
  raise ArgumentError, "state[:opcodes] must be an array" unless(@state[:opcodes].is_a?(Array))
end

Instance Attribute Details

#filesObject

Returns the value of attribute files.



6
7
8
# File 'lib/koi-vm-ruby/core.rb', line 6

def files
  @files
end

#stateObject

Returns the value of attribute state.



6
7
8
# File 'lib/koi-vm-ruby/core.rb', line 6

def state
  @state
end

Instance Method Details

#data_stackObject



4
5
6
# File 'lib/koi-vm-ruby/accessors.rb', line 4

def data_stack
  return @state[:fiber][:data_stack]
end

#data_stack=(stack) ⇒ Object



8
9
10
# File 'lib/koi-vm-ruby/accessors.rb', line 8

def data_stack=(stack)
  @state[:fiber][:data_stack] = stack
end

#decrement_scopeObject



45
46
47
48
# File 'lib/koi-vm-ruby/accessors.rb', line 45

def decrement_scope
  @state[:fiber][:locals].delete_at(@state[:fiber][:level])
  @state[:fiber][:level] -= 1
end

#globalsObject



36
37
38
# File 'lib/koi-vm-ruby/accessors.rb', line 36

def globals
  return @state[:globals]
end

#increment_scopeObject



40
41
42
43
# File 'lib/koi-vm-ruby/accessors.rb', line 40

def increment_scope
  @state[:fiber][:level] += 1
  @state[:fiber][:locals][@state[:fiber][:level]] = @state[:fiber][:locals][@state[:fiber][:level] - 1].dup
end

#instruction_pointerObject



20
21
22
# File 'lib/koi-vm-ruby/accessors.rb', line 20

def instruction_pointer
  return @state[:fiber][:instruction_pointer]
end

#instruction_pointer=(ip) ⇒ Object



24
25
26
# File 'lib/koi-vm-ruby/accessors.rb', line 24

def instruction_pointer=(ip)
  @state[:fiber][:instruction_pointer] = ip
end

#levelObject



54
55
56
# File 'lib/koi-vm-ruby/accessors.rb', line 54

def level
  return @state[:fiber][:level]
end

#level=(level) ⇒ Object



58
59
60
# File 'lib/koi-vm-ruby/accessors.rb', line 58

def level=(level)
  @state[:fiber][:level] = level
end

#localsObject



32
33
34
# File 'lib/koi-vm-ruby/accessors.rb', line 32

def locals
  return @state[:fiber][:locals][@state[:fiber][:level]]
end

#opcodesObject



28
29
30
# File 'lib/koi-vm-ruby/accessors.rb', line 28

def opcodes
  return @state[:opcodes]
end

#reload_scopeObject



50
51
52
# File 'lib/koi-vm-ruby/accessors.rb', line 50

def reload_scope
  @state[:fiber][:locals][@state[:fiber][:level]] = {}
end

#return_stackObject



12
13
14
# File 'lib/koi-vm-ruby/accessors.rb', line 12

def return_stack
  return @state[:fiber][:return_stack]
end

#return_stack=(stack) ⇒ Object



16
17
18
# File 'lib/koi-vm-ruby/accessors.rb', line 16

def return_stack=(stack)
  @state[:fiber][:return_stack] = stack
end

#run(opcodes = []) ⇒ Object



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/koi-vm-ruby/core.rb', line 31

def run(opcodes = [])
  @state[:opcodes].concat(opcodes)
  opcode_size = @state[:opcodes].size
  while (@state[:fiber][:instruction_pointer] < opcode_size)
    begin
      break if(@@instruction[@state[:opcodes][@state[:fiber][:instruction_pointer]]].call(self) == true)
    rescue NoMethodError
      @state.delete(:opcodes)
      puts "\n\n" + @state.inspect + "\n\n" unless(defined?($test) && $test == true)
      raise 
    end
  end
  
  return @state
end