all repos — min @ de24bac6ab19ebc60478fc68abd48b5aa256ea4d

A small but practical concatenative programming language.

Added module operator and sigil; removed localSymbol (not necessary)
h3rald h3rald@h3rald.com
Sun, 26 Jun 2016 18:53:37 +0200
commit

de24bac6ab19ebc60478fc68abd48b5aa256ea4d

parent

357efcbe09d7585c9fd84dd7063387dd046b80ca

6 files changed, 103 insertions(+), 131 deletions(-)

jump to
M core/utils.nimcore/utils.nim

@@ -94,16 +94,7 @@ return scope

proc symbol*(scope: ref MinScope, sym: string, p: MinOperator): ref MinScope = scope.symbols[sym] = p - #if not scope.parent.isNil: - # scope.parent.symbols[scope.name & ":" & sym] = p return scope - -proc localSymbol*(i: In, obj: MinValue, objType: string, body: MinOperator): MinOperator = - if not obj.isObject(objType): - raiseInvalid("Object is not a socket") - return proc(i: In) = - i.push @[obj] - i.body() proc sigil*(scope: ref MinScope, sym: string, p: MinOperator): ref MinScope = scope.previous.sigils[sym] = p
M lib/min_lang.nimlib/min_lang.nim

@@ -86,18 +86,28 @@ .symbol("scope") do (i: In):

var code: MinValue i.reqQuotation code code.filename = i.filename + code.objType = "scope" i.unquote("<scope>", code) i.push @[code].newVal + .symbol("module") do (i: In): + var code, name: MinValue + i.reqStringLike name + i.reqQuotation code + code.filename = i.filename + code.objType = "module" + i.unquote("<module>", code) + i.scope.symbols[name.getString] = proc(i: In) = + i.push code + .symbol("import") do (i: In): var mdl, rawName: MinValue var name: string - i.reqString rawName - name = rawName.strVal + i.reqStringLike rawName + name = rawName.getString i.scope.getSymbol(name)(i) i.reqQuotation mdl if mdl.scope.isNotNil: - #echo "MODULE SCOPE PARENT: ", mdl.scope.name for sym, val in mdl.scope.symbols.pairs: i.debug "[import] $1:$2" % [i.scope.name, sym] i.scope.symbols[sym] = val

@@ -155,29 +165,6 @@ raiseUndefined("Symbol '$1' not found in scope '$2'" % [s, i.scope.fullname])

# Restore original quotation sProc(i) i.scope = origScope - - #var symbols, target: MinValue - #i.reqTwoQuotations symbols, target - #let vals = symbols.qVal - #var q: MinValue - #if vals.len == 0: - # raiseInvalid("No symbol to call") - #let origScope = i.scope - #i.scope = target.scope - #for c in 0..vals.len-1: - # if not vals[c].isStringLike: - # raiseInvalid("Quotation must contain only symbols or strings") - # let symbol = vals[c].getString - # let qProc = i.scope.getSymbol(symbol) - # if qProc.isNil: - # raiseUndefined("Symbol '$1' not found in scope '$2'" % [symbol, i.scope.fullname]) - # qProc(i) - # if vals.len > 1 and c < vals.len-1: - # q = i.pop - # if not q.isQuotation: - # raiseInvalid("Unable to evaluate symbol '$1'" % [symbol]) - # i.scope = q.scope - #i.scope = origScope .symbol("inspect") do (i: In): var scope: MinValue
M lib/min_net.nimlib/min_net.nim

@@ -7,88 +7,6 @@ ../core/utils

# Network -var symbols*: CritBitTree[proc(obj: Val, i: In): MinOperator] - -proc socketSymbol(name: string, body: proc(q: Val, i: In))= - symbols[name] = proc(obj: Val, i: In): MinOperator = - i.localSymbol(obj, "socket") do (i: In): - var q: MinValue - i.reqObject "socket", q - q.body(i) - -socketSymbol("domain") do (q: Val, i: In): - i.push q - i.push q.qVal[0].symVal.newVal - -socketSymbol("type") do (q: Val, i: In): - i.push q - i.push q.qVal[1].symVal.newVal - -socketSymbol("protocol") do (q: Val, i: In): - i.push q - i.push q.qVal[2].symVal.newVal - -socketSymbol("close") do (q: Val, i: In): - q.to(Socket).close() - -socketSymbol("listen") do (q: Val, i: In): - var port: MinValue - i.reqInt port - var socket = q.to(Socket) - socket.bindAddr(Port(port.intVal)) - q.qVal.add "0.0.0.0".newSym - q.qVal.add port - q.scope.symbols["address"] = proc (i:In) = - i.push "0.0.0.0".newVal - q.scope.symbols["port"] = proc (i:In) = - i.push port - socket.listen() - i.push q - -socketSymbol("accept") do (q: Val, i: In): - # Open same socket type as server - i.eval "$1 net %^socket" % [$q.qVal[0..2].newVal] - var clientVal: MinValue - i.reqObject "socket", clientVal - var client = clientVal.to(Socket) - var address = "" - q.to(Socket).acceptAddr(client, address) - clientVal.qVal.add address.newSym - i.push clientVal - -socketSymbol("connect") do (q: Val, i: In): - var q, address, port: MinValue - i.reqInt port - i.reqString address - q.to(Socket).connect(address.strVal, Port(port.intVal)) - q.qVal.add address.strVal.newSym - q.qVal.add port - q.scope.symbols["client-address"] = proc (i:In) = - i.push address.strVal.newVal - q.scope.symbols["client-port"] = proc (i:In) = - i.push port - i.push q - -socketSymbol("send") do (q: Val, i: In): - var s: MinValue - i.reqString s - q.to(Socket).send s.strVal - i.push q - -socketSymbol("recv") do (q: Val, i: In): - var size: MinValue - i.reqInt size - var s = "" - discard q.to(Socket).recv(s, size.intVal.int) - i.push q - i.push s.newVal - -socketSymbol("recv-line") do (q: Val, i: In): - var s = "" - q.to(Socket).readLine(s) - i.push @[q] - i.push s.newVal - define("net") .symbol("^socket") do (i: In):

