MCPcopy Create free account
hub / github.com/akyoto/q / compileLoop

Method compileLoop

src/core/compileLoop.go:12–172  ·  view source on GitHub ↗

compileLoop compiles an endless loop.

(node *ast.Loop)

Source from the content-addressed store, hash-verified

10
11// compileLoop compiles an endless loop.
12func (f *Function) compileLoop(node *ast.Loop) error {
13 f.Count.Loop++
14 headLabel := f.CreateLabel("loop.head", f.Count.Loop)
15 exitLabel := f.CreateLabel("loop.exit", f.Count.Loop)
16 beforeLoop := f.Block()
17 loopHead := ssa.NewBlock(headLabel)
18 loopExit := ssa.NewBlock(exitLabel)
19 loopBlockIndex := len(f.Blocks)
20
21 loop := &Loop{
22 Head: loopHead,
23 Exit: loopExit,
24 }
25
26 if node.Head != nil {
27 // Before the loop starts, we evaluate the lower limit
28 // and identify it as the loop counter.
29 name, from, to := f.parseLoopHeader(node.Head)
30
31 if from == nil {
32 return errors.New(InvalidLoopHeader, f.File, node.Head.Source())
33 }
34
35 loop.IteratorName = name
36 fromValue, err := f.evaluateRight(from)
37
38 if err != nil {
39 return err
40 }
41
42 if !types.Is(fromValue.Type(), types.AnyInt) {
43 return errors.New(&TypeMismatch{Encountered: fromValue.Type().Name(), Expected: types.AnyInt.Name()}, f.File, from.Source())
44 }
45
46 if f.Block().IsIdentified(fromValue) {
47 fromValue = f.copy(fromValue, from.Source())
48 }
49
50 beforeLoop.Identify(name, fromValue)
51 f.jump(loopHead)
52
53 // Loop starts, this is the jump target for new iterations.
54 // The upper limit is recalculated on every iteration.
55 // We check that the condition to jump to the loop body is true,
56 // otherwise we jump to the loop exit.
57 f.AddBlock(loopHead)
58 toValue, err := f.evaluateRight(to)
59
60 if err != nil {
61 return err
62 }
63
64 if !types.Is(toValue.Type(), fromValue.Type()) {
65 return errors.New(&TypeMismatch{Encountered: toValue.Type().Name(), Expected: fromValue.Type().Name()}, f.File, to.Source())
66 }
67
68 condition := f.Append(&ssa.BinaryOp{
69 Op: token.Less,

Callers 1

compileASTNodeMethod · 0.95

Calls 15

CreateLabelMethod · 0.95
parseLoopHeaderMethod · 0.95
evaluateRightMethod · 0.95
copyMethod · 0.95
jumpMethod · 0.95
AddSuccessorMethod · 0.95
compileASTMethod · 0.95
loopNextMethod · 0.95
NewBlockFunction · 0.92
NewFunction · 0.92
IsFunction · 0.92
BlockMethod · 0.80

Tested by

no test coverage detected