bfrb 0.1.1 → 0.1.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.
- data/README.rdoc +3 -3
- data/VERSION +1 -1
- data/bfrb.gemspec +3 -3
- data/lib/bfrb/interpreter.rb +11 -6
- data/test/test_interpreter.rb +100 -0
- metadata +12 -12
- data/test/test_bfrb.rb +0 -7
data/README.rdoc
CHANGED
@@ -24,9 +24,9 @@ You can also start an interactive interpreter by running bfrb without any parame
|
|
24
24
|
== Things To Do
|
25
25
|
|
26
26
|
* Compiler
|
27
|
-
* Unit Testing
|
28
27
|
|
29
28
|
== History
|
30
29
|
|
31
|
-
|
32
|
-
|
30
|
+
* 0.1.2 - Added unit tests
|
31
|
+
* 0.1.1 - Added REPL.
|
32
|
+
* 0.1.0 - Initial release. Allows running code passed in or from a file.
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.1.
|
1
|
+
0.1.2
|
data/bfrb.gemspec
CHANGED
@@ -5,7 +5,7 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = %q{bfrb}
|
8
|
-
s.version = "0.1.
|
8
|
+
s.version = "0.1.2"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Chris ONeal"]
|
@@ -30,7 +30,7 @@ Gem::Specification.new do |s|
|
|
30
30
|
"lib/bfrb/interpreter.rb",
|
31
31
|
"lib/bfrb/memory.rb",
|
32
32
|
"test/helper.rb",
|
33
|
-
"test/
|
33
|
+
"test/test_interpreter.rb"
|
34
34
|
]
|
35
35
|
s.homepage = %q{http://github.com/ctoneal/bfrb}
|
36
36
|
s.licenses = ["MIT"]
|
@@ -39,7 +39,7 @@ Gem::Specification.new do |s|
|
|
39
39
|
s.summary = %q{A simple brainfuck interpreter in Ruby}
|
40
40
|
s.test_files = [
|
41
41
|
"test/helper.rb",
|
42
|
-
"test/
|
42
|
+
"test/test_interpreter.rb"
|
43
43
|
]
|
44
44
|
|
45
45
|
if s.respond_to? :specification_version then
|
data/lib/bfrb/interpreter.rb
CHANGED
@@ -5,11 +5,14 @@ module BfRb
|
|
5
5
|
class Interpreter
|
6
6
|
|
7
7
|
attr_reader :program_counter, :memory_counter
|
8
|
+
attr_accessor :input_stream, :output_stream
|
8
9
|
|
9
10
|
# initialize the interpreter
|
10
11
|
def initialize
|
11
12
|
@memory = Memory.new
|
12
13
|
initialize_environment
|
14
|
+
@input_stream = $stdin
|
15
|
+
@output_stream = $stdout
|
13
16
|
end
|
14
17
|
|
15
18
|
# cleans the memory and initializes member variables
|
@@ -30,13 +33,13 @@ module BfRb
|
|
30
33
|
# evaluate each instruction in the current code
|
31
34
|
def evaluate_code
|
32
35
|
while ((0 <= @program_counter) and (@program_counter < @code.length))
|
33
|
-
evaluate_instruction
|
36
|
+
evaluate_instruction(@code[@program_counter])
|
34
37
|
end
|
35
38
|
end
|
36
39
|
|
37
40
|
# evaluate an individual instruction
|
38
|
-
def evaluate_instruction
|
39
|
-
case
|
41
|
+
def evaluate_instruction(instruction)
|
42
|
+
case instruction
|
40
43
|
when ">"
|
41
44
|
@memory_counter += 1
|
42
45
|
when "<"
|
@@ -48,11 +51,13 @@ module BfRb
|
|
48
51
|
when "+"
|
49
52
|
@memory.set(@memory_counter, current_memory + 1)
|
50
53
|
when "-"
|
51
|
-
|
54
|
+
unless current_memory == 0
|
55
|
+
@memory.set(@memory_counter, current_memory - 1)
|
56
|
+
end
|
52
57
|
when "."
|
53
|
-
print current_memory.chr
|
58
|
+
@output_stream.print current_memory.chr
|
54
59
|
when ","
|
55
|
-
input =
|
60
|
+
input = @input_stream.gets.getbyte(0)
|
56
61
|
@memory.set(@memory_counter, input)
|
57
62
|
when "["
|
58
63
|
if current_memory != 0
|
@@ -0,0 +1,100 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
module BfRb
|
4
|
+
class TestInterpreter < Test::Unit::TestCase
|
5
|
+
def setup
|
6
|
+
@interpreter = Interpreter.new
|
7
|
+
end
|
8
|
+
|
9
|
+
context ">" do
|
10
|
+
should "increment the memory counter" do
|
11
|
+
initial_mc = @interpreter.memory_counter
|
12
|
+
@interpreter.evaluate_instruction(">")
|
13
|
+
assert_equal(initial_mc + 1, @interpreter.memory_counter)
|
14
|
+
end
|
15
|
+
|
16
|
+
end
|
17
|
+
|
18
|
+
context "<" do
|
19
|
+
should "decrement the memory counter" do
|
20
|
+
@interpreter.evaluate_instruction(">")
|
21
|
+
initial_mc = @interpreter.memory_counter
|
22
|
+
@interpreter.evaluate_instruction("<")
|
23
|
+
assert_equal(initial_mc - 1, @interpreter.memory_counter)
|
24
|
+
end
|
25
|
+
|
26
|
+
should "not decrement below zero" do
|
27
|
+
@interpreter.evaluate_instruction("<")
|
28
|
+
assert_equal(0, @interpreter.memory_counter)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
context "+" do
|
33
|
+
should "increment the current value in memory" do
|
34
|
+
initial_value = @interpreter.current_memory
|
35
|
+
@interpreter.evaluate_instruction("+")
|
36
|
+
assert_equal(initial_value + 1, @interpreter.current_memory)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
context "-" do
|
41
|
+
should "decrement the current value in memory" do
|
42
|
+
@interpreter.evaluate_instruction("+")
|
43
|
+
initial_value = @interpreter.current_memory
|
44
|
+
@interpreter.evaluate_instruction("-")
|
45
|
+
assert_equal(initial_value - 1, @interpreter.current_memory)
|
46
|
+
end
|
47
|
+
|
48
|
+
should "not decrement below zero" do
|
49
|
+
@interpreter.evaluate_instruction("-")
|
50
|
+
assert_equal(0, @interpreter.current_memory)
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
context "[]" do
|
55
|
+
should "loop properly if value in memory is not zero" do
|
56
|
+
@interpreter.evaluate_instruction("+")
|
57
|
+
initial_value = @interpreter.program_counter
|
58
|
+
@interpreter.evaluate_instruction("[")
|
59
|
+
@interpreter.evaluate_instruction("+")
|
60
|
+
@interpreter.evaluate_instruction("]")
|
61
|
+
assert_equal(initial_value, @interpreter.program_counter)
|
62
|
+
end
|
63
|
+
|
64
|
+
should "break out of the loop if value in memory is zero" do
|
65
|
+
@interpreter.evaluate_instruction("+")
|
66
|
+
initial_value = @interpreter.program_counter
|
67
|
+
@interpreter.evaluate_instruction("[")
|
68
|
+
@interpreter.evaluate_instruction("-")
|
69
|
+
@interpreter.evaluate_instruction("]")
|
70
|
+
assert_not_equal(initial_value, @interpreter.program_counter)
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
74
|
+
context "." do
|
75
|
+
should "output the intended character to the screen" do
|
76
|
+
@interpreter.evaluate_instruction("+")
|
77
|
+
output, input = IO.pipe
|
78
|
+
@interpreter.output_stream = input
|
79
|
+
@interpreter.evaluate_instruction(".")
|
80
|
+
input.close
|
81
|
+
value = output.getbyte
|
82
|
+
output.close
|
83
|
+
assert_equal(value, @interpreter.current_memory)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
87
|
+
context "," do
|
88
|
+
should "place the intended character in memory" do
|
89
|
+
output, input = IO.pipe
|
90
|
+
character = "a"
|
91
|
+
@interpreter.input_stream = output
|
92
|
+
input.write character
|
93
|
+
input.close
|
94
|
+
@interpreter.evaluate_instruction(",")
|
95
|
+
output.close
|
96
|
+
assert_equal(character.getbyte(0), @interpreter.current_memory)
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
100
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bfrb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.2
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -14,7 +14,7 @@ default_executable: bfrb
|
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: shoulda
|
17
|
-
requirement: &
|
17
|
+
requirement: &9363720 !ruby/object:Gem::Requirement
|
18
18
|
none: false
|
19
19
|
requirements:
|
20
20
|
- - ! '>='
|
@@ -22,10 +22,10 @@ dependencies:
|
|
22
22
|
version: '0'
|
23
23
|
type: :development
|
24
24
|
prerelease: false
|
25
|
-
version_requirements: *
|
25
|
+
version_requirements: *9363720
|
26
26
|
- !ruby/object:Gem::Dependency
|
27
27
|
name: bundler
|
28
|
-
requirement: &
|
28
|
+
requirement: &9362928 !ruby/object:Gem::Requirement
|
29
29
|
none: false
|
30
30
|
requirements:
|
31
31
|
- - ~>
|
@@ -33,10 +33,10 @@ dependencies:
|
|
33
33
|
version: 1.0.0
|
34
34
|
type: :development
|
35
35
|
prerelease: false
|
36
|
-
version_requirements: *
|
36
|
+
version_requirements: *9362928
|
37
37
|
- !ruby/object:Gem::Dependency
|
38
38
|
name: jeweler
|
39
|
-
requirement: &
|
39
|
+
requirement: &9362280 !ruby/object:Gem::Requirement
|
40
40
|
none: false
|
41
41
|
requirements:
|
42
42
|
- - ~>
|
@@ -44,10 +44,10 @@ dependencies:
|
|
44
44
|
version: 1.5.2
|
45
45
|
type: :development
|
46
46
|
prerelease: false
|
47
|
-
version_requirements: *
|
47
|
+
version_requirements: *9362280
|
48
48
|
- !ruby/object:Gem::Dependency
|
49
49
|
name: rcov
|
50
|
-
requirement: &
|
50
|
+
requirement: &9361608 !ruby/object:Gem::Requirement
|
51
51
|
none: false
|
52
52
|
requirements:
|
53
53
|
- - ! '>='
|
@@ -55,7 +55,7 @@ dependencies:
|
|
55
55
|
version: '0'
|
56
56
|
type: :development
|
57
57
|
prerelease: false
|
58
|
-
version_requirements: *
|
58
|
+
version_requirements: *9361608
|
59
59
|
description: bfrb is a brainfuck interpreter written in Ruby.
|
60
60
|
email: ctoneal@gmail.com
|
61
61
|
executables:
|
@@ -76,7 +76,7 @@ files:
|
|
76
76
|
- lib/bfrb/interpreter.rb
|
77
77
|
- lib/bfrb/memory.rb
|
78
78
|
- test/helper.rb
|
79
|
-
- test/
|
79
|
+
- test/test_interpreter.rb
|
80
80
|
has_rdoc: true
|
81
81
|
homepage: http://github.com/ctoneal/bfrb
|
82
82
|
licenses:
|
@@ -93,7 +93,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
93
93
|
version: '0'
|
94
94
|
segments:
|
95
95
|
- 0
|
96
|
-
hash:
|
96
|
+
hash: 624886557
|
97
97
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
98
98
|
none: false
|
99
99
|
requirements:
|
@@ -108,4 +108,4 @@ specification_version: 3
|
|
108
108
|
summary: A simple brainfuck interpreter in Ruby
|
109
109
|
test_files:
|
110
110
|
- test/helper.rb
|
111
|
-
- test/
|
111
|
+
- test/test_interpreter.rb
|