summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorAraq <rumpf_a@web.de>2011-08-19 01:46:24 +0200
committerAraq <rumpf_a@web.de>2011-08-19 01:46:24 +0200
commitc7b130b4e2b5350c8b48cdbbef35cd42e773f67f (patch)
treeed6ecc256628287f933bfaa956a455ef202e6e7f
parent257b16ca34af4695a2c8881c976f5fe343fe51ed (diff)
downloadNim-c7b130b4e2b5350c8b48cdbbef35cd42e773f67f.tar.gz
implemented --nimcache config option; big clean up of magic words
-rwxr-xr-xcompiler/commands.nim241
-rwxr-xr-xcompiler/nimrod.nim5
-rwxr-xr-xcompiler/options.nim11
-rwxr-xr-xcompiler/transf.nim34
-rwxr-xr-xcompiler/wordrecg.nim47
-rwxr-xr-xlib/pure/os.nim15
-rwxr-xr-xtodo.txt1
-rwxr-xr-xweb/news.txt3
8 files changed, 170 insertions, 187 deletions
diff --git a/compiler/commands.nim b/compiler/commands.nim
index a4fe80702..8c8f68745 100755
--- a/compiler/commands.nim
+++ b/compiler/commands.nim
@@ -229,57 +229,59 @@ proc processCompile(filename: string) =
   extccomp.addFileToLink(completeCFilePath(trunc, false))
 
 proc testCompileOptionArg*(switch, arg: string, info: TLineInfo): bool = 
-  case whichKeyword(switch)
-  of wGC: 
-    case whichKeyword(arg)
-    of wBoehm: result = contains(gGlobalOptions, optBoehmGC)
-    of wRefc:  result = contains(gGlobalOptions, optRefcGC)
-    of wNone:  result = gGlobalOptions * {optBoehmGC, optRefcGC} == {}
+  case switch.normalize
+  of "gc": 
+    case arg.normalize
+    of "boehm": result = contains(gGlobalOptions, optBoehmGC)
+    of "refc":  result = contains(gGlobalOptions, optRefcGC)
+    of "none":  result = gGlobalOptions * {optBoehmGC, optRefcGC} == {}
     else: LocalError(info, errNoneBoehmRefcExpectedButXFound, arg)
-  of wOpt: 
-    case whichKeyword(arg)
-    of wSpeed: result = contains(gOptions, optOptimizeSpeed)
-    of wSize: result = contains(gOptions, optOptimizeSize)
-    of wNone: result = gOptions * {optOptimizeSpeed, optOptimizeSize} == {}
+  of "opt": 
+    case arg.normalize
+    of "speed": result = contains(gOptions, optOptimizeSpeed)
+    of "size": result = contains(gOptions, optOptimizeSize)
+    of "none": result = gOptions * {optOptimizeSpeed, optOptimizeSize} == {}
     else: LocalError(info, errNoneSpeedOrSizeExpectedButXFound, arg)
   else: InvalidCmdLineOption(passCmd1, switch, info)
 
 proc testCompileOption*(switch: string, info: TLineInfo): bool = 
