new VM: improvements
This commit is contained in:
parent
29357ab556
commit
6db20a4be8
7 changed files with 114 additions and 57 deletions
|
|
@ -300,11 +300,11 @@ proc semOf(c: PContext, n: PNode): PNode =
|
||||||
result = n
|
result = n
|
||||||
|
|
||||||
proc isOpImpl(c: PContext, n: PNode): PNode =
|
proc isOpImpl(c: PContext, n: PNode): PNode =
|
||||||
InternalAssert n.sonsLen == 3 and
|
internalAssert n.sonsLen == 3 and
|
||||||
n[1].kind == nkSym and n[1].sym.kind == skType and
|
n[1].typ != nil and
|
||||||
n[2].kind in {nkStrLit..nkTripleStrLit, nkType}
|
n[2].kind in {nkStrLit..nkTripleStrLit, nkType}
|
||||||
|
|
||||||
let t1 = n[1].sym.typ.skipTypes({tyTypeDesc})
|
let t1 = n[1].typ.skipTypes({tyTypeDesc})
|
||||||
|
|
||||||
if n[2].kind in {nkStrLit..nkTripleStrLit}:
|
if n[2].kind in {nkStrLit..nkTripleStrLit}:
|
||||||
case n[2].strVal.normalize
|
case n[2].strVal.normalize
|
||||||
|
|
|
||||||
|
|
@ -33,10 +33,8 @@ proc semInstantiationInfo(c: PContext, n: PNode): PNode =
|
||||||
result.add(line)
|
result.add(line)
|
||||||
|
|
||||||
|
|
||||||
proc evalTypeTrait(trait, operand: PNode, context: PSym): PNode =
|
proc evalTypeTrait(trait: PNode, operand: PType, context: PSym): PNode =
|
||||||
InternalAssert operand.kind == nkSym
|
let typ = operand.skipTypes({tyTypeDesc})
|
||||||
|
|
||||||
let typ = operand.sym.typ.skipTypes({tyTypeDesc})
|
|
||||||
case trait.sym.name.s.normalize
|
case trait.sym.name.s.normalize
|
||||||
of "name":
|
of "name":
|
||||||
result = newStrNode(nkStrLit, typ.typeToString(preferName))
|
result = newStrNode(nkStrLit, typ.typeToString(preferName))
|
||||||
|
|
@ -51,13 +49,10 @@ proc evalTypeTrait(trait, operand: PNode, context: PSym): PNode =
|
||||||
|
|
||||||
proc semTypeTraits(c: PContext, n: PNode): PNode =
|
proc semTypeTraits(c: PContext, n: PNode): PNode =
|
||||||
checkMinSonsLen(n, 2)
|
checkMinSonsLen(n, 2)
|
||||||
internalAssert n.sons[1].kind == nkSym
|
let t = n.sons[1].typ
|
||||||
let typArg = n.sons[1].sym
|
internalAssert t != nil
|
||||||
if typArg.kind == skType or
|
if not containsGenericType(t):
|
||||||
(typArg.kind == skParam and typArg.typ.sonsLen > 0):
|
result = evalTypeTrait(n[0], t, GetCurrOwner())
|
||||||
# This is either a type known to sem or a typedesc
|
|
||||||
# param to a regular proc (again, known at instantiation)
|
|
||||||
result = evalTypeTrait(n[0], n[1], GetCurrOwner())
|
|
||||||
else:
|
else:
|
||||||
# a typedesc variable, pass unmodified to evals
|
# a typedesc variable, pass unmodified to evals
|
||||||
result = n
|
result = n
|
||||||
|
|
|
||||||
|
|
@ -52,9 +52,9 @@ proc stackTraceAux(c: PCtx; x: PStackFrame; pc: int) =
|
||||||
|
|
||||||
proc stackTrace(c: PCtx, tos: PStackFrame, pc: int,
|
proc stackTrace(c: PCtx, tos: PStackFrame, pc: int,
|
||||||
msg: TMsgKind, arg = "") =
|
msg: TMsgKind, arg = "") =
|
||||||
MsgWriteln("stack trace: (most recent call last)")
|
msgWriteln("stack trace: (most recent call last)")
|
||||||
stackTraceAux(c, tos, pc)
|
stackTraceAux(c, tos, pc)
|
||||||
LocalError(c.debug[pc], msg, arg)
|
localError(c.debug[pc], msg, arg)
|
||||||
|
|
||||||
proc bailOut(c: PCtx; tos: PStackFrame) =
|
proc bailOut(c: PCtx; tos: PStackFrame) =
|
||||||
stackTrace(c, tos, c.exceptionInstr, errUnhandledExceptionX,
|
stackTrace(c, tos, c.exceptionInstr, errUnhandledExceptionX,
|
||||||
|
|
@ -63,9 +63,6 @@ proc bailOut(c: PCtx; tos: PStackFrame) =
|
||||||
when not defined(nimComputedGoto):
|
when not defined(nimComputedGoto):
|
||||||
{.pragma: computedGoto.}
|
{.pragma: computedGoto.}
|
||||||
|
|
||||||
template inc(pc: ptr TInstr, diff = 1) =
|
|
||||||
inc cast[TAddress](pc), TInstr.sizeof * diff
|
|
||||||
|
|
||||||
proc myreset(n: PNode) =
|
proc myreset(n: PNode) =
|
||||||
when defined(system.reset):
|
when defined(system.reset):
|
||||||
var oldInfo = n.info
|
var oldInfo = n.info
|
||||||
|
|
@ -299,6 +296,7 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
let instr = c.code[pc]
|
let instr = c.code[pc]
|
||||||
let ra = instr.regA
|
let ra = instr.regA
|
||||||
#echo "PC ", pc, " ", c.code[pc].opcode, " ra ", ra
|
#echo "PC ", pc, " ", c.code[pc].opcode, " ra ", ra
|
||||||
|
#message(c.debug[pc], warnUser, "gah")
|
||||||
case instr.opcode
|
case instr.opcode
|
||||||
of opcEof: return regs[ra]
|
of opcEof: return regs[ra]
|
||||||
of opcRet:
|
of opcRet:
|
||||||
|
|
@ -338,25 +336,38 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
# a = b[c]
|
# a = b[c]
|
||||||
let rb = instr.regB
|
let rb = instr.regB
|
||||||
let rc = instr.regC
|
let rc = instr.regC
|
||||||
let idx = regs[rc].intVal
|
let idx = regs[rc].intVal.int
|
||||||
# XXX what if the array is not 0-based? -> codegen should insert a sub
|
# XXX what if the array is not 0-based? -> codegen should insert a sub
|
||||||
assert regs[rb].kind != nkMetaNode
|
assert regs[rb].kind != nkMetaNode
|
||||||
asgnComplex(regs[ra], regs[rb].sons[idx.int])
|
let src = regs[rb]
|
||||||
|
if src.kind notin {nkEmpty..nkNilLit} and idx <% src.len:
|
||||||
|
asgnComplex(regs[ra], src.sons[idx])
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcLdStrIdx:
|
of opcLdStrIdx:
|
||||||
decodeBC(nkIntLit)
|
decodeBC(nkIntLit)
|
||||||
let idx = regs[rc].intVal
|
let idx = regs[rc].intVal.int
|
||||||
regs[ra].intVal = regs[rb].strVal[idx.int].ord
|
if idx <=% regs[rb].strVal.len:
|
||||||
|
regs[ra].intVal = regs[rb].strVal[idx].ord
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcWrArr:
|
of opcWrArr:
|
||||||
# a[b] = c
|
# a[b] = c
|
||||||
let rb = instr.regB
|
let rb = instr.regB
|
||||||
let rc = instr.regC
|
let rc = instr.regC
|
||||||
let idx = regs[rb].intVal
|
let idx = regs[rb].intVal.int
|
||||||
asgnComplex(regs[ra].sons[idx.int], regs[rc])
|
if idx <% regs[ra].len:
|
||||||
|
asgnComplex(regs[ra].sons[idx], regs[rc])
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcWrArrRef:
|
of opcWrArrRef:
|
||||||
let rb = instr.regB
|
let rb = instr.regB
|
||||||
let rc = instr.regC
|
let rc = instr.regC
|
||||||
let idx = regs[rb].intVal
|
let idx = regs[rb].intVal.int
|
||||||
asgnRef(regs[ra].sons[idx.int], regs[rc])
|
if idx <% regs[ra].len:
|
||||||
|
asgnRef(regs[ra].sons[idx], regs[rc])
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcLdObj:
|
of opcLdObj:
|
||||||
# a = b.c
|
# a = b.c
|
||||||
let rb = instr.regB
|
let rb = instr.regB
|
||||||
|
|
@ -381,7 +392,10 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
of opcWrStrIdx:
|
of opcWrStrIdx:
|
||||||
decodeBC(nkStrLit)
|
decodeBC(nkStrLit)
|
||||||
let idx = regs[rb].intVal.int
|
let idx = regs[rb].intVal.int
|
||||||
regs[ra].strVal[idx] = chr(regs[rc].intVal)
|
if idx <% regs[ra].strVal.len:
|
||||||
|
regs[ra].strVal[idx] = chr(regs[rc].intVal)
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcAddr:
|
of opcAddr:
|
||||||
decodeB(nkRefTy)
|
decodeB(nkRefTy)
|
||||||
if regs[ra].len == 0: regs[ra].add regs[rb]
|
if regs[ra].len == 0: regs[ra].add regs[rb]
|
||||||
|
|
@ -631,7 +645,7 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
#echo "new pc ", newPc, " calling: ", prc.name.s
|
#echo "new pc ", newPc, " calling: ", prc.name.s
|
||||||
var newFrame = PStackFrame(prc: prc, comesFrom: pc, next: tos)
|
var newFrame = PStackFrame(prc: prc, comesFrom: pc, next: tos)
|
||||||
newSeq(newFrame.slots, prc.offset)
|
newSeq(newFrame.slots, prc.offset)
|
||||||
if not isEmptyType(prc.typ.sons[0]):
|
if not isEmptyType(prc.typ.sons[0]) or prc.kind == skMacro:
|
||||||
newFrame.slots[0] = getNullValue(prc.typ.sons[0], prc.info)
|
newFrame.slots[0] = getNullValue(prc.typ.sons[0], prc.info)
|
||||||
# pass every parameter by var (the language definition allows this):
|
# pass every parameter by var (the language definition allows this):
|
||||||
for i in 1 .. rc-1:
|
for i in 1 .. rc-1:
|
||||||
|
|
@ -769,7 +783,15 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
regs[ra].strVal.setLen(regs[rb].getOrdValue.int)
|
regs[ra].strVal.setLen(regs[rb].getOrdValue.int)
|
||||||
of opcOf:
|
of opcOf:
|
||||||
decodeBC(nkIntLit)
|
decodeBC(nkIntLit)
|
||||||
regs[ra].intVal = ord(inheritanceDiff(regs[rb].typ, regs[rc].typ) >= 0)
|
let typ = c.types[regs[rc].intVal.int]
|
||||||
|
regs[ra].intVal = ord(inheritanceDiff(regs[rb].typ, typ) >= 0)
|
||||||
|
of opcIs:
|
||||||
|
decodeBC(nkIntLit)
|
||||||
|
let t1 = regs[rb].typ.skipTypes({tyTypeDesc})
|
||||||
|
let t2 = c.types[regs[rc].intVal.int]
|
||||||
|
let match = if t2.kind == tyTypeClass: matchTypeClass(t2, t1)
|
||||||
|
else: sameType(t1, t2)
|
||||||
|
regs[ra].intVal = ord(match)
|
||||||
of opcSetLenSeq:
|
of opcSetLenSeq:
|
||||||
decodeB(nkBracket)
|
decodeB(nkBracket)
|
||||||
let newLen = regs[rb].getOrdValue.int
|
let newLen = regs[rb].getOrdValue.int
|
||||||
|
|
@ -787,10 +809,20 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
decodeBC(nkMetaNode)
|
decodeBC(nkMetaNode)
|
||||||
if regs[rb].kind != nkMetaNode:
|
if regs[rb].kind != nkMetaNode:
|
||||||
internalError(c.debug[pc], "no MetaNode")
|
internalError(c.debug[pc], "no MetaNode")
|
||||||
setMeta(regs[ra], regs[rb].uast.sons[regs[rc].intVal.int])
|
let idx = regs[rc].intVal.int
|
||||||
|
let src = regs[rb].uast
|
||||||
|
if src.kind notin {nkEmpty..nkNilLit} and idx <% src.len:
|
||||||
|
setMeta(regs[ra], src.sons[idx])
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcNSetChild:
|
of opcNSetChild:
|
||||||
decodeBC(nkMetaNode)
|
decodeBC(nkMetaNode)
|
||||||
regs[ra].uast.sons[regs[rb].intVal.int] = regs[rc].uast
|
let idx = regs[rb].intVal.int
|
||||||
|
var dest = regs[ra].uast
|
||||||
|
if dest.kind notin {nkEmpty..nkNilLit} and idx <% dest.len:
|
||||||
|
dest.sons[idx] = regs[rc].uast
|
||||||
|
else:
|
||||||
|
stackTrace(c, tos, pc, errIndexOutOfBounds)
|
||||||
of opcNAdd:
|
of opcNAdd:
|
||||||
decodeBC(nkMetaNode)
|
decodeBC(nkMetaNode)
|
||||||
var u = regs[rb].uast
|
var u = regs[rb].uast
|
||||||
|
|
@ -986,6 +1018,15 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): PNode =
|
||||||
decodeB(nkStrLit)
|
decodeB(nkStrLit)
|
||||||
let typ = regs[rb].sym.typ.skipTypes({tyTypeDesc})
|
let typ = regs[rb].sym.typ.skipTypes({tyTypeDesc})
|
||||||
regs[ra].strVal = typ.typeToString(preferExported)
|
regs[ra].strVal = typ.typeToString(preferExported)
|
||||||
|
of opcGlobalOnce:
|
||||||
|
let rb = instr.regBx
|
||||||
|
if c.globals.sons[rb - wordExcess - 1].kind != nkEmpty:
|
||||||
|
# skip initialization instructions:
|
||||||
|
while true:
|
||||||
|
inc pc
|
||||||
|
if c.code[pc].opcode in {opcWrGlobal, opcWrGlobalRef} and
|
||||||
|
c.code[pc].regBx == rb:
|
||||||
|
break
|
||||||
inc pc
|
inc pc
|
||||||
|
|
||||||
proc fixType(result, n: PNode) {.inline.} =
|
proc fixType(result, n: PNode) {.inline.} =
|
||||||
|
|
@ -1073,6 +1114,7 @@ proc setupMacroParam(x: PNode): PNode =
|
||||||
y.flags.incl nfIsRef
|
y.flags.incl nfIsRef
|
||||||
result = newNode(nkMetaNode)
|
result = newNode(nkMetaNode)
|
||||||
result.add y
|
result.add y
|
||||||
|
result.typ = x.typ
|
||||||
|
|
||||||
var evalMacroCounter: int
|
var evalMacroCounter: int
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -60,7 +60,7 @@ type
|
||||||
opcEqStr, opcLeStr, opcLtStr, opcEqSet, opcLeSet, opcLtSet,
|
opcEqStr, opcLeStr, opcLtStr, opcEqSet, opcLeSet, opcLtSet,
|
||||||
opcMulSet, opcPlusSet, opcMinusSet, opcSymdiffSet, opcConcatStr,
|
opcMulSet, opcPlusSet, opcMinusSet, opcSymdiffSet, opcConcatStr,
|
||||||
opcContainsSet, opcRepr, opcSetLenStr, opcSetLenSeq,
|
opcContainsSet, opcRepr, opcSetLenStr, opcSetLenSeq,
|
||||||
opcSwap, opcIsNil, opcOf,
|
opcSwap, opcIsNil, opcOf, opcIs,
|
||||||
opcSubStr, opcConv, opcCast, opcQuit, opcReset,
|
opcSubStr, opcConv, opcCast, opcQuit, opcReset,
|
||||||
|
|
||||||
opcAddStrCh,
|
opcAddStrCh,
|
||||||
|
|
@ -122,6 +122,7 @@ type
|
||||||
opcLdImmInt, # dest = immediate value
|
opcLdImmInt, # dest = immediate value
|
||||||
opcWrGlobal,
|
opcWrGlobal,
|
||||||
opcWrGlobalRef,
|
opcWrGlobalRef,
|
||||||
|
opcGlobalOnce, # used to introduce an assignment to a global once
|
||||||
opcSetType, # dest.typ = types[Bx]
|
opcSetType, # dest.typ = types[Bx]
|
||||||
opcTypeTrait
|
opcTypeTrait
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -301,7 +301,8 @@ proc sameConstant*(a, b: PNode): bool =
|
||||||
of nkCharLit..nkInt64Lit: result = a.intVal == b.intVal
|
of nkCharLit..nkInt64Lit: result = a.intVal == b.intVal
|
||||||
of nkFloatLit..nkFloat64Lit: result = a.floatVal == b.floatVal
|
of nkFloatLit..nkFloat64Lit: result = a.floatVal == b.floatVal
|
||||||
of nkStrLit..nkTripleStrLit: result = a.strVal == b.strVal
|
of nkStrLit..nkTripleStrLit: result = a.strVal == b.strVal
|
||||||
of nkEmpty, nkNilLit, nkType: result = true
|
of nkType: result = a.typ == b.typ
|
||||||
|
of nkEmpty, nkNilLit: result = true
|
||||||
else:
|
else:
|
||||||
if sonsLen(a) == sonsLen(b):
|
if sonsLen(a) == sonsLen(b):
|
||||||
for i in countup(0, sonsLen(a) - 1):
|
for i in countup(0, sonsLen(a) - 1):
|
||||||
|
|
@ -674,12 +675,16 @@ proc genMagic(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
unused(n, dest)
|
unused(n, dest)
|
||||||
var d = c.genx(n.sons[1])
|
var d = c.genx(n.sons[1])
|
||||||
c.gABC(n, opcReset, d)
|
c.gABC(n, opcReset, d)
|
||||||
of mOf:
|
of mOf, mIs:
|
||||||
if dest < 0: dest = c.getTemp(n.typ)
|
if dest < 0: dest = c.getTemp(n.typ)
|
||||||
var tmp = c.genx(n.sons[1])
|
var tmp = c.genx(n.sons[1])
|
||||||
c.gABC(n, opcOf, dest, tmp)
|
var idx = c.getTemp(getSysType(tyInt))
|
||||||
c.gABx(n, opcOf, 0, c.genType(n.sons[2].typ.skipTypes(abstractPtrs)))
|
var typ = n.sons[2].typ
|
||||||
|
if m == mOf: typ = typ.skipTypes(abstractPtrs)
|
||||||
|
c.gABx(n, opcLdImmInt, idx, c.genType(typ))
|
||||||
|
c.gABC(n, if m == mOf: opcOf else: opcIs, dest, tmp, idx)
|
||||||
c.freeTemp(tmp)
|
c.freeTemp(tmp)
|
||||||
|
c.freeTemp(idx)
|
||||||
of mSizeOf:
|
of mSizeOf:
|
||||||
GlobalError(n.info, errCannotInterpretNodeX, renderTree(n))
|
GlobalError(n.info, errCannotInterpretNodeX, renderTree(n))
|
||||||
of mHigh:
|
of mHigh:
|
||||||
|
|
@ -717,8 +722,6 @@ proc genMagic(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
c.gABx(n, opcSetType, tmp, c.genType(n.sons[1].typ))
|
c.gABx(n, opcSetType, tmp, c.genType(n.sons[1].typ))
|
||||||
c.gABC(n, opcTypeTrait, dest, tmp)
|
c.gABC(n, opcTypeTrait, dest, tmp)
|
||||||
c.freeTemp(tmp)
|
c.freeTemp(tmp)
|
||||||
of mIs:
|
|
||||||
InternalError(n.info, "cannot generate code for: " & $m)
|
|
||||||
of mSlurp: genUnaryABC(c, n, dest, opcSlurp)
|
of mSlurp: genUnaryABC(c, n, dest, opcSlurp)
|
||||||
of mStaticExec: genBinaryABC(c, n, dest, opcGorge)
|
of mStaticExec: genBinaryABC(c, n, dest, opcGorge)
|
||||||
of mNLen: genUnaryABI(c, n, dest, opcLenSeq)
|
of mNLen: genUnaryABI(c, n, dest, opcLenSeq)
|
||||||
|
|
@ -905,6 +908,11 @@ proc genLit(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
let lit = genLiteral(c, n)
|
let lit = genLiteral(c, n)
|
||||||
c.gABx(n, opc, dest, lit)
|
c.gABx(n, opc, dest, lit)
|
||||||
|
|
||||||
|
proc genTypeLit(c: PCtx; t: PType; dest: var TDest) =
|
||||||
|
var n = newNode(nkType)
|
||||||
|
n.typ = t
|
||||||
|
genLit(c, n, dest)
|
||||||
|
|
||||||
proc importcSym(c: PCtx; info: TLineInfo; s: PSym) =
|
proc importcSym(c: PCtx; info: TLineInfo; s: PSym) =
|
||||||
when hasFFI:
|
when hasFFI:
|
||||||
if allowFFI in c.features:
|
if allowFFI in c.features:
|
||||||
|
|
@ -920,6 +928,17 @@ proc cannotEval(n: PNode) {.noinline.} =
|
||||||
globalError(n.info, errGenerated, "cannot evaluate at compile time: " &
|
globalError(n.info, errGenerated, "cannot evaluate at compile time: " &
|
||||||
n.renderTree)
|
n.renderTree)
|
||||||
|
|
||||||
|
proc genGlobalInit(c: PCtx; n: PNode; s: PSym) =
|
||||||
|
c.globals.add(emptyNode)
|
||||||
|
s.position = c.globals.len
|
||||||
|
# This is rather hard to support, due to the laziness of the VM code
|
||||||
|
# generator. See tests/compile/tmacro2 for why this is necesary:
|
||||||
|
# var decls{.compileTime.}: seq[PNimrodNode] = @[]
|
||||||
|
c.gABx(n, opcGlobalOnce, 0, s.position)
|
||||||
|
let tmp = c.genx(s.ast)
|
||||||
|
c.gABx(n, whichAsgnOpc(n, opcWrGlobal), tmp, s.position)
|
||||||
|
c.freeTemp(tmp)
|
||||||
|
|
||||||
proc genRdVar(c: PCtx; n: PNode; dest: var TDest) =
|
proc genRdVar(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
let s = n.sym
|
let s = n.sym
|
||||||
if s.isGlobal:
|
if s.isGlobal:
|
||||||
|
|
@ -930,10 +949,7 @@ proc genRdVar(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
if dest < 0: dest = c.getTemp(s.typ)
|
if dest < 0: dest = c.getTemp(s.typ)
|
||||||
if s.position == 0:
|
if s.position == 0:
|
||||||
if sfImportc in s.flags: c.importcSym(n.info, s)
|
if sfImportc in s.flags: c.importcSym(n.info, s)
|
||||||
else:
|
else: genGlobalInit(c, n, s)
|
||||||
c.globals.add(s.ast)
|
|
||||||
s.position = c.globals.len
|
|
||||||
# XXX var g = codeHere() ?
|
|
||||||
c.gABx(n, opcLdGlobal, dest, s.position)
|
c.gABx(n, opcLdGlobal, dest, s.position)
|
||||||
else:
|
else:
|
||||||
if s.position > 0 or (s.position == 0 and s.kind in {skParam, skResult}):
|
if s.position > 0 or (s.position == 0 and s.kind in {skParam, skResult}):
|
||||||
|
|
@ -1052,6 +1068,7 @@ proc genVarSection(c: PCtx; n: PNode) =
|
||||||
let sa = if s.ast.isNil: getNullValue(s.typ, a.info) else: s.ast
|
let sa = if s.ast.isNil: getNullValue(s.typ, a.info) else: s.ast
|
||||||
c.globals.add(sa)
|
c.globals.add(sa)
|
||||||
s.position = c.globals.len
|
s.position = c.globals.len
|
||||||
|
# "Once support" is unnecessary here
|
||||||
if a.sons[2].kind == nkEmpty:
|
if a.sons[2].kind == nkEmpty:
|
||||||
when false:
|
when false:
|
||||||
withTemp(tmp, s.typ):
|
withTemp(tmp, s.typ):
|
||||||
|
|
@ -1079,15 +1096,16 @@ proc genVarSection(c: PCtx; n: PNode) =
|
||||||
proc genArrayConstr(c: PCtx, n: PNode, dest: var TDest) =
|
proc genArrayConstr(c: PCtx, n: PNode, dest: var TDest) =
|
||||||
if dest < 0: dest = c.getTemp(n.typ)
|
if dest < 0: dest = c.getTemp(n.typ)
|
||||||
c.gABx(n, opcLdNull, dest, c.genType(n.typ))
|
c.gABx(n, opcLdNull, dest, c.genType(n.typ))
|
||||||
let intType = getSysType(tyInt)
|
if n.len > 0:
|
||||||
var tmp = getTemp(c, intType)
|
let intType = getSysType(tyInt)
|
||||||
c.gABx(n, opcLdNull, tmp, c.genType(intType))
|
var tmp = getTemp(c, intType)
|
||||||
for x in n:
|
c.gABx(n, opcLdNull, tmp, c.genType(intType))
|
||||||
let a = c.genx(x)
|
for x in n:
|
||||||
c.gABC(n, whichAsgnOpc(x, opcWrArr), dest, tmp, a)
|
let a = c.genx(x)
|
||||||
c.gABI(n, opcAddImmInt, tmp, tmp, 1)
|
c.gABC(n, whichAsgnOpc(x, opcWrArr), dest, tmp, a)
|
||||||
c.freeTemp(a)
|
c.gABI(n, opcAddImmInt, tmp, tmp, 1)
|
||||||
c.freeTemp(tmp)
|
c.freeTemp(a)
|
||||||
|
c.freeTemp(tmp)
|
||||||
|
|
||||||
proc genSetConstr(c: PCtx, n: PNode, dest: var TDest) =
|
proc genSetConstr(c: PCtx, n: PNode, dest: var TDest) =
|
||||||
if dest < 0: dest = c.getTemp(n.typ)
|
if dest < 0: dest = c.getTemp(n.typ)
|
||||||
|
|
@ -1167,6 +1185,8 @@ proc gen(c: PCtx; n: PNode; dest: var TDest) =
|
||||||
InternalError(n.info,
|
InternalError(n.info,
|
||||||
"too large offset! cannot generate code for: " & s.name.s)
|
"too large offset! cannot generate code for: " & s.name.s)
|
||||||
dest = s.position
|
dest = s.position
|
||||||
|
of skType:
|
||||||
|
genTypeLit(c, s.typ, dest)
|
||||||
else:
|
else:
|
||||||
InternalError(n.info, "cannot generate code for: " & s.name.s)
|
InternalError(n.info, "cannot generate code for: " & s.name.s)
|
||||||
of nkCallKinds:
|
of nkCallKinds:
|
||||||
|
|
@ -1371,7 +1391,7 @@ proc genProc(c: PCtx; s: PSym): int =
|
||||||
c.gABC(body, opcEof, eofInstr.regA)
|
c.gABC(body, opcEof, eofInstr.regA)
|
||||||
c.optimizeJumps(result)
|
c.optimizeJumps(result)
|
||||||
s.offset = c.prc.maxSlots
|
s.offset = c.prc.maxSlots
|
||||||
#if s.name.s == "treeRepr" or s.name.s == "traverse":
|
#if s.name.s == "importImpl_forward" or s.name.s == "importImpl":
|
||||||
# c.echoCode(result)
|
# c.echoCode(result)
|
||||||
# echo renderTree(body)
|
# echo renderTree(body)
|
||||||
c.prc = oldPrc
|
c.prc = oldPrc
|
||||||
|
|
|
||||||
|
|
@ -257,7 +257,7 @@ proc limitCommitMsg(m: string): string =
|
||||||
proc handleWebMessage(state: PState, line: string) =
|
proc handleWebMessage(state: PState, line: string) =
|
||||||
echo("Got message from hub: " & line)
|
echo("Got message from hub: " & line)
|
||||||
var json = parseJson(line)
|
var json = parseJson(line)
|
||||||
if json.existsKey("payload"):
|
if json.hasKey("payload"):
|
||||||
for i in 0..min(4, json["payload"]["commits"].len-1):
|
for i in 0..min(4, json["payload"]["commits"].len-1):
|
||||||
var commit = json["payload"]["commits"][i]
|
var commit = json["payload"]["commits"][i]
|
||||||
# Create the message
|
# Create the message
|
||||||
|
|
@ -273,8 +273,8 @@ proc handleWebMessage(state: PState, line: string) =
|
||||||
|
|
||||||
# Send message to #nimrod.
|
# Send message to #nimrod.
|
||||||
state.ircClient.privmsg(joinChans[0], message)
|
state.ircClient.privmsg(joinChans[0], message)
|
||||||
elif json.existsKey("redisinfo"):
|
elif json.hasKey("redisinfo"):
|
||||||
assert json["redisinfo"].existsKey("port")
|
assert json["redisinfo"].hasKey("port")
|
||||||
#let redisPort = json["redisinfo"]["port"].num
|
#let redisPort = json["redisinfo"]["port"].num
|
||||||
state.dbConnected = true
|
state.dbConnected = true
|
||||||
|
|
||||||
|
|
|
||||||
1
todo.txt
1
todo.txt
|
|
@ -20,7 +20,6 @@ Bugs
|
||||||
- bug: 'type T = ref T' not recognized as illegal recursion
|
- bug: 'type T = ref T' not recognized as illegal recursion
|
||||||
- bug: type conversions concerning proc types are weird
|
- bug: type conversions concerning proc types are weird
|
||||||
- compilation of niminst takes way too long. looks like a regression
|
- compilation of niminst takes way too long. looks like a regression
|
||||||
- simple closure iterator doesn't work
|
|
||||||
- docgen: sometimes effects are listed twice
|
- docgen: sometimes effects are listed twice
|
||||||
- 'result' is not properly cleaned for NRVO --> use uninit checking instead
|
- 'result' is not properly cleaned for NRVO --> use uninit checking instead
|
||||||
- sneaking with qualifiedLookup() is really broken!
|
- sneaking with qualifiedLookup() is really broken!
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue