diff --git a/forge/builtins/builtins.go b/forge/builtins/builtins.go index 3d7ae4a..3825282 100644 --- a/forge/builtins/builtins.go +++ b/forge/builtins/builtins.go @@ -6,7 +6,7 @@ type FE = forge.FE type XT = forge.XT type builtins struct { - Add, Dup, Lit, Mult XT + Add, Dup, Get, Lit, Mult, Put XT } func Get(f FE) *builtins { @@ -27,7 +27,9 @@ func setup(f FE) *builtins { return &builtins{ Add: r("+", func(f FE, _ XT) { f.Push(f.Pop().(int) + f.Pop().(int)) }), Dup: r("dup", func(f FE, _ XT) { f.Push(f.Peek(0)) }), + Get: r("@", func(f FE, _ XT) { f.Push(f.Pop().(forge.FPtr).Value()) }), Lit: r("literal", func(f FE, _ XT) { f.Literal() }), Mult: r("*", func(f FE, _ XT) { f.Push(f.Pop().(int) * f.Pop().(int)) }), + Put: r("!", func(f FE, _ XT) { f.Pop().(forge.FPtr).Set(f.Pop()) }), } } diff --git a/forge/forge.go b/forge/forge.go index 09bb76e..ba77198 100644 --- a/forge/forge.go +++ b/forge/forge.go @@ -10,6 +10,8 @@ import ( type fitem interface{} type fptr = ptr.Ptr[fitem] +type FPtr = fptr + type fstack = stack.Stack[fitem] type fvoc = voc.Vocabulary[fitem] @@ -163,9 +165,9 @@ func (f *forgeEnv) Def(name string, items ...fitem) XT { return Register(f.voc, FCode(name, code)) } -func (f *forgeEnv) Const(name string, value fitem) XT { - data := newScalar().Append(value) - return Register(f.voc, Data(name, data, nil)) +func (f *forgeEnv) Create(name string, value fitem, code fptr) XT { + data := newScalar().Set(value) + return Register(f.voc, Data(name, data, code)) } func (f *forgeEnv) Literal() { @@ -195,5 +197,9 @@ func doDef(f *forgeEnv, xt XT) { } func doData(f *forgeEnv, xt XT) { - f.Push(xt.Data().Value()) + f.Push(xt.Data()) + code := xt.Code() + if code != nil { + f.Call(code) + } } diff --git a/tests/forge_test.go b/tests/forge_test.go index 7a2023d..0039ce6 100644 --- a/tests/forge_test.go +++ b/tests/forge_test.go @@ -22,7 +22,8 @@ func ExecTest(t *testing.T) { sq := fe.Def("square", b.Dup, b.Mult) fe.Exec(b.Lit, 3, sq, b.Lit, 2, b.Add) t.AssertEqual(fe.Pop(), 11) - seven := fe.Const("seven", 7) + seven := fe.Create("seven", 7, fe.Code(b.Get)) + //fe.Exec(b.Lit, 7, seven, b.Put) fe.Exec(b.Lit, 3, seven, sq, b.Add) t.AssertEqual(fe.Pop(), 52) }