-  case whichKeyword(switch)
-  of wDebuginfo: result = contains(gGlobalOptions, optCDebug)
-  of wCompileOnly, wC: result = contains(gGlobalOptions, optCompileOnly)
-  of wNoLinking: result = contains(gGlobalOptions, optNoLinking)
-  of wNoMain: result = contains(gGlobalOptions, optNoMain)
-  of wForceBuild, wF: result = contains(gGlobalOptions, optForceFullMake)
-  of wWarnings, wW: result = contains(gOptions, optWarns)
-  of wHints: result = contains(gOptions, optHints)
-  of wThreadAnalysis: result = contains(gGlobalOptions, optThreadAnalysis)
-  of wStackTrace: result = contains(gOptions, optStackTrace)
-  of wLineTrace: result = contains(gOptions, optLineTrace)
-  of wDebugger: result = contains(gOptions, optEndb)
-  of wProfiler: result = contains(gOptions, optProfiler)
-  of wChecks, wX: result = gOptions * checksOptions == checksOptions
-  of wFloatChecks:
+  case switch.normalize
+  of "debuginfo": result = contains(gGlobalOptions, optCDebug)
+  of "compileonly", "c": result = contains(gGlobalOptions, optCompileOnly)
+  of "nolinking": result = contains(gGlobalOptions, optNoLinking)
+  of "nomain": result = contains(gGlobalOptions, optNoMain)
+  of "forcebuild", "f": result = contains(gGlobalOptions, optForceFullMake)
+  of "warnings", "w": result = contains(gOptions, optWarns)
+  of "hints": result = contains(gOptions, optHints)
+  of "threadanalysis": result = contains(gGlobalOptions, optThreadAnalysis)
+  of "stacktrace": result = contains(gOptions, optStackTrace)
+  of "linetrace": result = contains(gOptions, optLineTrace)
+  of "debugger": result = contains(gOptions, optEndb)
+  of "profiler": result = contains(gOptions, optProfiler)
+  of "checks", "x": result = gOptions * checksOptions == checksOptions
+  of "floatchecks":
     result = gOptions * {optNanCheck, optInfCheck} == {optNanCheck, optInfCheck}
-  of wInfChecks: result = contains(gOptions, optInfCheck)
-  of wNanChecks: result = contains(gOptions, optNanCheck)
-  of wObjChecks: result = contains(gOptions, optObjCheck)
-  of wFieldChecks: result = contains(gOptions, optFieldCheck)
-  of wRangeChecks: result = contains(gOptions, optRangeCheck)
-  of wBoundChecks: result = contains(gOptions, optBoundsCheck)
-  of wOverflowChecks: result = contains(gOptions, optOverflowCheck)
-  of wLineDir: result = contains(gOptions, optLineDir)
-  of wAssertions, wA: result = contains(gOptions, optAssert)
-  of wDeadCodeElim: result = contains(gGlobalOptions, optDeadCodeElim)
-  of wRun, wR: result = contains(gGlobalOptions, optRun)
-  of wSymbolFiles: result = contains(gGlobalOptions, optSymbolFiles)
-  of wGenScript: result = contains(gGlobalOptions, optGenScript)
-  of wThreads: result = contains(gGlobalOptions, optThreads)
+  of "infchecks": result = contains(gOptions, optInfCheck)
+  of "nanchecks": result = contains(gOptions, optNanCheck)
+  of "objchecks": result = contains(gOptions, optObjCheck)
+  of "fieldchecks": result = contains(gOptions, optFieldCheck)
+  of "rangechecks": result = contains(gOptions, optRangeCheck)
+  of "boundchecks": result = contains(gOptions, optBoundsCheck)
+  of "overflowchecks": result = contains(gOptions, optOverflowCheck)
+  of "linedir": result = contains(gOptions, optLineDir)
+  of "assertions", "a": result = contains(gOptions, optAssert)
+  of "deadcodeelim": result = contains(gGlobalOptions, optDeadCodeElim)
+  of "run", "r": result = contains(gGlobalOptions, optRun)
+  of "symbolfiles": result = contains(gGlobalOptions, optSymbolFiles)
+  of "genscript": result = contains(gGlobalOptions, optGenScript)
+  of "threads": result = contains(gGlobalOptions, optThreads)
   else: InvalidCmdLineOption(passCmd1, switch, info)
   
 proc processPath(path: string): string = 
   result = UnixToNativePath(path % ["nimrod", getPrefixDir(), "lib", libpath,
-    "home", removeTrailingDirSep(os.getHomeDir())])
+    "home", removeTrailingDirSep(os.getHomeDir()),
+    "projectname", options.projectName,
+    "projectpath", options.projectPath])
 
 proc addPath(path: string, info: TLineInfo) = 
   if not contains(options.searchPaths, path): 
@@ -310,134 +312,137 @@ proc processSwitch(switch, arg: string, pass: TCmdlinePass, info: TLineInfo) =
     theOS: TSystemOS
     cpu: TSystemCPU
     key, val: string
