zunscript 0.1.1
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.
- checksums.yaml +7 -0
- data/.gitignore +12 -0
- data/.travis.yml +3 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +21 -0
- data/README.md +100 -0
- data/Rakefile +9 -0
- data/bin/setup +5 -0
- data/bin/zsi +35 -0
- data/examples/test.zun +105 -0
- data/ext/zunscript/Makefile +9 -0
- data/ext/zunscript/ZunScript.g +87 -0
- data/ext/zunscript/antlr4ruby +106 -0
- data/ext/zunscript/ext.rb +2 -0
- data/ext/zunscript/extconf.rb +0 -0
- data/ext/zunscript/lexer.rb +1240 -0
- data/ext/zunscript/parser.rb +2225 -0
- data/lib/zunscript.rb +3 -0
- data/lib/zunscript/block.rb +72 -0
- data/lib/zunscript/environment.rb +104 -0
- data/lib/zunscript/scope.rb +55 -0
- data/lib/zunscript/value.rb +67 -0
- data/lib/zunscript/version.rb +3 -0
- data/zunscript.gemspec +29 -0
- metadata +141 -0
data/lib/zunscript.rb
ADDED
@@ -0,0 +1,72 @@
|
|
1
|
+
module ZunScript
|
2
|
+
class ZBlock < ZValue
|
3
|
+
def initialize statements, parameters, parentscope, env
|
4
|
+
super env
|
5
|
+
@body = statements
|
6
|
+
@parameters = parameters
|
7
|
+
@scope = parentscope
|
8
|
+
end
|
9
|
+
|
10
|
+
def call args
|
11
|
+
scope = ZScope.new @scope
|
12
|
+
@parameters.each do |p|
|
13
|
+
scope.set_local p.text, args.shift
|
14
|
+
end
|
15
|
+
|
16
|
+
result = nil
|
17
|
+
@body.each do |node|
|
18
|
+
result = @env.resolve node, scope
|
19
|
+
end
|
20
|
+
return result
|
21
|
+
end
|
22
|
+
|
23
|
+
def bind args
|
24
|
+
scope = ZScope.new @scope
|
25
|
+
i = 0
|
26
|
+
args.each do |a|
|
27
|
+
scope.set_local @parameters[i].text, a
|
28
|
+
i += 1
|
29
|
+
end
|
30
|
+
|
31
|
+
return ZBlock.new @body, @parameters[i..-1], scope, @env
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
class ZExternBlock < ZBlock
|
36
|
+
def initialize receiver, method, env, args = []
|
37
|
+
@env = env
|
38
|
+
@receiver = receiver
|
39
|
+
@method = method
|
40
|
+
@args = args
|
41
|
+
end
|
42
|
+
|
43
|
+
def parse_args args
|
44
|
+
return args.map do |a|
|
45
|
+
a = a.get if a.is_a? VariableReference
|
46
|
+
if a.is_a? ZNum or a.is_a? ZString or a.is_a? ZBool
|
47
|
+
a.value
|
48
|
+
else
|
49
|
+
a
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def call args
|
55
|
+
res = @receiver.send @method, *(@args + parse_args(args))
|
56
|
+
case res
|
57
|
+
when Fixnum, Float
|
58
|
+
return ZNum.new res, @env
|
59
|
+
when String
|
60
|
+
return ZString.new res, @env
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
def bind args
|
65
|
+
return ZExternBlock.new @receiver, @method, @env, @args + parse_args(args)
|
66
|
+
end
|
67
|
+
|
68
|
+
def inspect
|
69
|
+
return "#<EXTERN #{@receiver}\##{@method.to_s}>"
|
70
|
+
end
|
71
|
+
end
|
72
|
+
end
|
@@ -0,0 +1,104 @@
|
|
1
|
+
require 'zunscript/value'
|
2
|
+
require 'zunscript/scope'
|
3
|
+
require 'zunscript/block'
|
4
|
+
require 'colorize'
|
5
|
+
|
6
|
+
class Crutch
|
7
|
+
def puts_ *args
|
8
|
+
puts *args
|
9
|
+
end
|
10
|
+
|
11
|
+
def print_ *args
|
12
|
+
print *args #.join.colorize :green
|
13
|
+
puts
|
14
|
+
end
|
15
|
+
|
16
|
+
def add a, b
|
17
|
+
a + b
|
18
|
+
end
|
19
|
+
|
20
|
+
def multiply a, b
|
21
|
+
a * b
|
22
|
+
end
|
23
|
+
|
24
|
+
def if cond, tr, fl=nil
|
25
|
+
return tr.call if cond
|
26
|
+
return fl.call if fl
|
27
|
+
end
|
28
|
+
|
29
|
+
def range start, stop, step=1, each
|
30
|
+
(start..stop).step(step).each do |n|
|
31
|
+
each.call [ZunScript::ZNum.new(n, nil)]
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
module ZunScript
|
37
|
+
class Environment
|
38
|
+
def resolve node, scope = @rootscope
|
39
|
+
puts "#{node.line}: #{node.inspect}".colorize :yellow if @debug
|
40
|
+
case node.name
|
41
|
+
when "INVOKE"
|
42
|
+
block = resolve node[0], scope
|
43
|
+
block = block.get if block.is_a? VariableReference
|
44
|
+
throw "trying to invoke non-block: #{block.inspect} (#{node.line})" if not block.is_a? ZBlock
|
45
|
+
|
46
|
+
return block.call (node[1..-1].map do |c| resolve c, scope end)
|
47
|
+
when "BIND"
|
48
|
+
block = resolve node[0], scope
|
49
|
+
block = block.get if block.is_a? VariableReference
|
50
|
+
|
51
|
+
throw "trying to bind non-block: #{block.inspect} (#{node.line})" if not block.is_a? ZBlock
|
52
|
+
return block.bind (node[1..-1].map do |c| resolve c, scope end)
|
53
|
+
when "ASSIGN"
|
54
|
+
lval = resolve node[0]
|
55
|
+
throw "invalid LVALUE in assignment (#{node.line})" if not lval.is_a? VariableReference
|
56
|
+
|
57
|
+
return lval.assign (resolve node[1])
|
58
|
+
when "NUM"
|
59
|
+
return ZNum.new node[0].text.to_f, self
|
60
|
+
when "STR"
|
61
|
+
return ZString.new node[0].text[1..-2], self
|
62
|
+
when "BOOL"
|
63
|
+
return ZBool.new node[0].text == "true", self
|
64
|
+
when "BLK"
|
65
|
+
return ZBlock.new node[-1], node[0..-2], scope, self
|
66
|
+
when "VARIABLE"
|
67
|
+
x = node[0]
|
68
|
+
# puts "#{x.inspect}, #{node.inspect}"
|
69
|
+
return scope.find x.text
|
70
|
+
end
|
71
|
+
end
|
72
|
+
|
73
|
+
attr_reader :rootscope
|
74
|
+
def initialize debug: false
|
75
|
+
@rootscope = ZRootScope.new
|
76
|
+
@debug = debug
|
77
|
+
|
78
|
+
crutch = Crutch.new
|
79
|
+
@rootscope.set "print", ZExternBlock.new( crutch, :print_, self )
|
80
|
+
@rootscope.set "puts", ZExternBlock.new( crutch, :puts_, self )
|
81
|
+
@rootscope.set "add", ZExternBlock.new( crutch, :add, self )
|
82
|
+
@rootscope.set "multiply", ZExternBlock.new( crutch, :multiply, self )
|
83
|
+
@rootscope.set "for", ZExternBlock.new( crutch, :range, self )
|
84
|
+
@rootscope.set "if", ZExternBlock.new( crutch, :if, self )
|
85
|
+
end
|
86
|
+
|
87
|
+
def run_script script
|
88
|
+
tree = (ZunScript::Parser.new script).script.tree
|
89
|
+
if tree.type == 0 then
|
90
|
+
tree.each do |n|
|
91
|
+
res = resolve n
|
92
|
+
yield res if block_given?
|
93
|
+
end
|
94
|
+
else
|
95
|
+
res = interpret tree
|
96
|
+
yield res if block_given?
|
97
|
+
end
|
98
|
+
end
|
99
|
+
|
100
|
+
def run_line string
|
101
|
+
resolve ZunScript::Parser.new(string).line.tree
|
102
|
+
end
|
103
|
+
end
|
104
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
module ZunScript
|
2
|
+
class ZScope
|
3
|
+
def initialize parent = nil
|
4
|
+
@parent = parent
|
5
|
+
@hash = Hash.new
|
6
|
+
end
|
7
|
+
|
8
|
+
def first_with identifier
|
9
|
+
return @hash.has_key? identifier ? self : (@parent.first_with identifier)
|
10
|
+
end
|
11
|
+
|
12
|
+
def set_local identifier, value
|
13
|
+
return @hash[identifier] = value
|
14
|
+
end
|
15
|
+
|
16
|
+
def find identifier
|
17
|
+
return VariableReference.new (owner identifier), identifier
|
18
|
+
end
|
19
|
+
|
20
|
+
def get identifier
|
21
|
+
if @hash.has_key? identifier
|
22
|
+
return @hash[identifier]
|
23
|
+
end
|
24
|
+
return @parent.get identifier
|
25
|
+
#return @hash.has_key? identifier ? @hash[identifier] : (@parent.get identifier)
|
26
|
+
end
|
27
|
+
|
28
|
+
def owner identifier
|
29
|
+
(first_with identifier) or self
|
30
|
+
end
|
31
|
+
|
32
|
+
def set identifier, value
|
33
|
+
(owner identifier).set_local identifier, value
|
34
|
+
end
|
35
|
+
|
36
|
+
def inspect
|
37
|
+
@hash.to_s
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
class ZRootScope < ZScope
|
42
|
+
def initialize
|
43
|
+
super
|
44
|
+
end
|
45
|
+
|
46
|
+
def first_with identifier
|
47
|
+
return @hash.has_key? identifier ? self : nil
|
48
|
+
end
|
49
|
+
|
50
|
+
def get identifier
|
51
|
+
#puts "get #{identifier} @ root: #{@hash[identifier].inspect}"
|
52
|
+
return @hash[identifier]
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,67 @@
|
|
1
|
+
module ZunScript
|
2
|
+
class ZValue
|
3
|
+
def initialize env
|
4
|
+
@env = env
|
5
|
+
end
|
6
|
+
|
7
|
+
def inspect
|
8
|
+
return "#<ZVal: '#{value}'>" if respond_to? :value
|
9
|
+
return "#<#{self.class}>"
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
class ZNum < ZValue
|
14
|
+
attr_reader :value
|
15
|
+
|
16
|
+
def initialize value, env
|
17
|
+
super env
|
18
|
+
@value = value
|
19
|
+
end
|
20
|
+
|
21
|
+
def inspect
|
22
|
+
return "#<ZNum: #{value}>"
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
class ZString < ZValue
|
27
|
+
attr_reader :value
|
28
|
+
|
29
|
+
def initialize value, env
|
30
|
+
super env
|
31
|
+
@value = value
|
32
|
+
end
|
33
|
+
end
|
34
|
+
|
35
|
+
class ZBool < ZValue
|
36
|
+
attr_reader :value
|
37
|
+
|
38
|
+
def initialize value, env
|
39
|
+
super env
|
40
|
+
@value = value
|
41
|
+
end
|
42
|
+
end
|
43
|
+
|
44
|
+
class VariableReference < ZValue
|
45
|
+
def initialize scope, identifier
|
46
|
+
@scope = scope
|
47
|
+
@identifier = identifier
|
48
|
+
end
|
49
|
+
|
50
|
+
def method_missing m, *args
|
51
|
+
# puts "identifier: #{@identifier.inspect}"
|
52
|
+
(@scope.get @identifier).send m, *args
|
53
|
+
end
|
54
|
+
|
55
|
+
def get
|
56
|
+
@scope.get @identifier
|
57
|
+
end
|
58
|
+
|
59
|
+
def assign value
|
60
|
+
return @scope.set_local @identifier, value
|
61
|
+
end
|
62
|
+
|
63
|
+
def inspect
|
64
|
+
return "#<REF #{@identifier} @ #{@scope.inspect}>"
|
65
|
+
end
|
66
|
+
end
|
67
|
+
end
|
data/zunscript.gemspec
ADDED
@@ -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 'zunscript/version'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "zunscript"
|
8
|
+
spec.version = Zunscript::VERSION
|
9
|
+
spec.authors = ["Sol Bekic"]
|
10
|
+
spec.email = ["s0lll0s@blinkenshell.org"]
|
11
|
+
|
12
|
+
spec.summary = %q{ZunScript is a conceptual Scripting Language.}
|
13
|
+
spec.description = %q{The main goals are to boil the language down to a tiny but substantial feature set and to explore function binding}
|
14
|
+
spec.homepage = "https://github.com/S0lll0s/zunscript"
|
15
|
+
spec.license = "MIT"
|
16
|
+
|
17
|
+
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
18
|
+
spec.executables = ["zsi"]
|
19
|
+
spec.require_paths = ["lib", "ext"]
|
20
|
+
|
21
|
+
spec.extensions = ["ext/zunscript/extconf.rb"]
|
22
|
+
|
23
|
+
spec.add_development_dependency "bundler", "~> 1.9"
|
24
|
+
spec.add_development_dependency "rake", "~> 10.0"
|
25
|
+
|
26
|
+
spec.add_dependency "antlr3", "~> 1.10"
|
27
|
+
spec.add_dependency "trollop", "~> 1.16"
|
28
|
+
spec.add_dependency "colorize", "~> 0.7"
|
29
|
+
end
|
metadata
ADDED
@@ -0,0 +1,141 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: zunscript
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.1.1
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Sol Bekic
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2015-04-29 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: bundler
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.9'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.9'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: rake
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - "~>"
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '10.0'
|
34
|
+
type: :development
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - "~>"
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '10.0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: antlr3
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - "~>"
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '1.10'
|
48
|
+
type: :runtime
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - "~>"
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '1.10'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: trollop
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - "~>"
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '1.16'
|
62
|
+
type: :runtime
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - "~>"
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '1.16'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: colorize
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - "~>"
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0.7'
|
76
|
+
type: :runtime
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - "~>"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0.7'
|
83
|
+
description: The main goals are to boil the language down to a tiny but substantial
|
84
|
+
feature set and to explore function binding
|
85
|
+
email:
|
86
|
+
- s0lll0s@blinkenshell.org
|
87
|
+
executables:
|
88
|
+
- zsi
|
89
|
+
extensions:
|
90
|
+
- ext/zunscript/extconf.rb
|
91
|
+
extra_rdoc_files: []
|
92
|
+
files:
|
93
|
+
- ".gitignore"
|
94
|
+
- ".travis.yml"
|
95
|
+
- Gemfile
|
96
|
+
- LICENSE.txt
|
97
|
+
- README.md
|
98
|
+
- Rakefile
|
99
|
+
- bin/setup
|
100
|
+
- bin/zsi
|
101
|
+
- examples/test.zun
|
102
|
+
- ext/zunscript/Makefile
|
103
|
+
- ext/zunscript/ZunScript.g
|
104
|
+
- ext/zunscript/antlr4ruby
|
105
|
+
- ext/zunscript/ext.rb
|
106
|
+
- ext/zunscript/extconf.rb
|
107
|
+
- ext/zunscript/lexer.rb
|
108
|
+
- ext/zunscript/parser.rb
|
109
|
+
- lib/zunscript.rb
|
110
|
+
- lib/zunscript/block.rb
|
111
|
+
- lib/zunscript/environment.rb
|
112
|
+
- lib/zunscript/scope.rb
|
113
|
+
- lib/zunscript/value.rb
|
114
|
+
- lib/zunscript/version.rb
|
115
|
+
- zunscript.gemspec
|
116
|
+
homepage: https://github.com/S0lll0s/zunscript
|
117
|
+
licenses:
|
118
|
+
- MIT
|
119
|
+
metadata: {}
|
120
|
+
post_install_message:
|
121
|
+
rdoc_options: []
|
122
|
+
require_paths:
|
123
|
+
- lib
|
124
|
+
- ext
|
125
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
126
|
+
requirements:
|
127
|
+
- - ">="
|
128
|
+
- !ruby/object:Gem::Version
|
129
|
+
version: '0'
|
130
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
131
|
+
requirements:
|
132
|
+
- - ">="
|
133
|
+
- !ruby/object:Gem::Version
|
134
|
+
version: '0'
|
135
|
+
requirements: []
|
136
|
+
rubyforge_project:
|
137
|
+
rubygems_version: 2.4.5
|
138
|
+
signing_key:
|
139
|
+
specification_version: 4
|
140
|
+
summary: ZunScript is a conceptual Scripting Language.
|
141
|
+
test_files: []
|