1
1
package compiler
2
2
3
3
import (
4
+ "fmt"
4
5
"github.com/llir/llvm/ir"
5
6
"github.com/llir/llvm/ir/constant"
6
7
llvmTypes "github.com/llir/llvm/ir/types"
@@ -11,7 +12,7 @@ import (
11
12
"github.com/zegl/tre/compiler/parser"
12
13
)
13
14
14
- func (c * Compiler ) compileDefineFuncNode (v * parser.DefineFuncNode ) {
15
+ func (c * Compiler ) compileDefineFuncNode (v * parser.DefineFuncNode ) value. Value {
15
16
var compiledName string
16
17
17
18
if v .IsMethod {
@@ -31,8 +32,10 @@ func (c *Compiler) compileDefineFuncNode(v *parser.DefineFuncNode) {
31
32
32
33
// Change the name of our function
33
34
compiledName = c .currentPackageName + "_method_" + v .MethodOnType .TypeName + "_" + v .Name
34
- } else {
35
+ } else if v . IsNamed {
35
36
compiledName = c .currentPackageName + "_" + v .Name
37
+ } else {
38
+ compiledName = c .currentPackageName + "_" + getAnonFuncName ()
36
39
}
37
40
38
41
llvmParams := make ([]* ir.Param , len (v .Arguments ))
@@ -127,12 +130,15 @@ func (c *Compiler) compileDefineFuncNode(v *parser.DefineFuncNode) {
127
130
128
131
// Make this method available in interfaces via a jump function
129
132
typesFunc .JumpFunction = c .compileInterfaceMethodJump (fn )
130
- } else {
133
+ } else if v . IsNamed {
131
134
c .currentPackage .Funcs [v .Name ] = typesFunc
132
135
}
133
136
134
137
entry := fn .NewBlock (getBlockName ())
135
138
139
+ prevContextFunc := c .contextFunc
140
+ prevContextBlock := c .contextBlock
141
+
136
142
c .contextFunc = typesFunc
137
143
c .contextBlock = entry
138
144
c .pushVariablesStack ()
@@ -196,7 +202,15 @@ func (c *Compiler) compileDefineFuncNode(v *parser.DefineFuncNode) {
196
202
c .contextBlock .NewRet (constant .NewInt (llvmTypes .I32 , 0 ))
197
203
}
198
204
205
+ c .contextFunc = prevContextFunc
206
+ c .contextBlock = prevContextBlock
207
+
199
208
c .popVariablesStack ()
209
+
210
+ return value.Value {
211
+ Type : typesFunc ,
212
+ Value : typesFunc .LlvmFunction ,
213
+ }
200
214
}
201
215
202
216
func (c * Compiler ) compileInterfaceMethodJump (targetFunc * ir.Function ) * ir.Function {
@@ -248,7 +262,7 @@ func (c *Compiler) compileReturnNode(v *parser.ReturnNode) {
248
262
// Set value and jump to return block
249
263
val := c .compileValue (v .Vals [0 ])
250
264
251
- // Type cast if neccesary
265
+ // Type cast if necessary
252
266
val = c .valueToInterfaceValue (val , c .contextFunc .LlvmReturnType )
253
267
254
268
if val .IsVariable {
@@ -264,7 +278,7 @@ func (c *Compiler) compileReturnNode(v *parser.ReturnNode) {
264
278
for i , val := range v .Vals {
265
279
compVal := c .compileValue (val )
266
280
267
- // Type cast if neccesary
281
+ // TODO: Type cast if necessary
268
282
// compVal = c.valueToInterfaceValue(compVal, c.contextFunc.ReturnType)
269
283
270
284
// Assign to ptr
@@ -300,7 +314,16 @@ func (c *Compiler) compileCallNode(v *parser.CallNode) value.Value {
300
314
var fn * types.Function
301
315
302
316
if isNameNode {
303
- fn = c .funcByName (name .Name )
317
+ if namedFn , ok := c .funcByName (name .Name ); ok {
318
+ fn = namedFn
319
+ } else {
320
+ funcByVal := c .compileValue (v .Function )
321
+ if checkIfFunc , ok := funcByVal .Type .(* types.Function ); ok {
322
+ fn = checkIfFunc
323
+ } else {
324
+ panic (fmt .Sprintf ("no such function: %v" , v ))
325
+ }
326
+ }
304
327
} else {
305
328
funcByVal := c .compileValue (v .Function )
306
329
if checkIfFunc , ok := funcByVal .Type .(* types.Function ); ok {
0 commit comments