-  case whichKeyword(switch)
-  of wPath, wP: 
+  case switch.normalize
+  of "path", "p": 
     expectArg(switch, arg, pass, info)
     addPath(processPath(arg), info)
-  of wRecursivePath:
+  of "recursivepath":
     expectArg(switch, arg, pass, info)
     var path = processPath(arg)
     addPathRec(path, info)
     addPath(path, info)
-  of wOut, wO: 
+  of "nimcache":
+    expectArg(switch, arg, pass, info)
+    options.nimcacheDir = processPath(arg)
+  of "out", "o": 
     expectArg(switch, arg, pass, info)
     options.outFile = arg
-  of wDefine, wD: 
+  of "define", "d": 
     expectArg(switch, arg, pass, info)
     DefineSymbol(arg)
-  of wUndef, wU: 
+  of "undef", "u": 
     expectArg(switch, arg, pass, info)
     UndefSymbol(arg)
-  of wCompile: 
+  of "compile": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: processCompile(arg)
-  of wLink: 
+  of "link": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: addFileToLink(arg)
-  of wDebuginfo: 
+  of "debuginfo": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optCDebug)
-  of wCompileOnly, wC: 
+  of "compileonly", "c": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optCompileOnly)
-  of wNoLinking: 
+  of "nolinking": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optNoLinking)
-  of wNoMain: 
+  of "nomain": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optNoMain)
-  of wForceBuild, wF: 
+  of "forcebuild", "f": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optForceFullMake)
-  of wGC: 
+  of "gc": 
     expectArg(switch, arg, pass, info)
-    case whichKeyword(arg)
-    of wBoehm: 
+    case arg.normalize
+    of "boehm": 
       incl(gGlobalOptions, optBoehmGC)
       excl(gGlobalOptions, optRefcGC)
       DefineSymbol("boehmgc")
-    of wRefc: 
+    of "refc": 
       excl(gGlobalOptions, optBoehmGC)
       incl(gGlobalOptions, optRefcGC)
-    of wNone: 
+    of "none": 
       excl(gGlobalOptions, optRefcGC)
       excl(gGlobalOptions, optBoehmGC)
       defineSymbol("nogc")
     else: LocalError(info, errNoneBoehmRefcExpectedButXFound, arg)
-  of wWarnings, wW: ProcessOnOffSwitch({optWarns}, arg, pass, info)
-  of wWarning: ProcessSpecificNote(arg, wWarning, pass, info)
-  of wHint: ProcessSpecificNote(arg, wHint, pass, info)
-  of wHints: ProcessOnOffSwitch({optHints}, arg, pass, info)
-  of wThreadAnalysis: ProcessOnOffSwitchG({optThreadAnalysis}, arg, pass, info)
-  of wStackTrace: ProcessOnOffSwitch({optStackTrace}, arg, pass, info)
-  of wLineTrace: ProcessOnOffSwitch({optLineTrace}, arg, pass, info)
-  of wDebugger: 
+  of "warnings", "w": ProcessOnOffSwitch({optWarns}, arg, pass, info)
+  of "warning": ProcessSpecificNote(arg, wWarning, pass, info)
+  of "hint": ProcessSpecificNote(arg, wHint, pass, info)
+  of "hints": ProcessOnOffSwitch({optHints}, arg, pass, info)
+  of "threadanalysis": ProcessOnOffSwitchG({optThreadAnalysis}, arg, pass, info)
+  of "stacktrace": ProcessOnOffSwitch({optStackTrace}, arg, pass, info)
+  of "linetrace": ProcessOnOffSwitch({optLineTrace}, arg, pass, info)
+  of "debugger": 
     ProcessOnOffSwitch({optEndb}, arg, pass, info)
     if optEndb in gOptions: DefineSymbol("endb")
     else: UndefSymbol("endb")
-  of wProfiler: 
+  of "profiler": 
     ProcessOnOffSwitch({optProfiler}, arg, pass, info)
     if optProfiler in gOptions: DefineSymbol("profiler")
     else: UndefSymbol("profiler")
