nydp 0.0.6 → 0.0.7

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.
@@ -0,0 +1,22 @@
1
+ (register-test '(suite "Error Tests"
2
+ ("'ensuring gets called on the way out"
3
+ (let x 10
4
+ (ensure (assign x (+ x 11))
5
+ (assign x (+ x 22)))
6
+ x)
7
+ 43)
8
+
9
+ ("'on-err handles errors"
10
+ (let x nil
11
+ (on-err (= x "impossible")
12
+ (= x (nil nil nil)))
13
+ x)
14
+ "impossible")
15
+
16
+ ("'on-err handles errors but any ensuring clause gets called first"
17
+ (with (x nil y nil)
18
+ (on-err (= x 'impossible)
19
+ (ensure (assign y 'ensure-clause)
20
+ (nil nil nil)))
21
+ (list x y))
22
+ (impossible ensure-clause))))
@@ -1,4 +1,9 @@
1
1
  (register-test '(suite "Foundation Tests"
2
+ (suite "maths"
3
+ ("sqrt"
4
+ (sqrt 6.25)
5
+ 2.5))
6
+
2
7
  (suite "strings"
3
8
  (suite "string-split"
4
9
  ("splits a string using given expression"
@@ -23,6 +28,15 @@
23
28
  (type-of "foobar %%(+ 1 2)")
24
29
  string)))
25
30
 
31
+ (suite "eq?"
32
+ ("true for two empty symbols"
33
+ (eq? '|| '||)
34
+ t)
35
+
36
+ ("nil for two different symbols"
37
+ (eq? 'foo 'bar)
38
+ nil))
39
+
26
40
  (suite "truth and nil"
27
41
  ("t is boolean true"
28
42
  (if t "hello" "goodbye")
@@ -40,14 +54,6 @@
40
54
  (type-of nil)
41
55
  nil))
42
56
 
43
- (suite "Ensuring"
44
- ("gets called on the way out"
45
- (let x 10
46
- (ensuring (fn () (assign x (+ x 11)))
47
- (fn () (assign x (+ x 22))))
48
- x)
49
- 43))
50
-
51
57
  (suite "assignment with '="
52
58
  ("assigns a symbol"
53
59
  (pre-compile '(= this 'that))
@@ -66,20 +72,6 @@
66
72
  (pre-compile '(= a.b.c.d 42))
67
73
  (hash-set (hash-get (hash-get a 'b) 'c) 'd 42)))
68
74
 
69
-
70
- (suite "parse"
71
- ("parses a colon-syntax symbol"
72
- (parse "this:that")
73
- ((colon-syntax this that)) )
74
-
75
- ("parses a dot-syntax symbol"
76
- (parse "this.that.zozo")
77
- ((dot-syntax this that zozo)) )
78
-
79
- ("parses an expression"
80
- (parse "(foo bar \"hello, String\") 1 2 (3 t nil) nil")
81
- ((foo bar "hello, String") 1 2 (3 t nil))))
82
-
83
75
  (suite "isa"
84
76
  ("t for 'pair for list"
85
77
  (isa 'pair '(a b c))
@@ -0,0 +1,55 @@
1
+ (register-test '(suite "Parser tests"
2
+ (suite "brace-list"
3
+ ("parses an empty brace list"
4
+ (parse "{}")
5
+ ((brace-list)))
6
+
7
+ ("parses a single-item list"
8
+ (parse "{foo}")
9
+ ((brace-list foo)))
10
+
11
+ ("parses a list"
12
+ (parse "{foo bar 1 2 3}")
13
+ ((brace-list foo bar 1 2 3))))
14
+
15
+ (suite "parse"
16
+ ("parses an empty symbol"
17
+ (parse "||")
18
+ (||) )
19
+
20
+ ("parses a colon-syntax symbol"
21
+ (parse "this:that")
22
+ ((colon-syntax this that)) )
23
+
24
+ ("parses a dot-syntax symbol"
25
+ (parse "this.that.zozo")
26
+ ((dot-syntax this that zozo)) )
27
+
28
+ ("parses a mixed-syntax symbol"
29
+ (parse "this$that.zozo")
30
+ ((dot-syntax (dollar-syntax this that) zozo)))
31
+
32
+ ("parses a mixed-syntax prefix symbol"
33
+ (parse "$this.that.zozo")
34
+ ((dot-syntax (dollar-syntax || this) that zozo)))
35
+
36
+ ("parses a prefix dollar"
37
+ (parse "$this")
38
+ ((dollar-syntax || this)))
39
+
40
+ ("parses a prefix dollar-dot"
41
+ (parse "$.this")
42
+ ((dot-syntax (dollar-syntax || ||) this)))
43
+
44
+ ("parses an expression"
45
+ (parse "(foo bar \"hello, String\") 1 2 (3 t nil) nil")
46
+ ((foo bar "hello, String") 1 2 (3 t nil))))
47
+
48
+ (suite "parse-in-string"
49
+ ("parses a plain string"
50
+ (parse-in-string "hello, world, take me to your dealer")
51
+ "hello, world, take me to your dealer")
52
+
53
+ ("parses a plain string with interpolations"
54
+ (parse-in-string (joinstr "" (list "hello, " '~ "(world), take me to your " '~ "dealer please")))
55
+ (string-pieces "hello, " (world) ", take me to your " dealer " please")))))
@@ -7,33 +7,43 @@ module Nydp
7
7
  def self.loadfiles; PLUGINS.map(&:loadfiles).flatten ; end
8
8
  def self.testfiles; PLUGINS.map(&:testfiles).flatten ; end
9
9
  def self.plugin_names ; PLUGINS.map(&:name) ; end
10
- def self.loadall vm, ns, files
10
+ def self.loadall ns, files
11
+ vm = VM.new
11
12
  files.each { |f|
12
13
  reader = Nydp::StreamReader.new(File.new(f))
13
14
  Nydp::Runner.new(vm, ns, reader).run
14
15
  }
15
16
  end
16
17
 
17
- def self.repl
18
- puts "welcome to nydp"
18
+ def self.build_nydp extra_files=nil
19
19
  ns = { }
20
20
  setup(ns)
21
- vm = VM.new
22
- loadall vm, ns, loadfiles
21
+ loadall ns, loadfiles
22
+ loadall ns, extra_files if extra_files
23
+ ns
24
+ end
25
+
26
+ def self.apply_function ns, function_name, *args
27
+ function = Nydp::Symbol.mk(function_name, ns).value
28
+ args = Nydp::Pair.from_list args
29
+ vm = VM.new
30
+
31
+ function.invoke vm, args
32
+ return vm.pop_arg
33
+ end
34
+
35
+ def self.repl
36
+ puts "welcome to nydp"
37
+ puts "^D to exit"
23
38
  reader = Nydp::ReadlineReader.new $stdin, "nydp > "
24
- Nydp::Runner.new(vm, ns, reader, $stdout).run
39
+ Nydp::Runner.new(VM.new, build_nydp, reader, $stdout).run
25
40
  end
26
41
 
27
42
  def self.tests *options
28
43
  verbose = options.include?(:verbose) ? "t" : "nil"
29
44
  puts "welcome to nydp : running tests"
30
- ns = { }
31
- setup(ns)
32
- vm = VM.new
33
- loadall vm, ns, loadfiles
34
- loadall vm, ns, testfiles
35
45
  reader = Nydp::StringReader.new "(run-all-tests #{verbose})"
36
- Nydp::Runner.new(vm, ns, reader).run
46
+ Nydp::Runner.new(VM.new, build_nydp(testfiles), reader).run
37
47
  end
38
48
 
39
49
  end
@@ -30,9 +30,11 @@ module Nydp
30
30
  end
31
31
 
32
32
  def to_s
33
- "#assignment #{@instructions.cdr.car} #{@value_src}"
33
+ "#assignment #{@instructions.cdr.car} #{@value_src.inspect}"
34
34
  end
35
35
 
36
+ def inspect; to_s ; end
37
+
36
38
  def execute vm
37
39
  vm.push_instructions @instructions, vm.peek_context
38
40
  end
@@ -1,15 +1,12 @@
1
1
  require 'nydp'
2
+ require 'nydp/error'
2
3
 
3
4
  module Nydp::Builtin
4
5
  module Base
5
- def indent_text txt
6
- txt.split(/\n/).map { |line| " #{line}"}.join("\n")
7
- end
8
-
9
6
  def invoke vm, args
10
7
  builtin_invoke vm, args
11
8
  rescue Exception => e
12
- new_msg = "Invoking #{self.class.name}\nwith args #{args}\nraised\n#{indent_text e.message}"
9
+ new_msg = "Invoking #{self.class.name}\nwith args #{args}\nraised\n#{Nydp.indent_text e.message}"
13
10
  raise $!, new_msg, $!.backtrace
14
11
  end
15
12
  end
@@ -1,7 +1,10 @@
1
+ require "nydp/vm"
2
+
1
3
  class Nydp::Builtin::Ensuring
2
4
  include Nydp::Helper
3
5
 
4
6
  class InvokeProtection
7
+ include Nydp::VM::Finally
5
8
  attr_reader :protection
6
9
 
7
10
  def initialize protection
@@ -9,6 +9,10 @@ class Nydp::Builtin::Eval
9
9
  end
10
10
 
11
11
  def to_s
12
- "Builtin:eval"
12
+ "eval"
13
+ end
14
+
15
+ def inspect
16
+ "Nydp::Builtin::Eval"
13
17
  end
14
18
  end
@@ -0,0 +1,39 @@
1
+ require "nydp/vm"
2
+
3
+ class Nydp::Builtin::HandleError
4
+ include Nydp::Helper
5
+
6
+ class CatchError
7
+ include Nydp::Helper, Nydp::VM::HandleError
8
+
9
+ attr_reader :handler, :vm_arg_array_size
10
+
11
+ def initialize handler, vm_arg_array_size
12
+ @handler, @vm_arg_array_size = handler, vm_arg_array_size
13
+ end
14
+
15
+ def execute vm
16
+ e = vm.unhandled_error
17
+ vm.unhandled_error = nil
18
+ return unless e
19
+
20
+ vm.args = vm.args[0...vm_arg_array_size]
21
+
22
+ handler.invoke vm, cons(r2n e.message, nil)
23
+ end
24
+
25
+ def to_s
26
+ "(on-err: #{handler})"
27
+ end
28
+ end
29
+
30
+ def invoke vm, args
31
+ fn_handle = args.car
32
+ fn_tricky = args.cdr.car
33
+
34
+ catcher_instructions = Nydp::Pair.from_list [CatchError.new(fn_handle, vm.args.size)]
35
+ vm.push_instructions catcher_instructions, vm.peek_context
36
+
37
+ fn_tricky.invoke vm, Nydp.NIL
38
+ end
39
+ end
@@ -0,0 +1,11 @@
1
+ class Nydp::Builtin::ParseInString
2
+ def initialize ns
3
+ @parser = Nydp::Parser.new(ns)
4
+ end
5
+
6
+ def invoke vm, args
7
+ tokens = Nydp::Tokeniser.new Nydp::StringReader.new args.car.to_s
8
+ expr = @parser.string(tokens, "", :eof)
9
+ vm.push_arg expr
10
+ end
11
+ end
@@ -0,0 +1,5 @@
1
+ class Nydp::Builtin::Sqrt
2
+ def invoke vm, args
3
+ vm.push_arg Math.sqrt args.car
4
+ end
5
+ end
@@ -1,22 +1,54 @@
1
1
  module Nydp
2
+ class ContextLookup0 ; def self.get_context ctx; ctx; end; end
3
+ class ContextLookup1 ; def self.get_context ctx; ctx.parent; end; end
4
+ class ContextLookup2 ; def self.get_context ctx; ctx.parent.parent; end; end
5
+ class ContextLookup3 ; def self.get_context ctx; ctx.parent.parent.parent; end; end
6
+ class ContextLookup4 ; def self.get_context ctx; ctx.parent.parent.parent.parent; end; end
7
+ class ContextLookup5 ; def self.get_context ctx; ctx.parent.parent.parent.parent.parent; end; end
8
+ class ContextLookup6 ; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent; end; end
9
+ class ContextLookup7 ; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent; end; end
10
+ class ContextLookup8 ; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent; end; end
11
+ class ContextLookup9 ; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
12
+ class ContextLookup10; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
13
+ class ContextLookup11; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
14
+ class ContextLookup12; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
15
+ class ContextLookup13; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
16
+ class ContextLookup14; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
17
+ class ContextLookup15; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
18
+ class ContextLookup16; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
19
+ class ContextLookup17; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
20
+ class ContextLookup18; def self.get_context ctx; ctx.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent.parent; end; end
21
+ class ContextLookupN
22
+ def initialize depth ; @depth = depth ; end
23
+ def get_context ctx ; ctx.nth(@depth) ; end
24
+ end
25
+
2
26
  class ContextSymbol
3
- attr_accessor :depth, :name
27
+ attr_accessor :depth, :name, :binding_index
4
28
 
5
- def initialize depth, name
6
- @depth, @name = depth, name
29
+ def initialize depth, name, binding_index
30
+ @ctx_lookup = build_lookup depth
31
+ @depth, @name, @binding_index = depth, name, binding_index
7
32
  end
8
33
 
34
+ def get_context(context); @ctx_lookup.get_context context; end
35
+
9
36
  def value context
10
- context.nth(depth).at(name)
37
+ get_context(context).at_index(binding_index)
11
38
  end
12
39
 
13
40
  def assign value, context
14
- context.nth(depth).set(name, value)
41
+ get_context(context).set_index(binding_index, value)
15
42
  end
16
43
 
17
44
  def inspect; to_s; end
18
45
  def to_s
19
- "[#{depth}]#{name}"
46
+ "[#{depth}##{binding_index}]#{name}"
47
+ end
48
+
49
+ def build_lookup depth
50
+ fast = Nydp.const_get "ContextLookup#{depth}" rescue nil
51
+ return fast || ContextLookupN.new(depth)
20
52
  end
21
53
  end
22
54
  end
@@ -41,6 +41,7 @@ module Nydp
41
41
  Symbol.mk(:p, ns).assign(Nydp::Builtin::Puts.new)
42
42
  Symbol.mk(:PI, ns).assign Literal.new(3.1415)
43
43
  Symbol.mk(:nil, ns).assign Nydp.NIL
44
+ Symbol.mk(:sqrt, ns).assign Nydp::Builtin::Sqrt.new
44
45
  Symbol.mk(:t, ns).assign Nydp.T
45
46
  Symbol.mk(:sym, ns).assign Nydp::Builtin::ToSym.new(ns)
46
47
  Symbol.mk(:ensuring, ns).assign(Nydp::Builtin::Ensuring.new)
@@ -48,12 +49,14 @@ module Nydp
48
49
  Symbol.mk(:comment, ns).assign(Nydp::Builtin::Comment.new)
49
50
  Symbol.mk(:millisecs, ns).assign(Nydp::Builtin::Millisecs.new)
50
51
  Symbol.mk("load-tests", ns).assign(Nydp::Builtin::LoadTests.new(ns))
51
- Symbol.mk("random-string",ns).assign(Nydp::Builtin::RandomString.new)
52
- Symbol.mk("to-string", ns).assign(Nydp::Builtin::ToString.new)
53
- Symbol.mk("string-pieces",ns).assign(Nydp::Builtin::StringPieces.new)
54
- Symbol.mk("string-replace", ns).assign(Nydp::Builtin::StringReplace.new)
55
- Symbol.mk("string-split" , ns).assign(Nydp::Builtin::StringSplit.new )
56
- Symbol.mk("thread-locals" , ns).assign(Nydp::Builtin::ThreadLocals.new)
52
+ Symbol.mk("handle-error" , ns).assign(Nydp::Builtin::HandleError.new)
53
+ Symbol.mk("parse-in-string", ns).assign(Nydp::Builtin::ParseInString.new(ns))
54
+ Symbol.mk("random-string" , ns).assign(Nydp::Builtin::RandomString.new)
55
+ Symbol.mk("to-string" , ns).assign(Nydp::Builtin::ToString.new)
56
+ Symbol.mk("string-pieces" , ns).assign(Nydp::Builtin::StringPieces.new)
57
+ Symbol.mk("string-replace" , ns).assign(Nydp::Builtin::StringReplace.new)
58
+ Symbol.mk("string-split" , ns).assign(Nydp::Builtin::StringSplit.new )
59
+ Symbol.mk("thread-locals" , ns).assign(Nydp::Builtin::ThreadLocals.new)
57
60
  Symbol.mk("type-of", ns).assign(Nydp::Builtin::TypeOf.new(ns))
58
61
  Symbol.mk(:"eq?", ns).assign(Nydp::Builtin::IsEqual.new)
59
62
  Symbol.mk(:"pair?", ns).assign(Nydp::Builtin::IsPair.new)
@@ -1,4 +1,8 @@
1
1
  module Nydp
2
+ def self.indent_text txt
3
+ txt.split(/\n/).map { |line| " #{line}"}.join("\n")
4
+ end
5
+
2
6
  class Error < StandardError
3
7
  end
4
8
  end
@@ -19,7 +19,7 @@ module Nydp
19
19
  msg = "failed to execute invocation #{args.inspect}"
20
20
  msg += "\nsource was #{source.inspect}"
21
21
  msg += "\nfunction name was #{source.car.inspect}"
22
- i_f = InvocationFailed.new "#{msg}\n#{vm.error}#{e.message}"
22
+ i_f = InvocationFailed.new "#{msg}\n#{e.message}"
23
23
  i_f.set_backtrace e.backtrace
24
24
  raise i_f
25
25
  end
@@ -1,9 +1,10 @@
1
1
  class Nydp::LexicalContext
2
- attr_reader :values, :parent
2
+ attr_reader :names, :values, :parent
3
3
 
4
4
  def initialize parent
5
5
  @parent = parent
6
- @values = { }
6
+ @names = []
7
+ @values = []
7
8
  end
8
9
 
9
10
  def nth n
@@ -21,8 +22,17 @@ class Nydp::LexicalContext
21
22
  values[name]
22
23
  end
23
24
 
25
+ def at_index index
26
+ values[index]
27
+ end
28
+
24
29
  def set name, value
25
- values[name] = value
30
+ names << name
31
+ values << value
32
+ end
33
+
34
+ def set_index index, value
35
+ values[index] = value
26
36
  end
27
37
 
28
38
  def to_s_with_indent str