diff options
-rw-r--r-- | compiler/vm.nim | 33 | ||||
-rw-r--r-- | compiler/vmdeps.nim | 40 | ||||
-rw-r--r-- | compiler/vmgen.nim | 6 | ||||
-rw-r--r-- | lib/core/macros.nim | 6 |
4 files changed, 62 insertions, 23 deletions
diff --git a/compiler/vm.nim b/compiler/vm.nim index f799334d6..ee58b6d48 100644 --- a/compiler/vm.nim +++ b/compiler/vm.nim @@ -1185,19 +1185,28 @@ proc rawExecute(c: PCtx, start: int, tos: PStackFrame): TFullReg = of opcNGetType: let rb = instr.regB let rc = instr.regC - if rc == 0: - ensureKind(rkNode) - if regs[rb].kind == rkNode and regs[rb].node.typ != nil: - regs[ra].node = opMapTypeToAst(regs[rb].node.typ, c.debug[pc]) + case rc: + of 0: + # getType opcode: + ensureKind(rkNode) + if regs[rb].kind == rkNode and regs[rb].node.typ != nil: + regs[ra].node = opMapTypeToAst(regs[rb].node.typ, c.debug[pc]) + else: + stackTrace(c, tos, pc, errGenerated, "node has no type") + of 1: + # typeKind opcode: + ensureKind(rkInt) + if regs[rb].kind == rkNode and regs[rb].node.typ != nil: + regs[ra].intVal = ord(regs[rb].node.typ.kind) + #else: + # stackTrace(c, tos, pc, errGenerated, "node has no type") else: - stackTrace(c, tos, pc, errGenerated, "node has no type") - else: - # typeKind opcode: - ensureKind(rkInt) - if regs[rb].kind == rkNode and regs[rb].node.typ != nil: - regs[ra].intVal = ord(regs[rb].node.typ.kind) - #else: - # stackTrace(c, tos, pc, errGenerated, "node has no type") + # getTypeInst opcode: + ensureKind(rkNode) + if regs[rb].kind == rkNode and regs[rb].node.typ != nil: + regs[ra].node = opMapTypeInstToAst(regs[rb].node.typ, c.debug[pc]) + else: + stackTrace(c, tos, pc, errGenerated, "node has no type") of opcNStrVal: decodeB(rkNode) createStr regs[ra] diff --git a/compiler/vmdeps.nim b/compiler/vmdeps.nim index a4f02092d..9519da8ba 100644 --- a/compiler/vmdeps.nim +++ b/compiler/vmdeps.nim @@ -67,9 +67,11 @@ proc atomicTypeX(name: string; t: PType; info: TLineInfo): PNode = result = newSymNode(sym) result.typ = t -proc mapTypeToAst(t: PType, info: TLineInfo; allowRecursion=false): PNode +proc mapTypeToAstImpl(t: PType; info: TLineInfo; + inst=false; allowRecursion=false): PNode -proc mapTypeToBracket(name: string; t: PType; info: TLineInfo): PNode = +proc mapTypeToBracketImpl(name: string; t: PType; info: TLineInfo; + inst=false): PNode = result = newNodeIT(nkBracketExpr, if t.n.isNil: info else: t.n.info, t) result.add atomicTypeX(name, t, info) for i in 0 .. < t.len: @@ -78,10 +80,14 @@ proc mapTypeToBracket(name: string; t: PType; info: TLineInfo): PNode = void.typ = newType(tyEmpty, t.owner) result.add void else: - result.add mapTypeToAst(t.sons[i], info) + result.add mapTypeToAstImpl(t.sons[i], info, inst) -proc mapTypeToAst(t: PType, info: TLineInfo; allowRecursion=false): PNode = +proc mapTypeToAstImpl(t: PType; info: TLineInfo; + inst=false; allowRecursion=false): PNode = template atomicType(name): expr = atomicTypeX(name, t, info) + template mapTypeToAst(t,info): expr = mapTypeToAstImpl(t, info, inst) + template mapTypeToBracket(name,t,info): expr = + mapTypeToBracketImpl(name, t, info, inst) case t.kind of tyNone: result = atomicType("none") @@ -107,7 +113,14 @@ proc mapTypeToAst(t: PType, info: TLineInfo; allowRecursion=false): PNode = result = newNodeIT(nkBracketExpr, if t.n.isNil: info else: t.n.info, t) for i in 0 .. < t.len: result.add mapTypeToAst(t.sons[i], info) - of tyGenericInst, tyGenericBody, tyOrdinal, tyUserTypeClassInst: + of tyGenericInst: + if inst: + result = newNodeIT(nkBracketExpr, if t.n.isNil: info else: t.n.info, t) + for i in 0 .. < t.len-1: + result.add mapTypeToAst(t.sons[i], info) + else: + result = mapTypeToAst(t.lastSon, info) + of tyGenericBody, tyOrdinal, tyUserTypeClassInst: result = mapTypeToAst(t.lastSon, info) of tyDistinct: if allowRecursion: @@ -174,10 +187,17 @@ proc mapTypeToAst(t: PType, info: TLineInfo; allowRecursion=false): PNode = of tyNot: result = mapTypeToBracket("not", t, info) of tyAnything: result = atomicType"anything" of tyStatic, tyFromExpr, tyFieldAccessor: - result = newNodeIT(nkBracketExpr, if t.n.isNil: info else: t.n.info, t) - result.add atomicType("static") - if t.n != nil: - result.add t.n.copyTree + if inst: + if t.n != nil: result = t.n.copyTree + else: result = atomicType "void" + else: + result = newNodeIT(nkBracketExpr, if t.n.isNil: info else: t.n.info, t) + result.add atomicType("static") + if t.n != nil: + result.add t.n.copyTree proc opMapTypeToAst*(t: PType; info: TLineInfo): PNode = - result = mapTypeToAst(t, info, true) + result = mapTypeToAstImpl(t, info, false, true) + +proc opMapTypeInstToAst*(t: PType; info: TLineInfo): PNode = + result = mapTypeToAstImpl(t, info, true, true) diff --git a/compiler/vmgen.nim b/compiler/vmgen.nim index 019c79eb3..5ea0989dc 100644 --- a/compiler/vmgen.nim +++ b/compiler/vmgen.nim @@ -983,7 +983,11 @@ proc genMagic(c: PCtx; n: PNode; dest: var TDest; m: TMagic) = of mNGetType: let tmp = c.genx(n.sons[1]) if dest < 0: dest = c.getTemp(n.typ) - c.gABC(n, opcNGetType, dest, tmp, if n[0].sym.name.s == "typeKind": 1 else: 0) + let rc = case n[0].sym.name.s: + of "getType": 0 + of "typeKind": 1 + else: 2 # "getTypeInst" + c.gABC(n, opcNGetType, dest, tmp, rc) c.freeTemp(tmp) #genUnaryABC(c, n, dest, opcNGetType) of mNStrVal: genUnaryABC(c, n, dest, opcNStrVal) diff --git a/lib/core/macros.nim b/lib/core/macros.nim index 678982a52..76fdea9b0 100644 --- a/lib/core/macros.nim +++ b/lib/core/macros.nim @@ -197,6 +197,12 @@ proc typeKind*(n: NimNode): NimTypeKind {.magic: "NGetType", noSideEffect.} ## Returns the type kind of the node 'n' that should represent a type, that ## means the node should have been obtained via `getType`. +proc getTypeInst*(n: NimNode): NimNode {.magic: "NGetType", noSideEffect.} + ## Like getType except it includes generic parameters for a specific instance + +proc getTypeInst*(n: typedesc): NimNode {.magic: "NGetType", noSideEffect.} + ## Like getType except it includes generic parameters for a specific instance + proc strVal*(n: NimNode): string {.magic: "NStrVal", noSideEffect.} proc `intVal=`*(n: NimNode, val: BiggestInt) {.magic: "NSetIntVal", noSideEffect.} |