-  of wChecks, wX: ProcessOnOffSwitch(checksOptions, arg, pass, info)
-  of wFloatChecks:
+  of "checks", "x": ProcessOnOffSwitch(checksOptions, arg, pass, info)
+  of "floatchecks":
     ProcessOnOffSwitch({optNanCheck, optInfCheck}, arg, pass, info)
-  of wInfChecks: ProcessOnOffSwitch({optInfCheck}, arg, pass, info)
-  of wNanChecks: ProcessOnOffSwitch({optNanCheck}, arg, pass, info)
-  of wObjChecks: ProcessOnOffSwitch({optObjCheck}, arg, pass, info)
-  of wFieldChecks: ProcessOnOffSwitch({optFieldCheck}, arg, pass, info)
-  of wRangeChecks: ProcessOnOffSwitch({optRangeCheck}, arg, pass, info)
-  of wBoundChecks: ProcessOnOffSwitch({optBoundsCheck}, arg, pass, info)
-  of wOverflowChecks: ProcessOnOffSwitch({optOverflowCheck}, arg, pass, info)
-  of wLineDir: ProcessOnOffSwitch({optLineDir}, arg, pass, info)
-  of wAssertions, wA: ProcessOnOffSwitch({optAssert}, arg, pass, info)
-  of wDeadCodeElim: ProcessOnOffSwitchG({optDeadCodeElim}, arg, pass, info)
-  of wThreads: ProcessOnOffSwitchG({optThreads}, arg, pass, info)
-  of wOpt: 
+  of "infchecks": ProcessOnOffSwitch({optInfCheck}, arg, pass, info)
+  of "nanchecks": ProcessOnOffSwitch({optNanCheck}, arg, pass, info)
+  of "objchecks": ProcessOnOffSwitch({optObjCheck}, arg, pass, info)
+  of "fieldchecks": ProcessOnOffSwitch({optFieldCheck}, arg, pass, info)
+  of "rangechecks": ProcessOnOffSwitch({optRangeCheck}, arg, pass, info)
+  of "boundchecks": ProcessOnOffSwitch({optBoundsCheck}, arg, pass, info)
+  of "overflowchecks": ProcessOnOffSwitch({optOverflowCheck}, arg, pass, info)
+  of "linedir": ProcessOnOffSwitch({optLineDir}, arg, pass, info)
+  of "assertions", "a": ProcessOnOffSwitch({optAssert}, arg, pass, info)
+  of "deadcodeelim": ProcessOnOffSwitchG({optDeadCodeElim}, arg, pass, info)
+  of "threads": ProcessOnOffSwitchG({optThreads}, arg, pass, info)
+  of "opt":
     expectArg(switch, arg, pass, info)
-    case whichKeyword(arg)
-    of wSpeed: 
+    case arg.normalize
+    of "speed": 
       incl(gOptions, optOptimizeSpeed)
       excl(gOptions, optOptimizeSize)
-    of wSize: 
+    of "size": 
       excl(gOptions, optOptimizeSpeed)
       incl(gOptions, optOptimizeSize)
-    of wNone: 
+    of "none":
       excl(gOptions, optOptimizeSpeed)
       excl(gOptions, optOptimizeSize)
     else: LocalError(info, errNoneSpeedOrSizeExpectedButXFound, arg)
-  of wApp: 
+  of "app": 
     expectArg(switch, arg, pass, info)
-    case whichKeyword(arg)
-    of wGui: 
+    case arg.normalize
+    of "gui": 
       incl(gGlobalOptions, optGenGuiApp)
       defineSymbol("guiapp")
-    of wConsole: 
+    of "console": 
       excl(gGlobalOptions, optGenGuiApp)
-    of wLib: 
+    of "lib": 
       incl(gGlobalOptions, optGenDynLib)
       excl(gGlobalOptions, optGenGuiApp)
       defineSymbol("library")
     else: LocalError(info, errGuiConsoleOrLibExpectedButXFound, arg)
