diff options
Diffstat (limited to 'compiler')
-rw-r--r-- | compiler/astalgo.nim | 8 | ||||
-rw-r--r-- | compiler/semexprs.nim | 7 | ||||
-rw-r--r-- | compiler/semmagic.nim | 10 | ||||
-rw-r--r-- | compiler/sempass2.nim | 2 | ||||
-rw-r--r-- | compiler/transf.nim | 4 |
5 files changed, 23 insertions, 8 deletions
diff --git a/compiler/astalgo.nim b/compiler/astalgo.nim index 62d49445b..839c4645d 100644 --- a/compiler/astalgo.nim +++ b/compiler/astalgo.nim @@ -1001,3 +1001,11 @@ proc iiTablePut(t: var TIITable, key, val: int) = swap(t.data, n) iiTableRawInsert(t.data, key, val) inc(t.counter) + +proc isAddrNode*(n: PNode): bool = + case n.kind + of nkAddr, nkHiddenAddr: true + of nkCallKinds: + if n[0].kind == nkSym and n[0].sym.magic == mAddr: true + else: false + else: false \ No newline at end of file diff --git a/compiler/semexprs.nim b/compiler/semexprs.nim index 91ee2aae8..3e8edc687 100644 --- a/compiler/semexprs.nim +++ b/compiler/semexprs.nim @@ -2034,7 +2034,9 @@ proc semMagic(c: PContext, n: PNode, s: PSym, flags: TExprFlags): PNode = case s.magic # magics that need special treatment of mAddr: checkSonsLen(n, 2, c.config) - result = semAddr(c, n.sons[1], s.name.s == "unsafeAddr") + result[0] = newSymNode(s, n[0].info) + result[1] = semAddrArg(c, n.sons[1], s.name.s == "unsafeAddr") + result.typ = makePtrType(c, result[1].typ) of mTypeOf: result = semTypeOf(c, n) #of mArrGet: result = semArrGet(c, n, flags) @@ -2579,7 +2581,8 @@ proc semExpr(c: PContext, n: PNode, flags: TExprFlags = {}): PNode = of nkAddr: result = n checkSonsLen(n, 1, c.config) - result = semAddr(c, n.sons[0]) + result[0] = semAddrArg(c, n.sons[0]) + result.typ = makePtrType(c, result[0].typ) of nkHiddenAddr, nkHiddenDeref: checkSonsLen(n, 1, c.config) n.sons[0] = semExpr(c, n.sons[0], flags) diff --git a/compiler/semmagic.nim b/compiler/semmagic.nim index 77286393e..a0c35c9ca 100644 --- a/compiler/semmagic.nim +++ b/compiler/semmagic.nim @@ -10,8 +10,7 @@ # This include file implements the semantic checking for magics. # included from sem.nim -proc semAddr(c: PContext; n: PNode; isUnsafeAddr=false): PNode = - result = newNodeI(nkAddr, n.info) +proc semAddrArg(c: PContext; n: PNode; isUnsafeAddr = false): PNode = let x = semExprWithType(c, n) if x.kind == nkSym: x.sym.flags.incl(sfAddrTaken) @@ -22,8 +21,7 @@ proc semAddr(c: PContext; n: PNode; isUnsafeAddr=false): PNode = localError(c.config, n.info, errExprHasNoAddress) else: localError(c.config, n.info, errExprHasNoAddress & "; maybe use 'unsafeAddr'") - result.add x - result.typ = makePtrType(c, x.typ) + result = x proc semTypeOf(c: PContext; n: PNode): PNode = var m = BiggestInt 1 # typeOfIter @@ -335,7 +333,9 @@ proc magicsAfterOverloadResolution(c: PContext, n: PNode, case n[0].sym.magic of mAddr: checkSonsLen(n, 2, c.config) - result = semAddr(c, n.sons[1], n[0].sym.name.s == "unsafeAddr") + result = n + result[1] = semAddrArg(c, n[1], n[0].sym.name.s == "unsafeAddr") + result.typ = makePtrType(c, result[1].typ) of mTypeOf: result = semTypeOf(c, n) of mSizeOf: diff --git a/compiler/sempass2.nim b/compiler/sempass2.nim index b23780ed4..6ac90f617 100644 --- a/compiler/sempass2.nim +++ b/compiler/sempass2.nim @@ -538,7 +538,7 @@ proc notNilCheck(tracked: PEffects, n: PNode, paramType: PType) = let paramType = paramType.skipTypesOrNil(abstractInst) if paramType != nil and tfNotNil in paramType.flags and n.typ != nil and tfNotNil notin n.typ.flags: - if n.kind == nkAddr: + if isAddrNode(n): # addr(x[]) can't be proven, but addr(x) can: if not containsNode(n, {nkDerefExpr, nkHiddenDeref}): return elif (n.kind == nkSym and n.sym.kind in routineKinds) or diff --git a/compiler/transf.nim b/compiler/transf.nim index ed4a7018d..cac0ded90 100644 --- a/compiler/transf.nim +++ b/compiler/transf.nim @@ -762,6 +762,10 @@ proc transformCall(c: PTransf, n: PNode): PTransNode = inc(j) add(result, a.PTransNode) if len(result) == 2: result = result[1] + elif magic == mAddr: + result = newTransNode(nkAddr, n, 1) + result[0] = n[1].PTransNode + result = transformAddrDeref(c, result.PNode, nkDerefExpr, nkHiddenDeref) elif magic in {mNBindSym, mTypeOf, mRunnableExamples}: # for bindSym(myconst) we MUST NOT perform constant folding: result = n.PTransNode |