@@ -125,16 +43,87 @@ var socket = newSocket(domain, sockettype, protocol)

q.objType = "socket" q.obj = socket[].addr i.newScope("<socket>", q) - q.scope.symbols["domain"] = symbols["domain"](q, i) - q.scope.symbols["type"] = symbols["type"](q, i) - q.scope.symbols["protocol"] = symbols["protocol"](q, i) - q.scope.symbols["close"] = symbols["close"](q, i) - q.scope.symbols["listen"] = symbols["listen"](q, i) - q.scope.symbols["accept"] = symbols["accept"](q, i) - q.scope.symbols["connect"] = symbols["connect"](q, i) - q.scope.symbols["send"] = symbols["send"](q, i) - q.scope.symbols["recv"] = symbols["recv"](q, i) - q.scope.symbols["recv-line"] = symbols["recv-line"](q, i) + + q.scope + .symbol("domain") do (i: In): + i.push q + i.push q.qVal[0].symVal.newVal + + .symbol("type") do (i: In): + i.push q + i.push q.qVal[1].symVal.newVal + + .symbol("protocol") do (i: In): + i.push q + i.push q.qVal[2].symVal.newVal + + .symbol("close") do (i: In): + q.to(Socket).close() + + .symbol("listen") do (i: In): + var port: MinValue + i.reqInt port + var socket = q.to(Socket) + socket.bindAddr(Port(port.intVal)) + q.qVal.add "0.0.0.0".newSym + q.qVal.add port + q.scope + .symbol("address") do (i:In): + i.push "0.0.0.0".newVal + .symbol("port") do (i:In): + i.push port + .finalize() + socket.listen() + i.push q + + .symbol("accept") do (i: In): + # Open same socket type as server + i.eval "$1 net %^socket" % [$q.qVal[0..2].newVal] + var clientVal: MinValue + i.reqObject "socket", clientVal + var client = clientVal.to(Socket) + var address = "" + q.to(Socket).acceptAddr(client, address) + clientVal.qVal.add address.newSym + i.push clientVal + + .symbol("connect") do (i: In): + var q, address, port: MinValue + i.reqInt port + i.reqString address + q.to(Socket).connect(address.strVal, Port(port.intVal)) + q.qVal.add address.strVal.newSym + q.qVal.add port + q.scope + .symbol("client-address") do (i:In): + i.push address.strVal.newVal + .symbol("client-port") do (i:In): + i.push port + .finalize() + i.push q + + .symbol("send") do (i: In): + var s: MinValue + i.reqString s + q.to(Socket).send s.strVal + i.push q + + .symbol("recv") do (i: In): + var size: MinValue + i.reqInt size + var s = "" + discard q.to(Socket).recv(s, size.intVal.int) + i.push q + i.push s.newVal + + .symbol("recv-line") do (i: In): + var s = "" + q.to(Socket).readLine(s) + i.push @[q] + i.push s.newVal + + .finalize() + i.push q .finalize()
M lib/prelude.minlib/prelude.min

@@ -19,6 +19,7 @@ (system) (!) sigil

(run) (&) sigil (load) (@) sigil (call) (%) sigil +(module) (=) sigil ; Aliases 'define ::
M tests/lang.mintests/lang.min

@@ -1,11 +1,15 @@

@test #test + "lang" describe - (symbols size put 175 ==) assert + "Total Symbols: " print! symbols size put! + " Total Sigils: " print! sigils size put! - (sigils size 10 ==) assert + (symbols size 176 ==) assert + + (sigils size 11 ==) assert (debug? false ==) assert

@@ -23,7 +27,7 @@

( ( (+) :myplus - ) => :mymath + ) =mymath ) :defmod (defmod symbols "mymath" contains) assert
M tests/test.mintests/test.min

@@ -50,4 +50,4 @@ )

map ) :report -) => :test +) =test