-  of wPassC, wT: 
+  of "passc", "t": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: extccomp.addCompileOption(arg)
-  of wPassL, wL: 
+  of "passl", "l": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: extccomp.addLinkOption(arg)
-  of wIndex: 
+  of "index": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: gIndexFile = arg
-  of wImport: 
+  of "import": 
     expectArg(switch, arg, pass, info)
     options.addImplicitMod(arg)
-  of wListCmd: 
+  of "listcmd": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optListCmd)
-  of wGenMapping: 
+  of "genmapping": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optGenMapping)
-  of wOS: 
+  of "os": 
     expectArg(switch, arg, pass, info)
     if (pass == passCmd1): 
       theOS = platform.NameToOS(arg)
@@ -446,7 +451,7 @@ proc processSwitch(switch, arg: string, pass: TCmdlinePass, info: TLineInfo) =
         setTarget(theOS, targetCPU)
         incl(gGlobalOptions, optCompileOnly)
         condsyms.InitDefines()
-  of wCPU: 
+  of "cpu": 
     expectArg(switch, arg, pass, info)
     if (pass == passCmd1): 
       cpu = platform.NameToCPU(arg)
@@ -455,61 +460,61 @@ proc processSwitch(switch, arg: string, pass: TCmdlinePass, info: TLineInfo) =
         setTarget(targetOS, cpu)
         incl(gGlobalOptions, optCompileOnly)
         condsyms.InitDefines()
-  of wRun, wR: 
+  of "run", "r": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optRun)
-  of wVerbosity: 
+  of "verbosity": 
     expectArg(switch, arg, pass, info)
     gVerbosity = parseInt(arg)
-  of wParallelBuild: 
+  of "parallelbuild": 
     expectArg(switch, arg, pass, info)
     gNumberOfProcessors = parseInt(arg)
-  of wVersion, wV: 
+  of "version", "v": 
     expectNoArg(switch, arg, pass, info)
     writeVersionInfo(pass)
-  of wAdvanced: 
+  of "advanced": 
     expectNoArg(switch, arg, pass, info)
     writeAdvancedUsage(pass)
-  of wHelp, wH: 
+  of "help", "h": 
     expectNoArg(switch, arg, pass, info)
     helpOnError(pass)
-  of wSymbolFiles: 
+  of "symbolfiles": 
     ProcessOnOffSwitchG({optSymbolFiles}, arg, pass, info)
-  of wSkipCfg: 
+  of "skipcfg": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optSkipConfigFile)
-  of wSkipProjCfg: 
+  of "skipprojcfg": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optSkipProjConfigFile)
-  of wGenScript: 
+  of "genscript": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optGenScript)
-  of wLib: 
+  of "lib": 
     expectArg(switch, arg, pass, info)
     libpath = processPath(arg)
-  of wPutEnv: 
+  of "putenv": 
     expectArg(switch, arg, pass, info)
     splitSwitch(arg, key, val, pass, info)
     os.putEnv(key, val)
-  of wCC: 
+  of "cc": 
     expectArg(switch, arg, pass, info)
     setCC(arg)
-  of wTrack:
+  of "track":
     expectArg(switch, arg, pass, info)
     track(arg, info)
-  of wSuggest: 
+  of "suggest": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optSuggest)
-  of wDef:
+  of "def":
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optDef)
-  of wContext:
+  of "context":
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optContext)
-  of wStdout: 
+  of "stdout": 
     expectNoArg(switch, arg, pass, info)
     incl(gGlobalOptions, optStdout)
-  else: 
+  else:
     if strutils.find(switch, '.') >= 0: options.setConfigVar(switch, arg)
     else: InvalidCmdLineOption(pass, switch, info)
   
diff --git a/compiler/nimrod.nim b/compiler/nimrod.nim
index e4a9d8827..5c91329cd 100755
--- a/compiler/nimrod.nim
+++ b/compiler/nimrod.nim
@@ -58,7 +58,10 @@ proc HandleCmdLine() =
     var command = ""
     var filename = ""
     ProcessCmdLine(passCmd1, command, filename)
