Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 4 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,6 @@
dist/
example/ffi.go
example/ffi_go.flint
example/ffi_go.flint
*.exe
*.out
*.ll
3 changes: 2 additions & 1 deletion example/match.flint
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ pub fn print(string: String) Nil
fn test(i: Int) String {
match i {
| 1 -> "Hello"
| x if x == 2 -> "Bye"
| _ -> match i == 10 {
| True -> "true"
| False -> "false"
Expand All @@ -12,5 +13,5 @@ fn test(i: Int) String {
}

pub fn main() Nil {
print(test(3))
print(test(3) <> "\n")
}
28 changes: 14 additions & 14 deletions internal/codegen/codegen.go
Original file line number Diff line number Diff line change
Expand Up @@ -266,27 +266,27 @@ func (cg *CodeGen) emitMatchCond(b *ir.Block, scr value.Value, pat parser.Expr,
if p.Pos.Kind == lexer.Underscore {
baseCond = constant.True
} else {
// alloc := b.NewAlloca(scr.Type())
// b.NewStore(scr, alloc)
// cg.locals[p.Name] = alloc
alloc := b.NewAlloca(scr.Type())
b.NewStore(scr, alloc)
cg.locals[p.Name] = alloc
baseCond = constant.True
}
default:
panic("unsupported match pattern: " + pat.NodeType())
}
// disable guards for now

// if guard != nil {
// guardVal := cg.emitExpr(b, guard, false)
// if _, ok := guardVal.Type().(*types.IntType); ok {
// if guardVal.Type() != types.I1 {
// guardVal = b.NewTrunc(guardVal, types.I1)
// }
// } else {
// panic("guard expression is not a boolean")
// }
// baseCond = b.NewAnd(baseCond, guardVal)
// }
if guard != nil {
guardVal := cg.emitExpr(b, guard, false)
if _, ok := guardVal.Type().(*types.IntType); ok {
if guardVal.Type() != types.I1 {
guardVal = b.NewTrunc(guardVal, types.I1)
}
} else {
panic("guard expression is not a boolean")
}
baseCond = b.NewAnd(baseCond, guardVal)
}
return baseCond
}

Expand Down
6 changes: 1 addition & 5 deletions internal/codegen/expr.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ package codegen

import (
"flint/internal/parser"
"reflect"

"github.com/llir/llvm/ir"
"github.com/llir/llvm/ir/constant"
Expand Down Expand Up @@ -32,10 +31,7 @@ func (cg *CodeGen) emitExpr(b *ir.Block, e parser.Expr, isTail bool) value.Value
if ptr == nil {
panic("undefined variable: " + v.Name)
}
if reflect.TypeOf(ptr.Type()).String() == "*types.PointerType" {
return b.NewLoad(ptr.Type().(*types.PointerType).ElemType, ptr)
}
return b.NewLoad(ptr.Type(), ptr)
return b.NewLoad(ptr.Type().(*types.PointerType).ElemType, ptr)
case *parser.InfixExpr:
return cg.emitInfix(b, v)
case *parser.IfExpr:
Expand Down
2 changes: 1 addition & 1 deletion internal/codegen/infix.go
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ func (cg *CodeGen) emitInfix(b *ir.Block, e *parser.InfixExpr) value.Value {
case lexer.GreaterEqualDot:
return b.NewFCmp(enum.FPredOGE, l, r)
case lexer.LtGt:
return nil // Add string
return nil
case lexer.AmperAmper:
return b.NewAnd(l, r)
case lexer.VbarVbar:
Expand Down
49 changes: 17 additions & 32 deletions internal/codegen/match.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ package codegen
import (
"flint/internal/parser"
"fmt"
"reflect"

"github.com/llir/llvm/ir"
"github.com/llir/llvm/ir/constant"
Expand All @@ -26,15 +25,15 @@ func (cg *CodeGen) emitMatch(b *ir.Block, m *parser.MatchExpr, isTail bool) valu

checkList = append(checkList, b)

// wildCardName := fmt.Sprintf("match.%d.wild", matchId)
wildCardName := fmt.Sprintf("match.%d.wild", matchId)

for caseId, arm := range m.Arms {
var name string
// if arm.IsWildCardArm() {
// name = wildCardName
// } else {
name = fmt.Sprintf("match.%d.arm.%d", matchId, caseId)
// }
if arm.IsWildCardArm() {
name = wildCardName
} else {
name = fmt.Sprintf("match.%d.arm.%d", matchId, caseId)
}

armBlock := parent.NewBlock(name)
if caseId != 0 && !arm.IsWildCardArm() {
Expand Down Expand Up @@ -110,33 +109,19 @@ func (cg *CodeGen) emitMatch(b *ir.Block, m *parser.MatchExpr, isTail bool) valu
return nil
}

for _, v := range checkList {
if v != nil {
opLen := len(b.Term.Operands())
for i := range opLen {
op := *v.Term.Operands()[i]
if reflect.TypeOf(op) == reflect.TypeOf(mergeBlock) {
if op.(*ir.Block) == mergeBlock {
incomings = append(incomings, ir.NewIncoming(
constant.NewUndef(phiType),
v,
))
}
}
}
}
if referencesBlock(b, mergeBlock) {
incomings = append(incomings, ir.NewIncoming(
constant.NewUndef(phiType),
b,
))
}

opLen := len(b.Term.Operands())
for i := range opLen {
op := *b.Term.Operands()[i]
if reflect.TypeOf(op) == reflect.TypeOf(mergeBlock) {
if op.(*ir.Block) == mergeBlock {
incomings = append(incomings, ir.NewIncoming(
constant.NewUndef(phiType),
b,
))
}
for _, v := range checkList {
if referencesBlock(v, mergeBlock) {
incomings = append(incomings, ir.NewIncoming(
constant.NewUndef(phiType),
v,
))
}
}

Expand Down
14 changes: 14 additions & 0 deletions internal/codegen/reflect.go
Original file line number Diff line number Diff line change
Expand Up @@ -29,3 +29,17 @@ func parentBlockOfValue(v value.Value) *ir.Block {
}
return parent
}

func referencesBlock(b *ir.Block, blockToFind *ir.Block) bool {
if b != nil && b.Term != nil {
opLen := len(b.Term.Operands())
for i := range opLen {
op := *b.Term.Operands()[i]
v, ok := op.(*ir.Block)
if ok && v == blockToFind {
return true
}
}
}
return false
}