diff options
-rw-r--r-- | compiler/ccgmerge.nim | 2 | ||||
-rwxr-xr-x | compiler/ccgstmts.nim | 2 | ||||
-rwxr-xr-x | compiler/extccomp.nim | 2 | ||||
-rwxr-xr-x | compiler/semexprs.nim | 44 | ||||
-rwxr-xr-x | compiler/semgnrc.nim | 35 | ||||
-rwxr-xr-x | compiler/types.nim | 2 | ||||
-rw-r--r-- | doc/trmacros.txt | 2 | ||||
-rwxr-xr-x | koch.nim | 1 | ||||
-rwxr-xr-x | lib/pure/sockets.nim | 3 | ||||
-rw-r--r-- | lib/pure/subexes.nim | 4 | ||||
-rwxr-xr-x | tests/tester.nim | 10 | ||||
-rwxr-xr-x | web/nimrod.ini | 2 |
12 files changed, 70 insertions, 39 deletions
diff --git a/compiler/ccgmerge.nim b/compiler/ccgmerge.nim index 8c490a693..df7e7f68b 100644 --- a/compiler/ccgmerge.nim +++ b/compiler/ccgmerge.nim @@ -228,7 +228,7 @@ proc processMergeInfo(L: var TBaseLexer, m: BModule) = when not defined(nimhygiene): {.pragma: inject.} -template withCFile(cfilename: string, body: stmt) = +template withCFile(cfilename: string, body: stmt) {.immediate.} = var s = LLStreamOpen(cfilename, fmRead) if s == nil: return var L {.inject.}: TBaseLexer diff --git a/compiler/ccgstmts.nim b/compiler/ccgstmts.nim index 7a2eaec9c..dfa624821 100755 --- a/compiler/ccgstmts.nim +++ b/compiler/ccgstmts.nim @@ -87,7 +87,7 @@ proc genSimpleBlock(p: BProc, stmts: PNode) {.inline.} = genStmts(p, stmts) endBlock(p) -template preserveBreakIdx(body: stmt): stmt = +template preserveBreakIdx(body: stmt): stmt {.immediate.} = var oldBreakIdx = p.breakIdx body p.breakIdx = oldBreakIdx diff --git a/compiler/extccomp.nim b/compiler/extccomp.nim index f6ce307d6..7b3dc0b3e 100755 --- a/compiler/extccomp.nim +++ b/compiler/extccomp.nim @@ -50,7 +50,7 @@ type # When adding new compilers, the cmake sources could be a good reference: # http://cmake.org/gitweb?p=cmake.git;a=tree;f=Modules/Platform; -template compiler(name: expr, settings: stmt):stmt = +template compiler(name: expr, settings: stmt): stmt {.immediate.} = proc name: TInfoCC {.compileTime.} = settings compiler gcc: diff --git a/compiler/semexprs.nim b/compiler/semexprs.nim index fc3ea1820..027cd0946 100755 --- a/compiler/semexprs.nim +++ b/compiler/semexprs.nim @@ -1356,30 +1356,40 @@ proc semBlockExpr(c: PContext, n: PNode): PNode = closeScope(c.tab) Dec(c.p.nestedBlockCounter) -proc semMacroStmt(c: PContext, n: PNode, semCheck = true): PNode = - # XXX why no overloading here? +proc semMacroStmt(c: PContext, n: PNode, flags: TExprFlags, + semCheck = true): PNode = checkMinSonsLen(n, 2) var a: PNode if isCallExpr(n.sons[0]): a = n.sons[0].sons[0] else: a = n.sons[0] var s = qualifiedLookup(c, a, {checkUndeclared}) if s != nil: + # transform + # nkMacroStmt(nkCall(a...), stmt, b...) + # to + # nkCall(a..., stmt, b...) + result = newNodeI(nkCall, n.info) + addSon(result, a) + if isCallExpr(n.sons[0]): + for i in countup(1, sonsLen(n.sons[0]) - 1): + addSon(result, n.sons[0].sons[i]) + # for sigmatch this need to have a type; we use 'void': + for i in countup(1, sonsLen(n) - 1): + n.sons[i].typ = newTypeS(tyEmpty, c) + addSon(result, n.sons[i]) + case s.kind - of skMacro: - result = semMacroExpr(c, n, n, s, semCheck) + of skMacro: + if sfImmediate notin s.flags: + result = semDirectOp(c, result, flags) + else: + result = semMacroExpr(c, result, n, s, semCheck) of skTemplate: - # transform - # nkMacroStmt(nkCall(a...), stmt, b...) - # to - # nkCall(a..., stmt, b...) - result = newNodeI(nkCall, n.info) - addSon(result, a) - if isCallExpr(n.sons[0]): - for i in countup(1, sonsLen(n.sons[0]) - 1): - addSon(result, n.sons[0].sons[i]) - for i in countup(1, sonsLen(n) - 1): addSon(result, n.sons[i]) - result = semTemplateExpr(c, result, s, semCheck) - else: + if sfImmediate notin s.flags: + result = semDirectOp(c, result, flags) + else: + result = semTemplateExpr(c, result, s, semCheck) + else: LocalError(n.info, errXisNoMacroOrTemplate, s.name.s) result = errorNode(c, n) else: @@ -1494,7 +1504,7 @@ proc semExpr(c: PContext, n: PNode, flags: TExprFlags = {}): PNode = else: result = semIndirectOp(c, n, flags) of nkMacroStmt: - result = semMacroStmt(c, n) + result = semMacroStmt(c, n, flags) of nkWhenExpr: result = semWhen(c, n, false) result = semExpr(c, result) diff --git a/compiler/semgnrc.nim b/compiler/semgnrc.nim index ea3eebc3a..e9c746db5 100755 --- a/compiler/semgnrc.nim +++ b/compiler/semgnrc.nim @@ -40,6 +40,9 @@ proc semGenericStmtScope(c: PContext, n: PNode, result = semGenericStmt(c, n, flags, toBind) closeScope(c.tab) +template macroToExpand(s: expr): expr = + s.kind in {skMacro, skTemplate} and (s.typ.len == 1 or sfImmediate in s.flags) + proc semGenericStmtSymbol(c: PContext, n: PNode, s: PSym): PNode = incl(s.flags, sfUsed) case s.kind @@ -49,9 +52,15 @@ proc semGenericStmtSymbol(c: PContext, n: PNode, s: PSym): PNode = of skProc, skMethod, skIterator, skConverter: result = symChoice(c, n, s, scOpen) of skTemplate: - result = semTemplateExpr(c, n, s, false) + if macroToExpand(s): + result = semTemplateExpr(c, n, s, false) + else: + result = symChoice(c, n, s, scOpen) of skMacro: - result = semMacroExpr(c, n, n, s, false) + if macroToExpand(s): + result = semMacroExpr(c, n, n, s, false) + else: + result = symChoice(c, n, s, scOpen) of skGenericParam: result = newSymNode(s, n.info) of skParam: @@ -96,10 +105,18 @@ proc semGenericStmt(c: PContext, n: PNode, if s != nil: incl(s.flags, sfUsed) case s.kind - of skMacro: - result = semMacroExpr(c, n, n, s, false) + of skMacro: + if macroToExpand(s): + result = semMacroExpr(c, n, n, s, false) + else: + n.sons[0] = symChoice(c, n.sons[0], s, scOpen) + result = n of skTemplate: - result = semTemplateExpr(c, n, s, false) + if macroToExpand(s): + result = semTemplateExpr(c, n, s, false) + else: + n.sons[0] = symChoice(c, n.sons[0], s, scOpen) + result = n # BUGFIX: we must not return here, we need to do first phase of # symbol lookup ... of skUnknown, skParam: @@ -121,7 +138,13 @@ proc semGenericStmt(c: PContext, n: PNode, for i in countup(first, sonsLen(result) - 1): result.sons[i] = semGenericStmt(c, result.sons[i], flags, toBind) of nkMacroStmt: - result = semMacroStmt(c, n, false) + checkMinSonsLen(n, 2) + var a: PNode + if isCallExpr(n.sons[0]): a = n.sons[0].sons[0] + else: a = n.sons[0] + var s = qualifiedLookup(c, a, {}) + if s != nil and macroToExpand(s): + result = semMacroStmt(c, n, {}, false) for i in countup(0, sonsLen(result)-1): result.sons[i] = semGenericStmt(c, result.sons[i], flags, toBind) of nkIfStmt: diff --git a/compiler/types.nim b/compiler/types.nim index bf7655ebb..a0650abba 100755 --- a/compiler/types.nim +++ b/compiler/types.nim @@ -701,7 +701,7 @@ proc sameTuple(a, b: PType, c: var TSameTypeClosure): bool = else: result = false -template IfFastObjectTypeCheckFailed(a, b: PType, body: stmt) = +template IfFastObjectTypeCheckFailed(a, b: PType, body: stmt) {.immediate.} = if tfFromGeneric notin a.flags + b.flags: # fast case: id comparison suffices: result = a.id == b.id diff --git a/doc/trmacros.txt b/doc/trmacros.txt index bb6591827..e138625f0 100644 --- a/doc/trmacros.txt +++ b/doc/trmacros.txt @@ -17,7 +17,7 @@ pipeline with user defined optimizations: The compiler now rewrites ``x * 2`` as ``x + x``. The code inside the curlies is the pattern to match against. The operators ``*``, ``**``, - ``|``, ``~`` have a special meaning in patterns if they are written in infix +``|``, ``~`` have a special meaning in patterns if they are written in infix notation, so to match verbatim against ``*`` the ordinary function call syntax needs to be used. diff --git a/koch.nim b/koch.nim index 1be9a529d..6bc63a6ce 100755 --- a/koch.nim +++ b/koch.nim @@ -257,7 +257,6 @@ proc tests(args: string) = exec("nimrod cc --taintMode:on tests/tester") exec(getCurrentDir() / "tests/tester".exe & " reject") exec(getCurrentDir() / "tests/tester".exe & " compile") - exec(getCurrentDir() / "tests/tester".exe & " examples") exec(getCurrentDir() / "tests/tester".exe & " run") exec(getCurrentDir() / "tests/tester".exe & " merge") diff --git a/lib/pure/sockets.nim b/lib/pure/sockets.nim index d0a4c216a..7b1ef818b 100755 --- a/lib/pure/sockets.nim +++ b/lib/pure/sockets.nim @@ -388,7 +388,8 @@ proc getSockName*(socket: TSocket): TPort = proc selectWrite*(writefds: var seq[TSocket], timeout = 500): int -template acceptAddrPlain(noClientRet, successRet: expr, sslImplementation: stmt): stmt = +template acceptAddrPlain(noClientRet, successRet: expr, + sslImplementation: stmt): stmt {.immediate.} = assert(client != nil) var sockAddress: Tsockaddr_in var addrLen = sizeof(sockAddress).TSockLen diff --git a/lib/pure/subexes.nim b/lib/pure/subexes.nim index 3e5e36b38..92797744a 100644 --- a/lib/pure/subexes.nim +++ b/lib/pure/subexes.nim @@ -39,12 +39,12 @@ type f: cstring num, i, lineLen: int -template call(x: stmt) = +template call(x: stmt) {.immediate.} = p.i = i x i = p.i -template callNoLineLenTracking(x: stmt) = +template callNoLineLenTracking(x: stmt) {.immediate.} = let oldLineLen = p.lineLen p.i = i x diff --git a/tests/tester.nim b/tests/tester.nim index 8c9f7f782..795c094b7 100755 --- a/tests/tester.nim +++ b/tests/tester.nim @@ -18,7 +18,7 @@ const resultsFile = "testresults.html" jsonFile = "testresults.json" Usage = "usage: tester [--print] " & - "reject|compile|examples|run|" & + "reject|compile|run|" & "merge|special|rodfiles| [nimrod options]\n" & " or: tester test|comp|rej singleTest" @@ -65,7 +65,7 @@ proc extractSpec(filename: string): string = when not defined(nimhygiene): {.pragma: inject.} -template parseSpecAux(fillResult: stmt) = +template parseSpecAux(fillResult: stmt) {.immediate.} = var ss = newStringStream(extractSpec(filename)) var p {.inject.}: TCfgParser open(p, ss, filename, 1) @@ -125,7 +125,7 @@ proc callCompiler(cmdTemplate, filename, options: string): TSpec = var x = newStringOfCap(120) while outp.readLine(x.TaintedString) or running(p): if x =~ pegOfInterest: - # `s` should contain the last error/warning message + # `err` should contain the last error/warning message err = x elif x =~ pegSuccess: suc = x @@ -360,12 +360,10 @@ proc main() = of "compile": compile(r, "tests/compile/t*.nim", p.cmdLineRest.string) compile(r, "tests/ecmas.nim", p.cmdLineRest.string) - compileSpecialTests(r, p.cmdLineRest.string) - writeResults(compileJson, r) - of "examples": compileExample(r, "lib/pure/*.nim", p.cmdLineRest.string) compileExample(r, "examples/*.nim", p.cmdLineRest.string) compileExample(r, "examples/gtk/*.nim", p.cmdLineRest.string) + compileSpecialTests(r, p.cmdLineRest.string) writeResults(compileJson, r) of "run": run(r, "tests/run", p.cmdLineRest.string) diff --git a/web/nimrod.ini b/web/nimrod.ini index d81ec097c..104e84429 100755 --- a/web/nimrod.ini +++ b/web/nimrod.ini @@ -22,7 +22,7 @@ file: ticker [Documentation] doc: "endb;intern;apis;lib;manual;tut1;tut2;nimrodc;overview;filters;trmacros" -doc: "tools;c2nim;niminst;nimgrep" +doc: "tools;c2nim;niminst;nimgrep;gc" pdf: "manual;lib;tut1;tut2;nimrodc;c2nim;niminst;gc" srcdoc: "core/macros;pure/marshal;core/typeinfo;core/unsigned" srcdoc: "impure/graphics;impure/re;pure/sockets" |