1/*
2 * gomacro - A Go interpreter with Lisp-like macros
3 *
4 * Copyright (C) 2017-2019 Massimiliano Ghilardi
5 *
6 *     This Source Code Form is subject to the terms of the Mozilla Public
7 *     License, v. 2.0. If a copy of the MPL was not distributed with this
8 *     file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 *
10 *
11 * func0ret1.go
12 *
13 *  Created on Apr 16, 2017
14 *      Author Massimiliano Ghilardi
15 */
16
17package fast
18
19import (
20	r "reflect"
21	. "github.com/cosmos72/gomacro/base"
22	xr "github.com/cosmos72/gomacro/xreflect"
23)
24
25:import (
26	r "reflect"
27	"go/ast"
28)
29
30
31// ----------------- func() t0 ---------------------
32
33:macro mfunc0ret1(ret0typ ast.Node) ast.Node {
34	if EvalType(ret0typ) == nil {
35		// not a well-known type
36		return ~"{
37			return c.funcGeneric(t, m)
38		}
39	}
40	return ~"{
41		if funcbody == nil {
42			return func(env *Env) r.Value {
43				return r.ValueOf(func() (ret0 ~,ret0typ) {
44					return
45				})
46			}
47		}
48		resultfun := m.resultfun[0].(func (*Env) ~,ret0typ)
49		return func(env *Env) r.Value {
50			// function is closed over the env used to DECLARE it
51			env.MarkUsedByClosure()
52			return r.ValueOf(func() (ret0 ~,ret0typ) {
53				env := newEnv4Func(env, nbind, nintbind, debugC)
54
55				// execute the body
56				funcbody(env)
57
58				// extract result
59				ret0 = resultfun(env)
60				env.freeEnv4Func()
61				return
62			})
63		}
64	}
65}
66
67func (c *Comp) func0ret1(t xr.Type, m *funcMaker) func(*Env) r.Value {
68	// do NOT keep a reference to funcMaker
69	nbind := m.nbind
70	nintbind := m.nintbind
71	funcbody := m.funcbody
72
73	var debugC *Comp
74	if c.Globals.Options&OptDebugger != 0 {
75		// keep a reference to c only if needed
76		debugC = c
77	}
78	tret0 := t.Out(0)
79	kret0 := tret0.Kind()
80	switch kret0 {
81	case r.Bool:      {mfunc0ret1; bool}
82	case r.Int:       {mfunc0ret1; int}
83	case r.Int8:      {mfunc0ret1; int8}
84	case r.Int16:     {mfunc0ret1; int16}
85	case r.Int32:     {mfunc0ret1; int32}
86	case r.Int64:     {mfunc0ret1; int64}
87	case r.Uint:      {mfunc0ret1; uint}
88	case r.Uint8:     {mfunc0ret1; uint8}
89	case r.Uint16:    {mfunc0ret1; uint16}
90	case r.Uint32:    {mfunc0ret1; uint32}
91	case r.Uint64:    {mfunc0ret1; uint64}
92	case r.Uintptr:   {mfunc0ret1; uintptr}
93	case r.Float32:   {mfunc0ret1; float32}
94	case r.Float64:   {mfunc0ret1; float64}
95	case r.Complex64: {mfunc0ret1; complex64}
96	case r.Complex128:{mfunc0ret1; complex128}
97	case r.String:    {mfunc0ret1; string}
98	default:          return nil
99	}
100}
101
102