-    if filename != "": options.projectPath = splitFile(filename).dir
+    if filename != "": 
+      var p = splitFile(filename)
+      options.projectPath = p.dir
+      options.projectName = p.name
     nimconf.LoadConfig(filename) # load the right config file
     # now process command line arguments again, because some options in the
     # command line can overwite the config file's settings
diff --git a/compiler/options.nim b/compiler/options.nim
index 662848053..0e4960a7e 100755
--- a/compiler/options.nim
+++ b/compiler/options.nim
@@ -104,6 +104,8 @@ var
   gConfigVars*: PStringTable
   libpath*: string = ""
   projectPath*: string = ""
+  projectName* = ""
+  nimcacheDir* = ""
   gKeepComments*: bool = true # whether the parser needs to keep comments
   gImplicitMods*: TStringSeq = @[] # modules that are to be implicitly imported
 
@@ -155,16 +157,19 @@ proc removeTrailingDirSep*(path: string): string =
   else: 
     result = path
   
+proc getGeneratedPath: string =
+  result = if nimcacheDir.len > 0: nimcacheDir else: projectPath / genSubDir
+  
 proc toGeneratedFile(path, ext: string): string = 
   var (head, tail) = splitPath(path)
   if len(head) > 0: head = shortenDir(head & dirSep)
-  result = joinPath([projectPath, genSubDir, head, changeFileExt(tail, ext)])
+  result = joinPath([getGeneratedPath(), head, changeFileExt(tail, ext)])
 
 proc completeGeneratedFilePath(f: string, createSubDir: bool = true): string = 
   var (head, tail) = splitPath(f)
   if len(head) > 0: head = removeTrailingDirSep(shortenDir(head & dirSep))
-  var subdir = joinPath([projectPath, genSubDir, head])
-  if createSubDir: 
+  var subdir = getGeneratedPath() / head
+  if createSubDir:
     try: 
       createDir(subdir)
     except EOS: 
diff --git a/compiler/transf.nim b/compiler/transf.nim
index ce778fac9..482332f38 100755
--- a/compiler/transf.nim
+++ b/compiler/transf.nim
@@ -334,34 +334,6 @@ proc addVar(father, v: PNode) =
   addSon(vpart, ast.emptyNode)
   addSon(father, vpart)
 
-when false:
-  proc transformAddrDeref(c: PTransf, n: PNode, a, b: TNodeKind): PTransNode =
-    case n.sons[0].kind
-    of nkObjUpConv, nkObjDownConv, nkChckRange, nkChckRangeF, nkChckRange64:
-      var m = n.sons[0].sons[0]
-      if m.kind == a or m.kind == b:
-        # addr ( nkConv ( deref ( x ) ) ) --> nkConv(x)
-        var x = copyTree(n)
-        x.sons[0].sons[0] = m.sons[0]
-        result = transform(c, x.sons[0])
-      else:
-        result = transformSons(c, n)
-    of nkHiddenStdConv, nkHiddenSubConv, nkConv:
-      var m = n.sons[0].sons[1]
-      if m.kind == a or m.kind == b:
-        # addr ( nkConv ( deref ( x ) ) ) --> nkConv(x)
-        var x = copyTree(n)
-        x.sons[0].sons[1] = m.sons[0]
-        result = transform(c, x.sons[0])
-      else:
-        result = transformSons(c, n)
-    else:
-      if n.sons[0].kind == a or n.sons[0].kind == b:
-        # addr ( deref ( x )) --> x
-        result = transform(c, n.sons[0].sons[0])
-      else:
-        result = transformSons(c, n)
-
 proc transformAddrDeref(c: PTransf, n: PNode, a, b: TNodeKind): PTransNode =
   result = transformSons(c, n)
   var n = result.pnode
@@ -519,14 +491,8 @@ proc transformFor(c: PTransf, n: PNode): PTransNode =
       IdNodeTablePut(newC.mapping, formal, newSymNode(temp))
     of paVarAsgn:
       assert(skipTypes(formal.typ, abstractInst).kind == tyVar)
