diff options
Diffstat (limited to 'compiler/transf.nim')
-rw-r--r-- | compiler/transf.nim | 62 |
1 files changed, 32 insertions, 30 deletions
diff --git a/compiler/transf.nim b/compiler/transf.nim index 5922ca595..42a78c8e3 100644 --- a/compiler/transf.nim +++ b/compiler/transf.nim @@ -24,7 +24,7 @@ import lowerings, liftlocals, modulegraphs, lineinfos -proc transformBody*(g: ModuleGraph, prc: PSym, cache: bool): PNode +proc transformBody*(g: ModuleGraph; idgen: IdGenerator, prc: PSym, cache: bool): PNode import closureiters, lambdalifting @@ -40,7 +40,7 @@ type # if we encounter the 2nd yield statement next: PTransCon # for stacking - TTransfContext = object of TPassContext + TTransfContext = object module: PSym transCon: PTransCon # top of a TransCon stack inlining: int # > 0 if we are in inlining context (copy vars) @@ -48,6 +48,7 @@ type contSyms, breakSyms: seq[PSym] # to transform 'continue' and 'break' deferDetected, tooEarly: bool graph: ModuleGraph + idgen: IdGenerator PTransf = ref TTransfContext proc newTransNode(a: PNode): PNode {.inline.} = @@ -86,12 +87,12 @@ proc getCurrOwner(c: PTransf): PSym = else: result = c.module proc newTemp(c: PTransf, typ: PType, info: TLineInfo): PNode = - let r = newSym(skTemp, getIdent(c.graph.cache, genPrefix), getCurrOwner(c), info) + let r = newSym(skTemp, getIdent(c.graph.cache, genPrefix), nextId(c.idgen), getCurrOwner(c), info) r.typ = typ #skipTypes(typ, {tyGenericInst, tyAlias, tySink}) incl(r.flags, sfFromGeneric) let owner = getCurrOwner(c) if owner.isIterator and not c.tooEarly: - result = freshVarForClosureIter(c.graph, r, owner) + result = freshVarForClosureIter(c.graph, r, c.idgen, owner) else: result = newSymNode(r) @@ -111,13 +112,13 @@ proc transformSymAux(c: PTransf, n: PNode): PNode = let s = n.sym if s.typ != nil and s.typ.callConv == ccClosure: if s.kind in routineKinds: - discard transformBody(c.graph, s, true) + discard transformBody(c.graph, c.idgen, s, true) if s.kind == skIterator: if c.tooEarly: return n - else: return liftIterSym(c.graph, n, getCurrOwner(c)) + else: return liftIterSym(c.graph, n, c.idgen, getCurrOwner(c)) elif s.kind in {skProc, skFunc, skConverter, skMethod} and not c.tooEarly: # top level .closure procs are still somewhat supported for 'Nake': - return makeClosure(c.graph, s, nil, n.info) + return makeClosure(c.graph, c.idgen, s, nil, n.info) #elif n.sym.kind in {skVar, skLet} and n.sym.typ.callConv == ccClosure: # echo n.info, " come heer for ", c.tooEarly # if not c.tooEarly: @@ -160,9 +161,9 @@ proc transformSym(c: PTransf, n: PNode): PNode = proc freshVar(c: PTransf; v: PSym): PNode = let owner = getCurrOwner(c) if owner.isIterator and not c.tooEarly: - result = freshVarForClosureIter(c.graph, v, owner) + result = freshVarForClosureIter(c.graph, v, c.idgen, owner) else: - var newVar = copySym(v) + var newVar = copySym(v, nextId(c.idgen)) incl(newVar.flags, sfFromGeneric) newVar.owner = owner result = newSymNode(newVar) @@ -232,7 +233,7 @@ proc hasContinue(n: PNode): bool = if hasContinue(n[i]): return true proc newLabel(c: PTransf, n: PNode): PSym = - result = newSym(skLabel, nil, getCurrOwner(c), n.info) + result = newSym(skLabel, nil, nextId(c.idgen), getCurrOwner(c), n.info) result.name = getIdent(c.graph.cache, genPrefix) proc transformBlock(c: PTransf, n: PNode): PNode = @@ -423,7 +424,7 @@ proc transformAddrDeref(c: PTransf, n: PNode, a, b: TNodeKind): PNode = if n.typ.skipTypes(abstractVar).kind != tyOpenArray: result.typ = n.typ elif n.typ.skipTypes(abstractInst).kind in {tyVar}: - result.typ = toVar(result.typ, n.typ.skipTypes(abstractInst).kind) + result.typ = toVar(result.typ, n.typ.skipTypes(abstractInst).kind, c.idgen) of nkHiddenStdConv, nkHiddenSubConv, nkConv: var m = n[0][1] if m.kind == a or m.kind == b: @@ -433,7 +434,7 @@ proc transformAddrDeref(c: PTransf, n: PNode, a, b: TNodeKind): PNode = if n.typ.skipTypes(abstractVar).kind != tyOpenArray: result.typ = n.typ elif n.typ.skipTypes(abstractInst).kind in {tyVar}: - result.typ = toVar(result.typ, n.typ.skipTypes(abstractInst).kind) + result.typ = toVar(result.typ, n.typ.skipTypes(abstractInst).kind, c.idgen) else: if n[0].kind == a or n[0].kind == b: # addr ( deref ( x )) --> x @@ -495,7 +496,7 @@ proc transformConv(c: PTransf, n: PNode): PNode = of tyOpenArray, tyVarargs: result = transform(c, n[1]) #result = transformSons(c, n) - result.typ = takeType(n.typ, n[1].typ) + result.typ = takeType(n.typ, n[1].typ, c.idgen) #echo n.info, " came here and produced ", typeToString(result.typ), # " from ", typeToString(n.typ), " and ", typeToString(n[1].typ) of tyCString: @@ -629,7 +630,7 @@ proc transformFor(c: PTransf, n: PNode): PNode = result[1] = n result[1][^1] = transformLoopBody(c, n[^1]) result[1][^2] = transform(c, n[^2]) - result[1] = lambdalifting.liftForLoop(c.graph, result[1], getCurrOwner(c)) + result[1] = lambdalifting.liftForLoop(c.graph, result[1], c.idgen, getCurrOwner(c)) discard c.breakSyms.pop return result @@ -698,7 +699,7 @@ proc transformFor(c: PTransf, n: PNode): PNode = stmtList.add(newAsgnStmt(c, nkFastAsgn, temp, arg)) idNodeTablePut(newC.mapping, formal, temp) - let body = transformBody(c.graph, iter, true) + let body = transformBody(c.graph, c.idgen, iter, true) pushInfoContext(c.graph.config, n.info) inc(c.inlining) stmtList.add(transform(c, body)) @@ -830,7 +831,7 @@ proc transformExceptBranch(c: PTransf, n: PNode): PNode = let convNode = newTransNode(nkHiddenSubConv, n[1].info, 2) convNode[0] = newNodeI(nkEmpty, n.info) convNode[1] = excCall - convNode.typ = excTypeNode.typ.toRef() + convNode.typ = excTypeNode.typ.toRef(c.idgen) # -> let exc = ... let identDefs = newTransNode(nkIdentDefs, n[1].info, 3) identDefs[0] = n[0][2] @@ -850,10 +851,10 @@ proc transformExceptBranch(c: PTransf, n: PNode): PNode = else: result = transformSons(c, n) -proc commonOptimizations*(g: ModuleGraph; c: PSym, n: PNode): PNode = +proc commonOptimizations*(g: ModuleGraph; idgen: IdGenerator; c: PSym, n: PNode): PNode = result = n for i in 0..<n.safeLen: - result[i] = commonOptimizations(g, c, n[i]) + result[i] = commonOptimizations(g, idgen, c, n[i]) var op = getMergeOp(n) if (op != nil) and (op.magic != mNone) and (n.len >= 3): result = newNodeIT(nkCall, n.info, n.typ) @@ -873,7 +874,7 @@ proc commonOptimizations*(g: ModuleGraph; c: PSym, n: PNode): PNode = result.add(a) if result.len == 2: result = result[1] else: - var cnst = getConstExpr(c, n, g) + var cnst = getConstExpr(c, n, idgen, g) # we inline constants if they are not complex constants: if cnst != nil and not dontInlineConstant(n, cnst): result = cnst @@ -1012,7 +1013,7 @@ proc transform(c: PTransf, n: PNode): PNode = n.typ != nil and n.typ.kind == tyPointer if not exprIsPointerCast: - var cnst = getConstExpr(c.module, result, c.graph) + var cnst = getConstExpr(c.module, result, c.idgen, c.graph) # we inline constants if they are not complex constants: if cnst != nil and not dontInlineConstant(n, cnst): result = cnst # do not miss an optimization @@ -1027,12 +1028,13 @@ proc processTransf(c: PTransf, n: PNode, owner: PSym): PNode = popTransCon(c) incl(result.flags, nfTransf) -proc openTransf(g: ModuleGraph; module: PSym, filename: string): PTransf = +proc openTransf(g: ModuleGraph; module: PSym, filename: string; idgen: IdGenerator): PTransf = new(result) result.contSyms = @[] result.breakSyms = @[] result.module = module result.graph = g + result.idgen = idgen proc flattenStmts(n: PNode) = var goOn = true @@ -1075,7 +1077,7 @@ template liftDefer(c, root) = if c.deferDetected: liftDeferAux(root) -proc transformBody*(g: ModuleGraph, prc: PSym, cache: bool): PNode = +proc transformBody*(g: ModuleGraph; idgen: IdGenerator; prc: PSym; cache: bool): PNode = assert prc.kind in routineKinds if prc.transformedBody != nil: @@ -1084,14 +1086,14 @@ proc transformBody*(g: ModuleGraph, prc: PSym, cache: bool): PNode = result = prc.ast[bodyPos] else: prc.transformedBody = newNode(nkEmpty) # protects from recursion - var c = openTransf(g, prc.getModule, "") - result = liftLambdas(g, prc, prc.ast[bodyPos], c.tooEarly) + var c = openTransf(g, prc.getModule, "", idgen) + result = liftLambdas(g, prc, prc.ast[bodyPos], c.tooEarly, c.idgen) result = processTransf(c, result, prc) liftDefer(c, result) - result = liftLocalsIfRequested(prc, result, g.cache, g.config) + result = liftLocalsIfRequested(prc, result, g.cache, g.config, c.idgen) if prc.isIterator: - result = g.transformClosureIterator(prc, result) + result = g.transformClosureIterator(c.idgen, prc, result) incl(result.flags, nfTransf) @@ -1105,21 +1107,21 @@ proc transformBody*(g: ModuleGraph, prc: PSym, cache: bool): PNode = #if prc.name.s == "main": # echo "transformed into ", renderTree(result, {renderIds}) -proc transformStmt*(g: ModuleGraph; module: PSym, n: PNode): PNode = +proc transformStmt*(g: ModuleGraph; idgen: IdGenerator; module: PSym, n: PNode): PNode = if nfTransf in n.flags: result = n else: - var c = openTransf(g, module, "") + var c = openTransf(g, module, "", idgen) result = processTransf(c, n, module) liftDefer(c, result) #result = liftLambdasForTopLevel(module, result) incl(result.flags, nfTransf) -proc transformExpr*(g: ModuleGraph; module: PSym, n: PNode): PNode = +proc transformExpr*(g: ModuleGraph; idgen: IdGenerator; module: PSym, n: PNode): PNode = if nfTransf in n.flags: result = n else: - var c = openTransf(g, module, "") + var c = openTransf(g, module, "", idgen) result = processTransf(c, n, module) liftDefer(c, result) # expressions are not to be injected with destructor calls as that |