diff options
author | Andreas Rumpf <andreas@andreas-desktop> | 2010-03-10 16:33:55 +0100 |
---|---|---|
committer | Andreas Rumpf <andreas@andreas-desktop> | 2010-03-10 16:33:55 +0100 |
commit | 96b828a3863c28680e8a5b0165c5e0bbcca7a46c (patch) | |
tree | 6ab8e58da5bf2dde1c0c865f60ef9ecf1a55ba15 /rod | |
parent | 2e280eafa8b13802980cf0e2f309342742e61347 (diff) | |
download | Nim-96b828a3863c28680e8a5b0165c5e0bbcca7a46c.tar.gz |
bugfix: len openarray
Diffstat (limited to 'rod')
-rwxr-xr-x | rod/sem.nim | 5 | ||||
-rwxr-xr-x | rod/semfold.nim | 36 |
2 files changed, 28 insertions, 13 deletions
diff --git a/rod/sem.nim b/rod/sem.nim index 7ea6338a2..ac2f21857 100755 --- a/rod/sem.nim +++ b/rod/sem.nim @@ -85,7 +85,10 @@ proc semAndEvalConstExpr(c: PContext, n: PNode): PNode = proc semAfterMacroCall(c: PContext, n: PNode, s: PSym): PNode = result = n case s.typ.sons[0].kind - of tyExpr: result = semExprWithType(c, result) + of tyExpr: + # BUGFIX: we cannot expect a type here, because module aliases would not + # work then (see the ``tmodulealias`` test) + result = semExpr(c, result) # semExprWithType(c, result) of tyStmt: result = semStmt(c, result) of tyTypeDesc: result.typ = semTypeNode(c, result, nil) else: liMessage(s.info, errInvalidParamKindX, typeToString(s.typ.sons[0])) diff --git a/rod/semfold.nim b/rod/semfold.nim index fddf47398..95710af75 100755 --- a/rod/semfold.nim +++ b/rod/semfold.nim @@ -256,6 +256,21 @@ proc leValueConv(a, b: PNode): bool = else: InternalError(a.info, "leValueConv") else: InternalError(a.info, "leValueConv") +proc magicCall(m: PSym, n: PNode): PNode = + var s = n.sons[0].sym + var a = getConstExpr(m, n.sons[1]) + var b, c: PNode + if a == nil: return + if sonsLen(n) > 2: + b = getConstExpr(m, n.sons[2]) + if b == nil: return + if sonsLen(n) > 3: + c = getConstExpr(m, n.sons[3]) + if c == nil: return + else: + b = nil + result = evalOp(s.magic, n, a, b, c) + proc getConstExpr(m: PSym, n: PNode): PNode = result = nil case n.kind @@ -308,19 +323,16 @@ proc getConstExpr(m: PSym, n: PNode): PNode = if not (skipTypes(n.sons[1].typ, abstractVar).kind in {tyOpenArray, tySequence, tyString}): result = newIntNodeT(lastOrd(skipTypes(n.sons[1].typ, abstractVar)), n) + of mLengthOpenArray: + var a = n.sons[1] + if a.kind == nkPassAsOpenArray: a = a.sons[0] + if a.kind == nkBracket: + # we can optimize it away! This fixes the bug ``len(134)``. + result = newIntNodeT(sonsLen(a), n) + else: + result = magicCall(m, n) else: - var a = getConstExpr(m, n.sons[1]) - var b, c: PNode - if a == nil: return - if sonsLen(n) > 2: - b = getConstExpr(m, n.sons[2]) - if b == nil: return - if sonsLen(n) > 3: - c = getConstExpr(m, n.sons[3]) - if c == nil: return - else: - b = nil - result = evalOp(s.magic, n, a, b, c) + result = magicCall(m, n) except EOverflow: liMessage(n.info, errOverOrUnderflow) except EDivByZero: |