-      # XXX why is this even necessary?
-      when false:
-        var b = newNodeIT(nkHiddenAddr, arg.info, formal.typ)
-        b.add(arg)
-        arg = b
       IdNodeTablePut(newC.mapping, formal, arg)
       # XXX BUG still not correct if the arg has a side effect!
-      #InternalError(arg.info, "not implemented: pass to var parameter")
   var body = newC.owner.ast.sons[codePos]
   pushInfoContext(n.info)
   inc(c.inlining)
diff --git a/compiler/wordrecg.nim b/compiler/wordrecg.nim
index 1361475e4..97bdb5c55 100755
--- a/compiler/wordrecg.nim
+++ b/compiler/wordrecg.nim
@@ -40,27 +40,22 @@ type
     wAlign, wNodecl, wPure, wVolatile, wRegister, wSideeffect, wHeader, 
     wNosideeffect, wNoreturn, wMerge, wLib, wDynlib, wCompilerproc, wProcVar, 
     wFatal, wError, wWarning, wHint, wLine, wPush, wPop, wDefine, wUndef, 
-    wLinedir, wStacktrace, wLinetrace, wParallelBuild, wLink, wCompile, 
+    wLinedir, wStacktrace, wLinetrace, wLink, wCompile, 
     wLinksys, wDeprecated, wVarargs, wByref, wCallconv, wBreakpoint, wDebugger, 
     wNimcall, wStdcall, wCdecl, wSafecall, wSyscall, wInline, wNoInline, 
     wFastcall, wClosure, wNoconv, wOn, wOff, wChecks, wRangechecks, 
     wBoundchecks, wOverflowchecks, wNilchecks,
     wFloatchecks, wNanChecks, wInfChecks,
-    wAssertions, wWarnings, wW, 
-    wHints, wOptimization, wSpeed, wSize, wNone, wPath, wP, wD, wU, wDebuginfo, 
-    wCompileonly, wNolinking, wForcebuild, wF, wDeadCodeElim, wSafecode, 
+    wAssertions, wWarnings, 
+    wHints, wOptimization, wSpeed, wSize, wNone, 
+    wDeadCodeElim, wSafecode, 
     wPragma,
-    wCompileTime, wGc, wRefc, wBoehm, wA, wOpt, wO, wApp, wConsole, wGui, 
-    wPassc, wT, wPassl, wL, wListcmd, wGendoc, wGenmapping, wOs, wCpu, 
-    wGenerate, wG, wC, wBorrow, wRun, wR, wVerbosity, wV, wHelp, wH, 
-    wSymbolFiles, wFieldChecks, wX, wVersion, wAdvanced, wSkipcfg, wSkipProjCfg, 
-    wCc, wGenscript, wCheckPoint, wThreadAnalysis, wNoMain, wSubsChar, 
+    wCompileTime,
+    wPassc, wPassl, wBorrow, 
+    wFieldChecks, 
+    wCheckPoint, wSubsChar, 
     wAcyclic, wShallow, wUnroll, wLinearScanEnd,
-    wIndex, 
-    wWrite, wPutEnv, wPrependEnv, wAppendEnv, wThreadVar, wEmit, wThreads,
-    wRecursivePath, 
-    wStdout,
-    wIdeTools, wSuggest, wTrack, wDef, wContext
+    wWrite, wPutEnv, wPrependEnv, wAppendEnv, wThreadVar, wEmit
     
   TSpecialWords* = set[TSpecialWord]
 
@@ -89,28 +84,22 @@ const
     "header", "nosideeffect", "noreturn", "merge", "lib", "dynlib", 
     "compilerproc", "procvar", "fatal", "error", "warning", "hint", "line", 
     "push", "pop", "define", "undef", "linedir", "stacktrace", "linetrace", 
