defined the value type Value_t to be interface{} in place of unsafe.Pointer
This commit is contained in:
parent
1ad6779aa4
commit
3cae246546
@ -16,8 +16,9 @@ func main() {
|
|||||||
r *bufio.Reader
|
r *bufio.Reader
|
||||||
c rune
|
c rune
|
||||||
node *pcl.Cnode_t
|
node *pcl.Cnode_t
|
||||||
v *string
|
v pcl.Value_t
|
||||||
err error
|
|
||||||
|
err error
|
||||||
)
|
)
|
||||||
|
|
||||||
if len(os.Args) != 2 {
|
if len(os.Args) != 2 {
|
||||||
@ -73,7 +74,7 @@ func main() {
|
|||||||
if v == nil {
|
if v == nil {
|
||||||
panic("return value mut not be nil")
|
panic("return value mut not be nil")
|
||||||
}
|
}
|
||||||
fmt.Printf("RETURN VALUE = [%s]\n", *v)
|
fmt.Printf("RETURN VALUE = [%s]\n", *v.(*string))
|
||||||
|
|
||||||
/*
|
/*
|
||||||
err = interp.FeedRunes([]rune(`
|
err = interp.FeedRunes([]rune(`
|
||||||
|
201
interp/eval.go
201
interp/eval.go
@ -5,7 +5,7 @@ import (
|
|||||||
"unsafe"
|
"unsafe"
|
||||||
)
|
)
|
||||||
|
|
||||||
var debug bool = true
|
var debug bool = false
|
||||||
|
|
||||||
var err_num_args *error_t = &error_t{msg: "wrong number of arguments"}
|
var err_num_args *error_t = &error_t{msg: "wrong number of arguments"}
|
||||||
|
|
||||||
@ -26,12 +26,10 @@ func (p *process_t) push_cnode_value(val *Cnode_t) error {
|
|||||||
return fmt.Errorf("stack full")
|
return fmt.Errorf("stack full")
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: using the last bit won't be compatible with go's GC.
|
p.vstack[p.vsp] = val
|
||||||
// CHANGE to use inteface{} or devise a different scheme...
|
|
||||||
p.vstack[p.vsp] = unsafe.Pointer(uintptr(unsafe.Pointer(val)) | 1)
|
|
||||||
p.vsp++
|
p.vsp++
|
||||||
p.ctx.count++
|
p.ctx.count++
|
||||||
fmt.Printf("push_cnode_value = ctx.count => %d\n", p.ctx.count)
|
//fmt.Printf("push_cnode_value = ctx.count => %d\n", p.ctx.count)
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
@ -41,30 +39,38 @@ func (p *process_t) push_string_value(val string) error {
|
|||||||
return fmt.Errorf("stack full")
|
return fmt.Errorf("stack full")
|
||||||
}
|
}
|
||||||
|
|
||||||
p.vstack[p.vsp] = unsafe.Pointer(&val)
|
p.vstack[p.vsp] = &val
|
||||||
p.vsp++
|
p.vsp++
|
||||||
p.ctx.count++
|
p.ctx.count++
|
||||||
fmt.Printf("push_string_value = ctx.count => %d\n", p.ctx.count)
|
//fmt.Printf("push_string_value = ctx.count => %d\n", p.ctx.count)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) merge_top_values() error {
|
func (p *process_t) merge_top_values() error {
|
||||||
var new_val string
|
var new_val string
|
||||||
|
var v1, v2 *string
|
||||||
|
|
||||||
if p.vsp < 2 {
|
if p.vsp < 2 {
|
||||||
return fmt.Errorf("stack corrupt")
|
return fmt.Errorf("stack corrupt")
|
||||||
}
|
}
|
||||||
new_val = *(*string)(p.vstack[p.vsp-2]) + *(*string)(p.vstack[p.vsp-1])
|
|
||||||
|
v1, _ = p.vstack[p.vsp-2].(*string)
|
||||||
|
v2, _ = p.vstack[p.vsp-1].(*string)
|
||||||
|
//new_val = *(*string)(p.vstack[p.vsp-2]) + *(*string)(p.vstack[p.vsp-1])
|
||||||
|
new_val = *v1 + *v2
|
||||||
p.vsp--
|
p.vsp--
|
||||||
p.vstack[p.vsp] = nil
|
p.vstack[p.vsp] = nil
|
||||||
p.vstack[p.vsp-1] = unsafe.Pointer(&new_val)
|
p.vstack[p.vsp-1] = unsafe.Pointer(&new_val)
|
||||||
p.ctx.count--
|
p.ctx.count--
|
||||||
fmt.Printf("merge_top_values = ctx.count => %d\n", p.ctx.count)
|
|
||||||
|
if debug {
|
||||||
|
fmt.Printf("merge_top_values = ctx.count => %d\n", p.ctx.count)
|
||||||
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) pop_value() unsafe.Pointer {
|
func (p *process_t) pop_value() Value_t {
|
||||||
var v unsafe.Pointer
|
var v Value_t
|
||||||
p.vsp--
|
p.vsp--
|
||||||
v = p.vstack[p.vsp]
|
v = p.vstack[p.vsp]
|
||||||
p.vstack[p.vsp] = nil
|
p.vstack[p.vsp] = nil
|
||||||
@ -78,6 +84,11 @@ func (p *process_t) call() error {
|
|||||||
)
|
)
|
||||||
|
|
||||||
callee = p.GetCalleeName()
|
callee = p.GetCalleeName()
|
||||||
|
|
||||||
|
if debug {
|
||||||
|
fmt.Printf("calling..... [%s]\n", *callee)
|
||||||
|
}
|
||||||
|
|
||||||
// TODO: use a map
|
// TODO: use a map
|
||||||
switch *callee {
|
switch *callee {
|
||||||
case "if":
|
case "if":
|
||||||
@ -97,10 +108,12 @@ func (p *process_t) call() error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) GetCalleeName() *string {
|
func (p *process_t) GetCalleeName() *string {
|
||||||
return (*string)(p.vstack[p.vsp-p.ctx.count+1])
|
var v *string
|
||||||
|
v, _ = (p.vstack[p.vsp-p.ctx.count+1]).(*string)
|
||||||
|
return v
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) GetArg(idx int) unsafe.Pointer {
|
func (p *process_t) GetArg(idx int) Value_t {
|
||||||
return (p.vstack[p.vsp-p.ctx.count+2+idx])
|
return (p.vstack[p.vsp-p.ctx.count+2+idx])
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -108,11 +121,14 @@ func (p *process_t) GetNumArgs() int {
|
|||||||
return p.ctx.count - 2
|
return p.ctx.count - 2
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) Return(val string) {
|
func (p *process_t) Return(val Value_t) {
|
||||||
p.vstack[p.vsp-p.ctx.count] = unsafe.Pointer(&val)
|
p.vstack[p.vsp-p.ctx.count] = val
|
||||||
}
|
}
|
||||||
|
|
||||||
func (p *process_t) push_context(node *Cnode_t, container_node *Cnode_t) {
|
func (p *process_t) push_context(node *Cnode_t, container_node *Cnode_t) {
|
||||||
|
if debug {
|
||||||
|
fmt.Printf("PUSHING CONTEXT.....\n")
|
||||||
|
}
|
||||||
p.ctx = &context_t{count: 0, parent_ctx: p.ctx, parent_node: node, container_node: container_node}
|
p.ctx = &context_t{count: 0, parent_ctx: p.ctx, parent_node: node, container_node: container_node}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -123,6 +139,10 @@ func (p *process_t) pop_context(clear_vstack bool) (*Cnode_t, *Cnode_t) {
|
|||||||
container *Cnode_t
|
container *Cnode_t
|
||||||
)
|
)
|
||||||
|
|
||||||
|
if debug {
|
||||||
|
fmt.Printf("POPPING CONTEXT.....is_stmt/clear_vstack[%v]\n", clear_vstack)
|
||||||
|
}
|
||||||
|
|
||||||
node = p.ctx.parent_node
|
node = p.ctx.parent_node
|
||||||
container = p.ctx.container_node
|
container = p.ctx.container_node
|
||||||
|
|
||||||
@ -137,9 +157,9 @@ func (p *process_t) pop_context(clear_vstack bool) (*Cnode_t, *Cnode_t) {
|
|||||||
}
|
}
|
||||||
p.ctx = p.ctx.parent_ctx
|
p.ctx = p.ctx.parent_ctx
|
||||||
|
|
||||||
// if p.ctx != nil {
|
// if p.ctx != nil {
|
||||||
// p.ctx.count++ // let the return value be the argument to the caller
|
// p.ctx.count++ // let the return value be the argument to the caller
|
||||||
// }
|
// }
|
||||||
|
|
||||||
return node, container
|
return node, container
|
||||||
}
|
}
|
||||||
@ -147,13 +167,24 @@ func (p *process_t) pop_context(clear_vstack bool) (*Cnode_t, *Cnode_t) {
|
|||||||
func (interp *Interp) dump_vstack(p *process_t) {
|
func (interp *Interp) dump_vstack(p *process_t) {
|
||||||
fmt.Printf("p.VSP => %d\n", p.vsp)
|
fmt.Printf("p.VSP => %d\n", p.vsp)
|
||||||
for i := 0; i < p.vsp; i++ {
|
for i := 0; i < p.vsp; i++ {
|
||||||
x := uintptr(p.vstack[i])
|
/*
|
||||||
if x&1 == 0 {
|
x := uintptr(p.vstack[i])
|
||||||
// string value
|
if x&1 == 0 {
|
||||||
fmt.Printf(" %d => [%s]\n", i, *(*string)(p.vstack[i]))
|
// string value
|
||||||
} else {
|
fmt.Printf(" %d => [%s]\n", i, *(*string)(p.vstack[i]))
|
||||||
// cnode value
|
} else {
|
||||||
fmt.Printf(" %d => cnode %p", i, p.vstack[i]) // TODO: strip 1 off
|
// cnode value
|
||||||
|
fmt.Printf(" %d => cnode %p", i, p.vstack[i]) // TODO: strip 1 off
|
||||||
|
}*/
|
||||||
|
switch t := p.vstack[i].(type) {
|
||||||
|
case *string:
|
||||||
|
fmt.Printf(" %d => [%s]\n", i, t)
|
||||||
|
case *Cnode_t:
|
||||||
|
fmt.Printf(" %d => ", i)
|
||||||
|
interp.dump_cnodes(t, false)
|
||||||
|
fmt.Printf("\n")
|
||||||
|
default:
|
||||||
|
panic("internal error - unrecognized value")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -182,15 +213,16 @@ puts "hello" world
|
|||||||
[STMT]
|
[STMT]
|
||||||
[TEXT|null] [TEXT|1]
|
[TEXT|null] [TEXT|1]
|
||||||
*/
|
*/
|
||||||
func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error) {
|
func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (Value_t, error) {
|
||||||
var (
|
var (
|
||||||
p process_t
|
p process_t
|
||||||
v *string
|
v Value_t
|
||||||
stmt_node *Cnode_t
|
stmt_node *Cnode_t
|
||||||
upper_node *Cnode_t
|
upper_node *Cnode_t
|
||||||
inner_node *Cnode_t
|
inner_node *Cnode_t
|
||||||
is_stmt bool
|
is_stmt bool
|
||||||
err error
|
err error
|
||||||
|
org_vsp int
|
||||||
)
|
)
|
||||||
|
|
||||||
v = new(string) // TODO: change new(string) to a const
|
v = new(string) // TODO: change new(string) to a const
|
||||||
@ -199,19 +231,22 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
upper_node = container_node
|
upper_node = container_node
|
||||||
stmt_node = upper_node.child // the first statement
|
stmt_node = upper_node.child // the first statement
|
||||||
|
|
||||||
|
org_vsp = p.vsp
|
||||||
fmt.Printf("START p.sp = %d\n", p.vsp)
|
fmt.Printf("START p.sp = %d\n", p.vsp)
|
||||||
|
|
||||||
for stmt_node != nil {
|
if stmt_node == nil {
|
||||||
|
goto done
|
||||||
|
}
|
||||||
|
|
||||||
|
for {
|
||||||
start_over_0:
|
start_over_0:
|
||||||
if stmt_node.code != CNODE_STMT {
|
if stmt_node.code != CNODE_STMT {
|
||||||
panic("internal error - not statement node")
|
panic("internal error - not statement node")
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("PUSHING CONTEXT.....\n")
|
|
||||||
p.push_context(stmt_node, upper_node)
|
p.push_context(stmt_node, upper_node)
|
||||||
p.push_string_value("") // placeholder for return value
|
p.push_string_value("") // placeholder for return value
|
||||||
|
|
||||||
//start_over:
|
|
||||||
inner_node = stmt_node.child
|
inner_node = stmt_node.child
|
||||||
resume:
|
resume:
|
||||||
for inner_node != nil {
|
for inner_node != nil {
|
||||||
@ -235,7 +270,6 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
|
|
||||||
case CNODE_DQUOTE:
|
case CNODE_DQUOTE:
|
||||||
if inner_node.child != nil {
|
if inner_node.child != nil {
|
||||||
fmt.Printf("PUSHING CONTEXT.....\n")
|
|
||||||
p.push_context(stmt_node, inner_node)
|
p.push_context(stmt_node, inner_node)
|
||||||
//p.push_string_value("") // no placeholder for return value is needed
|
//p.push_string_value("") // no placeholder for return value is needed
|
||||||
inner_node = inner_node.child
|
inner_node = inner_node.child
|
||||||
@ -264,6 +298,9 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
// TODO: many more types...
|
// TODO: many more types...
|
||||||
case CNODE_JOIN:
|
case CNODE_JOIN:
|
||||||
p.merge_top_values()
|
p.merge_top_values()
|
||||||
|
|
||||||
|
case CNODE_INIT:
|
||||||
|
panic("internal error - INIT node must not appear inside a statement")
|
||||||
}
|
}
|
||||||
|
|
||||||
inner_node = inner_node.next
|
inner_node = inner_node.next
|
||||||
@ -273,10 +310,7 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
interp.dump_vstack(&p)
|
interp.dump_vstack(&p)
|
||||||
}
|
}
|
||||||
//fmt.Printf("p.ctx.parent_node.code %d p.ctx.container_node.code %d CNODE_STMT %d CNODE_DQUOTE %d CNODE_BRACKET %d\n", p.ctx.parent_node.code, p.ctx.container_node.code, CNODE_STMT, CNODE_DQUOTE, CNODE_BRACKET)
|
//fmt.Printf("p.ctx.parent_node.code %d p.ctx.container_node.code %d CNODE_STMT %d CNODE_DQUOTE %d CNODE_BRACKET %d\n", p.ctx.parent_node.code, p.ctx.container_node.code, CNODE_STMT, CNODE_DQUOTE, CNODE_BRACKET)
|
||||||
if p.ctx.container_node.code == CNODE_INIT || p.ctx.container_node.code == CNODE_BRACKET {
|
if p.ctx.container_node.code == CNODE_INIT || p.ctx.container_node.code == CNODE_BRACKET || p.ctx.container_node.code == CNODE_BRACE {
|
||||||
if debug {
|
|
||||||
fmt.Printf("calling..... [%s]\n", *p.GetCalleeName())
|
|
||||||
}
|
|
||||||
err = p.call()
|
err = p.call()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
goto oops
|
goto oops
|
||||||
@ -287,7 +321,6 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
is_stmt = false
|
is_stmt = false
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("POPPING CONTEXT.....is_stmt[%v]\n", is_stmt)
|
|
||||||
stmt_node, upper_node = p.pop_context(is_stmt)
|
stmt_node, upper_node = p.pop_context(is_stmt)
|
||||||
if upper_node != container_node {
|
if upper_node != container_node {
|
||||||
if debug {
|
if debug {
|
||||||
@ -296,7 +329,7 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
|
|
||||||
if upper_node.code != CNODE_BRACKET {
|
if upper_node.code != CNODE_BRACKET {
|
||||||
inner_node = upper_node.next // as if it hit the bottom of the innner for loop
|
inner_node = upper_node.next // as if it hit the bottom of the innner for loop
|
||||||
p.ctx.count++; // use return value on the stack as an argument
|
p.ctx.count++ // use return value on the stack as an argument
|
||||||
goto resume
|
goto resume
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -317,76 +350,100 @@ func (interp *Interp) eval_stmt_nodes(container_node *Cnode_t) (*string, error)
|
|||||||
if upper_node.code != CNODE_BRACKET {
|
if upper_node.code != CNODE_BRACKET {
|
||||||
panic("internal error - invalid cnode type in the context statck")
|
panic("internal error - invalid cnode type in the context statck")
|
||||||
}
|
}
|
||||||
fmt.Printf("POPPING CONTEXT.....false\n")
|
|
||||||
//stmt_node, upper_node = p.pop_context(false)
|
|
||||||
inner_node = upper_node.next
|
|
||||||
fmt.Printf(">>>>>>>>>>>>>>>>>> vsp %d ctx.count %d\n", p.vsp, p.ctx.count)
|
|
||||||
|
|
||||||
p.ctx.count++; // use the result value as an argument
|
inner_node = upper_node.next
|
||||||
|
//fmt.Printf(">>>>>>>>>>>>>>>>>> vsp %d ctx.count %d\n", p.vsp, p.ctx.count)
|
||||||
|
|
||||||
|
p.ctx.count++ // use the result value as an argument
|
||||||
goto resume
|
goto resume
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("POPVAL...\n")
|
v = p.pop_value() // get the return value of the statement.
|
||||||
v = (*string)(p.pop_value()) // get the return value of the statement.
|
|
||||||
if debug {
|
if debug {
|
||||||
interp.dump_vstack(&p)
|
interp.dump_vstack(&p)
|
||||||
}
|
}
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("POPVAL...\n")
|
v = p.pop_value() // get the return value of the statement.
|
||||||
v = (*string)(p.pop_value()) // get the return value of the statement.
|
|
||||||
if debug {
|
if debug {
|
||||||
interp.dump_vstack(&p)
|
interp.dump_vstack(&p)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
done:
|
||||||
|
|
||||||
if debug {
|
if debug {
|
||||||
interp.dump_vstack(&p)
|
interp.dump_vstack(&p)
|
||||||
fmt.Printf("END p.sp = %d\n", p.vsp)
|
fmt.Printf("END p.sp = %d\n", p.vsp)
|
||||||
}
|
}
|
||||||
|
if p.vsp != org_vsp {
|
||||||
|
panic("internal error - stack not clean")
|
||||||
|
}
|
||||||
return v, nil
|
return v, nil
|
||||||
|
|
||||||
oops:
|
oops:
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func (interp *Interp) eval_arg(p *process_t, pos int) (*string, error) {
|
func (interp *Interp) eval_arg(p *process_t, pos int) (Value_t, error) {
|
||||||
var (
|
/*
|
||||||
ptr uintptr
|
var (
|
||||||
)
|
ptr uintptr
|
||||||
|
)
|
||||||
|
|
||||||
ptr = uintptr(p.GetArg(pos))
|
ptr = uintptr(p.GetArg(pos))
|
||||||
if ptr&1 == 1 { // cnode
|
if ptr&1 == 1 { // cnode
|
||||||
ptr &= ^uintptr(1)
|
ptr &= ^uintptr(1)
|
||||||
//interp.dump_cnodes((*Cnode_t)(unsafe.Pointer(ptr)), true)
|
//interp.dump_cnodes((*Cnode_t)(unsafe.Pointer(ptr)), true)
|
||||||
//return interp.eval_atom_node((*Cnode_t)(unsafe.Pointer(ptr)).child)
|
//return interp.eval_atom_node((*Cnode_t)(unsafe.Pointer(ptr)).child)
|
||||||
return interp.eval_stmt_nodes((*Cnode_t)(unsafe.Pointer(ptr)))
|
return interp.eval_stmt_nodes((*Cnode_t)(unsafe.Pointer(ptr)))
|
||||||
} else {
|
} else {
|
||||||
return (*string)(unsafe.Pointer(ptr)), nil
|
return (*string)(unsafe.Pointer(ptr)), nil
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
switch t := p.GetArg(pos).(type) {
|
||||||
|
case *string:
|
||||||
|
return t, nil
|
||||||
|
case *Cnode_t:
|
||||||
|
return interp.eval_stmt_nodes(t)
|
||||||
|
default:
|
||||||
|
panic("internal error - argument type unrecognized")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (interp *Interp) eval_arg_literally(p *process_t, pos int) (*string, error) {
|
func (interp *Interp) eval_arg_literally(p *process_t, pos int) (Value_t, error) {
|
||||||
var (
|
/*
|
||||||
ptr uintptr
|
var (
|
||||||
//cnode *Cnode_t
|
ptr uintptr
|
||||||
)
|
//cnode *Cnode_t
|
||||||
|
)
|
||||||
|
|
||||||
ptr = uintptr(p.GetArg(pos))
|
ptr = uintptr(p.GetArg(pos))
|
||||||
if ptr&1 == 1 { // cnode
|
if ptr&1 == 1 { // cnode
|
||||||
ptr &= ^uintptr(1)
|
ptr &= ^uintptr(1)
|
||||||
//cnode = (*Cnode_t)(unsafe.Pointer(ptr))
|
//cnode = (*Cnode_t)(unsafe.Pointer(ptr))
|
||||||
//cnode.child i hate this portion....
|
//cnode.child i hate this portion....
|
||||||
|
return nil, fmt.Errorf("not supported - unable to evaluate {} literally")
|
||||||
|
} else {
|
||||||
|
return (*string)(unsafe.Pointer(ptr)), nil
|
||||||
|
}*/
|
||||||
|
|
||||||
|
switch t := p.GetArg(pos).(type) {
|
||||||
|
case *string:
|
||||||
|
return t, nil
|
||||||
|
case *Cnode_t:
|
||||||
|
// TODO: can support this? by storing the original text?
|
||||||
return nil, fmt.Errorf("not supported - unable to evaluate {} literally")
|
return nil, fmt.Errorf("not supported - unable to evaluate {} literally")
|
||||||
} else {
|
default:
|
||||||
return (*string)(unsafe.Pointer(ptr)), nil
|
panic("internal error - argument type unrecognized")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (interp *Interp) EvalText(text []rune) (*string, error) {
|
func (interp *Interp) EvalText(text []rune) (Value_t, error) {
|
||||||
var (
|
var (
|
||||||
v *string
|
v Value_t
|
||||||
node *Cnode_t
|
node *Cnode_t
|
||||||
err error
|
err error
|
||||||
)
|
)
|
||||||
|
@ -3,7 +3,6 @@ package interp
|
|||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"runtime"
|
"runtime"
|
||||||
"unsafe"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type error_t struct {
|
type error_t struct {
|
||||||
@ -40,9 +39,11 @@ type context_t struct {
|
|||||||
container_node *Cnode_t
|
container_node *Cnode_t
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Value_t interface{}
|
||||||
|
|
||||||
type process_t struct {
|
type process_t struct {
|
||||||
interp *Interp
|
interp *Interp
|
||||||
vstack [16]unsafe.Pointer // value stack - TODO: change size
|
vstack [16]Value_t // value stack - TODO: change size
|
||||||
vsp int
|
vsp int
|
||||||
ctx *context_t
|
ctx *context_t
|
||||||
}
|
}
|
||||||
@ -227,11 +228,11 @@ func get_top_call_frame(f *CallFrame) *CallFrame {
|
|||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
||||||
func (interp *Interp) Execute(node_head *Cnode_t) (*string, error) {
|
func (interp *Interp) Execute(node_head *Cnode_t) (Value_t, error) {
|
||||||
|
|
||||||
var (
|
var (
|
||||||
node *Cnode_t
|
node *Cnode_t
|
||||||
v *string
|
v Value_t
|
||||||
err error
|
err error
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -9,7 +9,9 @@ func proc_expr(p *process_t) error {
|
|||||||
|
|
||||||
func proc_if(p *process_t) error {
|
func proc_if(p *process_t) error {
|
||||||
var (
|
var (
|
||||||
v *string
|
v Value_t
|
||||||
|
vv *string
|
||||||
|
ok bool
|
||||||
err error
|
err error
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -24,14 +26,18 @@ func proc_if(p *process_t) error {
|
|||||||
goto done
|
goto done
|
||||||
}
|
}
|
||||||
|
|
||||||
if *v != "" {
|
vv, ok = v.(*string)
|
||||||
|
if !ok {
|
||||||
|
panic("internal error - screwed conditional value")
|
||||||
|
}
|
||||||
|
if *vv != "" {
|
||||||
//v, err = p.interp.eval_atom_node((*Cnode_t)(p.GetArg(1)))
|
//v, err = p.interp.eval_atom_node((*Cnode_t)(p.GetArg(1)))
|
||||||
v, err = p.interp.eval_arg(p, 1)
|
v, err = p.interp.eval_arg(p, 1)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
goto done
|
goto done
|
||||||
}
|
}
|
||||||
|
|
||||||
p.Return(*v)
|
p.Return(v)
|
||||||
} else {
|
} else {
|
||||||
// TODO: if elseif else
|
// TODO: if elseif else
|
||||||
}
|
}
|
||||||
@ -44,7 +50,8 @@ func proc_puts(p *process_t) error {
|
|||||||
var (
|
var (
|
||||||
i int
|
i int
|
||||||
nargs int
|
nargs int
|
||||||
v *string
|
v Value_t
|
||||||
|
vv *string
|
||||||
err error
|
err error
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -59,11 +66,13 @@ func proc_puts(p *process_t) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
fmt.Printf("%s", *v)
|
|
||||||
|
vv, _ = v.(*string)
|
||||||
|
fmt.Printf("%s", *vv)
|
||||||
}
|
}
|
||||||
|
|
||||||
if nargs >= 1 {
|
if nargs >= 1 {
|
||||||
p.Return(*v)
|
p.Return(v)
|
||||||
} else {
|
} else {
|
||||||
p.Return("hello")
|
p.Return("hello")
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user