-    "parallelbuild", "link", "compile", "linksys", "deprecated", "varargs", 
+    "link", "compile", "linksys", "deprecated", "varargs", 
     "byref", "callconv", "breakpoint", "debugger", "nimcall", "stdcall", 
     "cdecl", "safecall", "syscall", "inline", "noinline", "fastcall", "closure", 
     "noconv", "on", "off", "checks", "rangechecks", "boundchecks", 
     "overflowchecks", "nilchecks",
     "floatchecks", "nanchecks", "infchecks",
 
-    "assertions", "warnings", "w", "hints", 
-    "optimization", "speed", "size", "none", "path", "p", "d", "u", "debuginfo", 
-    "compileonly", "nolinking", "forcebuild", "f", "deadcodeelim", "safecode", 
+    "assertions", "warnings", "hints", 
+    "optimization", "speed", "size", "none", 
+    "deadcodeelim", "safecode", 
     "pragma",
-    "compiletime", "gc", "refc", "boehm", "a", "opt", "o", "app", "console", 
-    "gui", "passc", "t", "passl", "l", "listcmd", "gendoc", "genmapping", "os", 
-    "cpu", "generate", "g", "c", "borrow", "run", "r", "verbosity", "v", 
-    "help", "h", "symbolfiles", "fieldchecks", "x", "version", "advanced", 
-    "skipcfg", "skipprojcfg", "cc", "genscript", "checkpoint", "threadanalysis", 
-    "nomain", "subschar", "acyclic", "shallow", "unroll", "linearscanend",
-    "index", 
-    "write", "putenv", "prependenv", "appendenv", "threadvar", "emit",
-    "threads", "recursivepath", 
-    "stdout",
-    "idetools", "suggest", "track", "def", "context"]
+    "compiletime", 
+    "passc", "passl", "borrow", "fieldchecks",
+    "checkpoint",
+    "subschar", "acyclic", "shallow", "unroll", "linearscanend",
+    "write", "putenv", "prependenv", "appendenv", "threadvar", "emit"]
 
 proc findStr*(a: openarray[string], s: string): int = 
   for i in countup(low(a), high(a)): 
diff --git a/lib/pure/os.nim b/lib/pure/os.nim
index f33950376..feb2de977 100755
--- a/lib/pure/os.nim
+++ b/lib/pure/os.nim
@@ -512,6 +512,21 @@ proc cmpPaths*(pathA, pathB: string): int {.
   else:
     result = cmpIgnoreCase(pathA, pathB)
 
+proc isAbsolute*(path: string): bool {.rtl, noSideEffect, extern: "nos$1".} =
+  ## Checks whether a given path is absolute.
+  ##
+  ## on Windows, network paths are considered absolute too.
+  var len = len(path)
+  when doslike:
+    result = (len > 1 and path[0] in {'/', '\\'}) or
+             (len > 2 and path[0] in Letters and path[1] == ':')
+  elif defined(macos):
+    result = len > 0 and path[0] != ':'
+  elif defined(RISCOS):
+    result = path[0] == '$'
+  elif defined(posix):
+    result = path[0] == '/'
+
 proc sameFile*(path1, path2: string): bool {.rtl, extern: "nos$1".} =
   ## Returns True if both pathname arguments refer to the same file or
   ## directory (as indicated by device number and i-node number).
diff --git a/todo.txt b/todo.txt
index c621ab17b..99d9f5351 100755
--- a/todo.txt
+++ b/todo.txt
@@ -1,7 +1,6 @@
 Version 0.8.14
 ==============
 
-- fix ``m*`` for generics
 - optional indentation for 'case' statement
 - test the sort implementation again
 - export re-entrant and non-reentrant locks and condition vars; threads should
diff --git a/web/news.txt b/web/news.txt
index 0727000c5..01ce99683 100755
--- a/web/news.txt
+++ b/web/news.txt
@@ -66,7 +66,8 @@ Library Additions
 - Added ``strutils.unindent``.
 - Added ``system.slurp`` for easy resource embedding.
 - Added ``system.running`` for threads.
-- Added proc ``xmltree.innerText``.
+- Added ``xmltree.innerText``.
+- Added ``os.isAbsolute``.
 
 
 2011-07-10 Version 0.8.12 released