summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--build_tools.sh3
-rw-r--r--compiler/ast.nim2
-rw-r--r--compiler/ccgtypes.nim5
-rw-r--r--compiler/ccgutils.nim3
-rw-r--r--compiler/installer.ini7
-rw-r--r--compiler/jsgen.nim3
-rw-r--r--compiler/semasgn.nim3
-rw-r--r--compiler/seminst.nim2
-rw-r--r--compiler/semmagic.nim2
-rw-r--r--compiler/sigmatch.nim14
-rw-r--r--compiler/types.nim10
-rw-r--r--compiler/vmdeps.nim2
-rw-r--r--contributors.txt12
-rw-r--r--doc/contributing.rst (renamed from contributing.rst)0
-rw-r--r--doc/docs.rst (renamed from doc/docs.txt)0
-rw-r--r--doc/docstyle.rst (renamed from docstyle.rst)0
-rw-r--r--doc/gc.rst30
-rw-r--r--doc/overview.rst (renamed from doc/overview.txt)2
-rw-r--r--install_nimble.nims4
-rw-r--r--install_tools.nims6
-rw-r--r--koch.nim86
-rw-r--r--lib/core/macros.nim2
-rw-r--r--lib/pure/collections/sequtils.nim4
-rw-r--r--lib/pure/os.nim161
-rw-r--r--lib/pure/unittest.nim24
-rw-r--r--tools/finish.nim (renamed from finish.nim)4
-rw-r--r--tools/niminst/niminst.nim2
-rw-r--r--tools/nimweb.nim21
-rw-r--r--tools/noprefix.nim32
-rw-r--r--tools/start.bat (renamed from start.bat)6
-rw-r--r--web/download.rst10
-rw-r--r--web/news/e028_version_0_15_2.rst13
-rw-r--r--web/website.ini2
33 files changed, 297 insertions, 180 deletions
diff --git a/build_tools.sh b/build_tools.sh
deleted file mode 100644
index 4d867b0ad..000000000
--- a/build_tools.sh
+++ /dev/null
@@ -1,3 +0,0 @@
-./bin/nim c --noNimblePath -p:compiler -o:./bin/nimble dist/nimble/src/nimble.nim
-./bin/nim c --noNimblePath -p:compiler -o:./bin/nimsuggest dist/nimsuggest/nimsuggest.nim
-./bin/nim c -o:./bin/nimgrep tools/nimgrep.nim
diff --git a/compiler/ast.nim b/compiler/ast.nim
index d8939fc60..2426dcc02 100644
--- a/compiler/ast.nim
+++ b/compiler/ast.nim
@@ -347,7 +347,7 @@ type
     tyUInt, tyUInt8, tyUInt16, tyUInt32, tyUInt64,
     tyBigNum,
     tyConst, tyMutable, tyVarargs,
-    tyIter, # unused
+    tyUnused # kept for enum ordinal compatibility
     tyProxy # used as errornous type (for idetools)
 
     tyBuiltInTypeClass #\
diff --git a/compiler/ccgtypes.nim b/compiler/ccgtypes.nim
index eac734b3d..6dcf80f2f 100644
--- a/compiler/ccgtypes.nim
+++ b/compiler/ccgtypes.nim
@@ -122,7 +122,7 @@ proc mapType(typ: PType): TCTypeKind =
   of tyOpenArray, tyArrayConstr, tyArray, tyVarargs: result = ctArray
   of tyObject, tyTuple: result = ctStruct
   of tyGenericBody, tyGenericInst, tyGenericParam, tyDistinct, tyOrdinal,
-     tyConst, tyMutable, tyIter, tyTypeDesc:
+     tyConst, tyMutable, tyTypeDesc:
     result = mapType(lastSon(typ))
   of tyEnum:
     if firstOrd(typ) < 0:
@@ -711,8 +711,7 @@ proc getTypeDescAux(m: BModule, typ: PType, check: var IntSet): Rope =
       of 1, 2, 4, 8: addf(m.s[cfsTypes], "typedef NU$2 $1;$n", [result, rope(s*8)])
       else: addf(m.s[cfsTypes], "typedef NU8 $1[$2];$n",
              [result, rope(getSize(t))])
-  of tyGenericInst, tyDistinct, tyOrdinal, tyConst, tyMutable,
-      tyIter, tyTypeDesc:
+  of tyGenericInst, tyDistinct, tyOrdinal, tyConst, tyMutable, tyTypeDesc:
     result = getTypeDescAux(m, lastSon(t), check)
   else:
     internalError("getTypeDescAux(" & $t.kind & ')')
diff --git a/compiler/ccgutils.nim b/compiler/ccgutils.nim
index ecd98a2bf..898c00f73 100644
--- a/compiler/ccgutils.nim
+++ b/compiler/ccgutils.nim
@@ -106,7 +106,7 @@ proc getUniqueType*(key: PType): PType =
   of tyDistinct:
     if key.deepCopy != nil: result = key
     else: result = getUniqueType(lastSon(key))
-  of tyGenericInst, tyOrdinal, tyMutable, tyConst, tyIter, tyStatic:
+  of tyGenericInst, tyOrdinal, tyMutable, tyConst, tyStatic:
     result = getUniqueType(lastSon(key))
     #let obj = lastSon(key)
     #if obj.sym != nil and obj.sym.name.s == "TOption":
@@ -153,6 +153,7 @@ proc getUniqueType*(key: PType): PType =
     else:
       # ugh, we need the canon here:
       result = slowSearch(key, k)
+  of tyUnused: internalError("getUniqueType")
 
 proc tableGetType*(tab: TIdTable, key: PType): RootRef =
   # returns nil if we need to declare this type
diff --git a/compiler/installer.ini b/compiler/installer.ini
index 40050a2f7..5e4b3ddbc 100644
--- a/compiler/installer.ini
+++ b/compiler/installer.ini
@@ -41,8 +41,8 @@ Files: "config/nimdoc.tex.cfg"
 ; Files: "doc/*.cfg"
 ; Files: "doc/*.pdf"
 ; Files: "doc/*.ini"
-Files: "doc/overview.html"
-Start: "doc/overview.html"
+Files: "doc/html/overview.html"
+Start: "doc/html/overview.html"
 
 
 [Other]
@@ -63,6 +63,7 @@ Files: "icons/koch_icon.o"
 
 Files: "compiler"
 Files: "doc"
+Files: "doc/html"
 Files: "tools"
 Files: "web/website.ini"
 Files: "web/ticker.html"
@@ -93,7 +94,7 @@ Files: "bin/nimble.exe"
 Files: "koch.exe"
 Files: "finish.exe"
 ; Files: "dist/mingw"
-Files: "start.bat"
+Files: r"tools\start.bat"
 BinPath: r"bin;dist\mingw\bin;dist"
 
 ;           Section | dir | zipFile | size hint (in KB) | url | exe start menu entry
diff --git a/compiler/jsgen.nim b/compiler/jsgen.nim
index e7fe8cc27..6b95014f1 100644
--- a/compiler/jsgen.nim
+++ b/compiler/jsgen.nim
@@ -151,7 +151,7 @@ proc mapType(typ: PType): TJSTypeKind =
   of tyPointer:
     # treat a tyPointer like a typed pointer to an array of bytes
     result = etyBaseIndex
-  of tyRange, tyDistinct, tyOrdinal, tyConst, tyMutable, tyIter, tyProxy:
+  of tyRange, tyDistinct, tyOrdinal, tyConst, tyMutable, tyProxy:
     result = mapType(t.sons[0])
   of tyInt..tyInt64, tyUInt..tyUInt64, tyEnum, tyChar: result = etyInt
   of tyBool: result = etyBool
@@ -171,6 +171,7 @@ proc mapType(typ: PType): TJSTypeKind =
     else: result = etyNone
   of tyProc: result = etyProc
   of tyCString: result = etyString
+  of tyUnused: internalError("mapType")
 
 proc mapType(p: PProc; typ: PType): TJSTypeKind =
   if p.target == targetPHP: result = etyObject
diff --git a/compiler/semasgn.nim b/compiler/semasgn.nim
index 2e925e386..64a501e25 100644
--- a/compiler/semasgn.nim
+++ b/compiler/semasgn.nim
@@ -221,7 +221,7 @@ proc liftBodyAux(c: var TLiftCtx; t: PType; body, x, y: PNode) =
       body.add newAsgnStmt(x, call)
   of tyVarargs, tyOpenArray:
     localError(c.info, errGenerated, "cannot copy openArray")
-  of tyFromExpr, tyIter, tyProxy, tyBuiltInTypeClass, tyUserTypeClass,
+  of tyFromExpr, tyProxy, tyBuiltInTypeClass, tyUserTypeClass,
      tyUserTypeClassInst, tyCompositeTypeClass, tyAnd, tyOr, tyNot, tyAnything,
      tyMutable, tyGenericParam, tyGenericBody, tyNil, tyExpr, tyStmt,
      tyTypeDesc, tyGenericInvocation, tyBigNum, tyConst, tyForward:
@@ -229,6 +229,7 @@ proc liftBodyAux(c: var TLiftCtx; t: PType; body, x, y: PNode) =
   of tyOrdinal, tyRange,
      tyGenericInst, tyFieldAccessor, tyStatic, tyVar:
     liftBodyAux(c, lastSon(t), body, x, y)
+  of tyUnused: internalError("liftBodyAux")
 
 proc newProcType(info: TLineInfo; owner: PSym): PType =
   result = newType(tyProc, owner)
diff --git a/compiler/seminst.nim b/compiler/seminst.nim
index 338b254df..e1a65da74 100644
--- a/compiler/seminst.nim
+++ b/compiler/seminst.nim
@@ -58,7 +58,7 @@ iterator instantiateGenericParamList(c: PContext, n: PNode, pt: TIdTable): PSym
   for i, a in n.pairs:
     internalAssert a.kind == nkSym
     var q = a.sym
-    if q.typ.kind notin {tyTypeDesc, tyGenericParam, tyStatic, tyIter}+tyTypeClasses:
+    if q.typ.kind notin {tyTypeDesc, tyGenericParam, tyStatic}+tyTypeClasses:
       continue
     let symKind = if q.typ.kind == tyStatic: skConst else: skType
     var s = newSym(symKind, q.name, getCurrOwner(), q.info)
diff --git a/compiler/semmagic.nim b/compiler/semmagic.nim
index 806b00db6..cd90782d1 100644
--- a/compiler/semmagic.nim
+++ b/compiler/semmagic.nim
@@ -24,7 +24,7 @@ proc semTypeOf(c: PContext; n: PNode): PNode =
   result = newNodeI(nkTypeOfExpr, n.info)
   let typExpr = semExprWithType(c, n, {efInTypeof})
   result.add typExpr
-  result.typ = makeTypeDesc(c, typExpr.typ.skipTypes({tyTypeDesc, tyIter}))
+  result.typ = makeTypeDesc(c, typExpr.typ.skipTypes({tyTypeDesc}))
 
 type
   SemAsgnMode = enum asgnNormal, noOverloadedSubscript, noOverloadedAsgn
diff --git a/compiler/sigmatch.nim b/compiler/sigmatch.nim
index 44807dae2..15171874f 100644
--- a/compiler/sigmatch.nim
+++ b/compiler/sigmatch.nim
@@ -549,8 +549,6 @@ proc procTypeRel(c: var TCandidate, f, a: PType): TTypeRelation =
 
   of tyNil:
     result = f.allowsNil
-  of tyIter:
-    if tfIterator in f.flags: result = typeRel(c, f.base, a.base)
   else: discard
 
 proc typeRangeRel(f, a: PType): TTypeRelation {.noinline.} =
@@ -1223,13 +1221,6 @@ proc typeRel(c: var TCandidate, f, aOrig: PType, doBind = true): TTypeRelation =
       else:
         result = isNone
 
-  of tyIter:
-    if a.kind == tyIter or
-      (a.kind == tyProc and tfIterator in a.flags):
-      result = typeRel(c, f.base, a.base)
-    else:
-      result = isNone
-
   of tyStmt:
     if aOrig != nil and tfOldSchoolExprStmt notin f.flags:
       put(c, f, aOrig)
@@ -1587,8 +1578,9 @@ proc prepareOperand(c: PContext; formal: PType; a: PNode): PNode =
   elif a.typ.isNil:
     # XXX This is unsound! 'formal' can differ from overloaded routine to
     # overloaded routine!
-    let flags = if formal.kind == tyIter: {efDetermineType, efWantIterator}
-                else: {efDetermineType, efAllowStmt}
+    let flags = {efDetermineType, efAllowStmt}
+                #if formal.kind == tyIter: {efDetermineType, efWantIterator}
+                #else: {efDetermineType, efAllowStmt}
                 #elif formal.kind == tyStmt: {efDetermineType, efWantStmt}
                 #else: {efDetermineType}
     result = c.semOperand(c, a, flags)
diff --git a/compiler/types.nim b/compiler/types.nim
index 4e60e0121..d7651aad2 100644
--- a/compiler/types.nim
+++ b/compiler/types.nim
@@ -572,7 +572,7 @@ proc typeToString(typ: PType, prefer: TPreferedDesc = preferName): string =
       addSep(prag)
       add(prag, "locks: " & $t.lockLevel)
     if len(prag) != 0: add(result, "{." & prag & ".}")
-  of tyVarargs, tyIter:
+  of tyVarargs:
     result = typeToStr[t.kind] % typeToString(t.sons[0])
   else:
     result = typeToStr[t.kind]
@@ -965,7 +965,7 @@ proc sameTypeAux(x, y: PType, c: var TSameTypeClosure): bool =
       result = a.sym.position == b.sym.position
   of tyGenericInvocation, tyGenericBody, tySequence,
      tyOpenArray, tySet, tyRef, tyPtr, tyVar, tyArrayConstr,
-     tyArray, tyProc, tyConst, tyMutable, tyVarargs, tyIter,
+     tyArray, tyProc, tyConst, tyMutable, tyVarargs,
      tyOrdinal, tyTypeClasses, tyFieldAccessor:
     cycleCheck()
     if a.kind == tyUserTypeClass and a.n != nil: return a.n == b.n
@@ -980,6 +980,7 @@ proc sameTypeAux(x, y: PType, c: var TSameTypeClosure): bool =
         sameValue(a.n.sons[1], b.n.sons[1])
   of tyGenericInst: discard
   of tyNone: result = false
+  of tyUnused: internalError("sameFlags")
 
 proc sameBackendType*(x, y: PType): bool =
   var c = initSameTypeClosure()
@@ -1143,7 +1144,7 @@ proc typeAllowedAux(marker: var IntSet, typ: PType, kind: TSymKind,
     else: result = typeAllowedAux(marker, t.lastSon, skVar, flags+{taHeap})
   of tyPtr:
     result = typeAllowedAux(marker, t.lastSon, skVar, flags+{taHeap})
-  of tyArrayConstr, tySet, tyConst, tyMutable, tyIter:
+  of tyArrayConstr, tySet, tyConst, tyMutable:
     for i in countup(0, sonsLen(t) - 1):
       result = typeAllowedAux(marker, t.sons[i], kind, flags)
       if result != nil: break
@@ -1160,6 +1161,7 @@ proc typeAllowedAux(marker: var IntSet, typ: PType, kind: TSymKind,
     # for now same as error node; we say it's a valid type as it should
     # prevent cascading errors:
     result = nil
+  of tyUnused: internalError("typeAllowedAux")
 
 proc typeAllowed*(t: PType, kind: TSymKind): PType =
   # returns 'nil' on success and otherwise the part of the type that is
@@ -1311,7 +1313,7 @@ proc computeSizeAux(typ: PType, a: var BiggestInt): BiggestInt =
     if result < 0: return
     if a < maxAlign: a = maxAlign
     result = align(result, a)
-  of tyGenericInst, tyDistinct, tyGenericBody, tyMutable, tyConst, tyIter:
+  of tyGenericInst, tyDistinct, tyGenericBody, tyMutable, tyConst:
     result = computeSizeAux(lastSon(typ), a)
   of tyTypeDesc:
     result = computeSizeAux(typ.base, a)
diff --git a/compiler/vmdeps.nim b/compiler/vmdeps.nim
index b40ca1058..61f56092c 100644
--- a/compiler/vmdeps.nim
+++ b/compiler/vmdeps.nim
@@ -270,7 +270,6 @@ proc mapTypeToAstX(t: PType; info: TLineInfo;
   of tyConst: result = mapTypeToBracket("const", mNone, t, info)
   of tyMutable: result = mapTypeToBracket("mutable", mNone, t, info)
   of tyVarargs: result = mapTypeToBracket("varargs", mVarargs, t, info)
-  of tyIter: result = mapTypeToBracket("iter", mNone, t, info)
   of tyProxy: result = atomicType("error", mNone)
   of tyBuiltInTypeClass:
     result = mapTypeToBracket("builtinTypeClass", mNone, t, info)
@@ -292,6 +291,7 @@ proc mapTypeToAstX(t: PType; info: TLineInfo;
       result.add atomicType("static", mNone)
       if t.n != nil:
         result.add t.n.copyTree
+  of tyUnused: internalError("mapTypeToAstX")
 
 proc opMapTypeToAst*(t: PType; info: TLineInfo): PNode =
   result = mapTypeToAstX(t, info, false, true)
diff --git a/contributors.txt b/contributors.txt
deleted file mode 100644
index d54ec844a..000000000
--- a/contributors.txt
+++ /dev/null
@@ -1,12 +0,0 @@
-Comex
-Eric Doughty-Papassideris
-Simon Hafner
-Keita Haga
-Grzegorz Adam Hankiewicz
-Philippe Lhoste
-Zahary Karadjov
-Mario Ray Mahardhika
-Alexander Mitchell-Robinson (Amrykid)
-Dominik Picheta
-Jonathan Plona
-Alexander Rødseth
diff --git a/contributing.rst b/doc/contributing.rst
index 31f04a5e0..31f04a5e0 100644
--- a/contributing.rst
+++ b/doc/contributing.rst
diff --git a/doc/docs.txt b/doc/docs.rst
index 4484784ae..4484784ae 100644
--- a/doc/docs.txt
+++ b/doc/docs.rst
diff --git a/docstyle.rst b/doc/docstyle.rst
index d789b1df9..d789b1df9 100644
--- a/docstyle.rst
+++ b/doc/docstyle.rst
diff --git a/doc/gc.rst b/doc/gc.rst
index 1c8cb9122..bb0088617 100644
--- a/doc/gc.rst
+++ b/doc/gc.rst
@@ -19,8 +19,10 @@ This document describes how the GC works and how to tune it for
 
 The basic algorithm is *Deferred Reference Counting* with cycle detection.
 References on the stack are not counted for better performance (and easier C
-code generation). The GC **never** scans the whole heap but it may scan the
-delta-subgraph of the heap that changed since its last run.
+code generation). Cycle detection is currently done by a simple mark&sweep
+GC that has to scan the full (thread local heap). ``--gc:v2`` replaces this
+with an incremental mark and sweep. That it is not production ready yet,
+however.
 
 
 The GC is only triggered in a memory allocation operation. It is not triggered
@@ -34,17 +36,7 @@ Cycle collector
 ===============
 
 The cycle collector can be en-/disabled independently from the other parts of
-the GC with ``GC_enableMarkAndSweep`` and ``GC_disableMarkAndSweep``. The
-compiler analyses the types for their possibility to build cycles, but often
-it is necessary to help this analysis with the ``acyclic`` pragma (see
-`acyclic <manual.html#acyclic-pragma>`_ for further information).
-
-You can also use the ``acyclic`` pragma for data that is cyclic in reality and
-then break up the cycles explicitly with ``GC_addCycleRoot``. This can be a
-very valuable optimization; the Nim compiler itself relies on this
-optimization trick to improve performance. Note that ``GC_addCycleRoot`` is
-a quick operation; the root is only registered for the next run of the
-cycle collector.
+the GC with ``GC_enableMarkAndSweep`` and ``GC_disableMarkAndSweep``.
 
 
 Realtime support
@@ -55,19 +47,19 @@ defined via ``--define:useRealtimeGC`` (you can put this into your config
 file as well). With this switch the GC supports the following operations:
 
 .. code-block:: nim
-  proc GC_setMaxPause*(MaxPauseInUs: int)
+  proc GC_setMaxPause*(maxPauseInUs: int)
   proc GC_step*(us: int, strongAdvice = false, stackSize = -1)
 
-The unit of the parameters ``MaxPauseInUs`` and ``us`` is microseconds.
+The unit of the parameters ``maxPauseInUs`` and ``us`` is microseconds.
 
 These two procs are the two modus operandi of the realtime GC:
 
 (1) GC_SetMaxPause Mode
 
     You can call ``GC_SetMaxPause`` at program startup and then each triggered
-    GC run tries to not take longer than ``MaxPause`` time. However, it is
+    GC run tries to not take longer than ``maxPause`` time. However, it is
     possible (and common) that the work is nevertheless not evenly distributed
-    as each call to ``new`` can trigger the GC and thus take  ``MaxPause``
+    as each call to ``new`` can trigger the GC and thus take  ``maxPause``
     time.
 
 (2) GC_step Mode
@@ -86,8 +78,8 @@ These two procs are the two modus operandi of the realtime GC:
 These procs provide a "best effort" realtime guarantee; in particular the
 cycle collector is not aware of deadlines yet. Deactivate it to get more
 predictable realtime behaviour. Tests show that a 2ms max pause
-time will be met in almost all cases on modern CPUs unless the cycle collector
-is triggered.
+time will be met in almost all cases on modern CPUs (with the cycle collector
+disabled).
 
 
 Time measurement
diff --git a/doc/overview.txt b/doc/overview.rst
index 5b41752ae..e01520d7c 100644
--- a/doc/overview.txt
+++ b/doc/overview.rst
@@ -5,5 +5,5 @@ Nim Documentation Overview
 :Author: Andreas Rumpf
 :Version: |nimversion|
 
-.. include:: ../doc/docs.txt
+.. include:: docs.rst
 
diff --git a/install_nimble.nims b/install_nimble.nims
index 05024c046..6e929f499 100644
--- a/install_nimble.nims
+++ b/install_nimble.nims
@@ -3,6 +3,8 @@ import ospaths
 
 mode = ScriptMode.Verbose
 
+echo "This script is deprecated. Use 'koch nimble' instead."
+
 var id = 0
 while dirExists("nimble" & $id):
   inc id
@@ -20,4 +22,4 @@ try:
   mvFile "nimble" & $id & "/src/nimble".toExe, "bin/nimble".toExe
 except OSError:
   cpFile "nimble" & $id & "/src/nimble".toExe, "bin/nimble".toExe
-  
+
diff --git a/install_tools.nims b/install_tools.nims
index e211ff491..f5f320f78 100644
--- a/install_tools.nims
+++ b/install_tools.nims
@@ -3,6 +3,8 @@ import ospaths
 
 mode = ScriptMode.Verbose
 
+echo "This script is deprecated. Use 'koch tools' instead."
+
 if not dirExists"dist/nimble":
   echo "[Error] This script only works for the tarball."
 else:
@@ -11,8 +13,8 @@ else:
       " dist/nimble/src/nimble.nim"
 
   let nimsugExe = "./bin/nimsuggest".toExe
-  selfExec "c --noNimblePath -p:compiler -o:" & nimsugExe &
+  selfExec "c --noNimblePath -d:release -p:compiler -o:" & nimsugExe &
       " dist/nimsuggest/nimsuggest.nim"
 
   let nimgrepExe = "./bin/nimgrep".toExe
-  selfExec "c -o:./bin/nimgrep tools/nimgrep.nim"
+  selfExec "c -d:release -o:" & nimgrepExe & " tools/nimgrep.nim"
diff --git a/koch.nim b/koch.nim
index 74855a6b9..b50691d0d 100644
--- a/koch.nim
+++ b/koch.nim
@@ -49,6 +49,8 @@ Possible Commands:
   tests [options]          run the testsuite
   temp options             creates a temporary compiler for testing
   winrelease               creates a release (for coredevs only)
+  nimble                   builds the Nimble tool
+  tools                    builds Nim related tools
 Boot options:
   -d:release               produce a release version of the compiler
   -d:tinyc                 include the Tiny C backend (not supported on Windows)
@@ -88,6 +90,9 @@ proc exec(cmd: string, errorcode: int = QuitFailure, additionalPath = "") =
   if execShellCmd(cmd) != 0: quit("FAILURE", errorcode)
   putEnv("PATH", prevPath)
 
+proc nimexec(cmd: string) =
+  exec findNim() & " " & cmd
+
 proc execCleanPath(cmd: string,
                    additionalPath = ""; errorcode: int = QuitFailure) =
   # simulate a poor man's virtual environment
@@ -144,10 +149,13 @@ const
   compileNimInst = "tools/niminst/niminst"
 
 proc csource(args: string) =
-  exec("$4 cc $1 -r $3 --var:version=$2 --var:mingw=none csource --main:compiler/nim.nim compiler/installer.ini $1" %
-       [args, VersionAsString, compileNimInst, findNim()])
+  nimexec(("cc $1 -r $3 --var:version=$2 --var:mingw=none csource " &
+           "--main:compiler/nim.nim compiler/installer.ini $1") %
+       [args, VersionAsString, compileNimInst])
 
 proc bundleNimbleSrc() =
+  ## bunldeNimbleSrc() bundles a specific Nimble commit with the tarball. We
+  ## always bundle the latest official release.
   if dirExists("dist/nimble/.git"):
     exec("git --git-dir dist/nimble/.git pull")
   else:
@@ -160,42 +168,77 @@ proc bundleNimbleExe() =
   bundleNimbleSrc()
   # now compile Nimble and copy it to $nim/bin for the installer.ini
   # to pick it up:
-  exec(findNim() & " c dist/nimble/src/nimble.nim")
+  nimexec("c dist/nimble/src/nimble.nim")
   copyExe("dist/nimble/src/nimble".exe, "bin/nimble".exe)
 
+proc buildNimble() =
+  ## buildNimble() builds Nimble for the building via "github". As such, we
+  ## choose the most recent commit of Nimble too.
+  var installDir = "dist/nimble"
+  if dirExists("dist/nimble/.git"):
+    exec("git --git-dir dist/nimble/.git pull")
+  else:
+    # if dist/nimble exist, but is not a git repo, don't mess with it:
+    if dirExists(installDir):
+      var id = 0
+      while dirExists("dist/nimble" & $id):
+        inc id
+      installDir = "dist/nimble" & $id
+    exec("git clone https://github.com/nim-lang/nimble.git " & installDir)
+  nimexec("c " & installDir / "src/nimble.nim")
+  copyExe(installDir / "src/nimble".exe, "bin/nimble".exe)
+
 proc bundleNimsuggest(buildExe: bool) =
   if dirExists("dist/nimsuggest/.git"):
     exec("git --git-dir dist/nimsuggest/.git pull")
   else:
     exec("git clone https://github.com/nim-lang/nimsuggest.git dist/nimsuggest")
   if buildExe:
-    exec(findNim() & " c --noNimblePath -p:compiler dist/nimsuggest/nimsuggest.nim")
+    nimexec("c --noNimblePath -d:release -p:compiler dist/nimsuggest/nimsuggest.nim")
     copyExe("dist/nimsuggest/nimsuggest".exe, "bin/nimsuggest".exe)
+    removeFile("dist/nimsuggest/nimsuggest".exe)
 
 proc bundleFinishExe() =
-  exec(findNim() & " c finish.nim")
+  nimexec("c tools/finish.nim")
+  copyExe("tools/finish".exe, "finish".exe)
+  removeFile("tools/finish".exe)
 
 proc zip(args: string) =
   bundleNimbleSrc()
   bundleNimsuggest(false)
   bundleFinishExe()
-  exec("$3 cc -r $2 --var:version=$1 --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini" %
-       [VersionAsString, compileNimInst, findNim()])
+  nimexec("cc -r $2 --var:version=$1 --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini" %
+       [VersionAsString, compileNimInst])
   exec("$# --var:version=$# --var:mingw=none --main:compiler/nim.nim zip compiler/installer.ini" %
        ["tools/niminst/niminst".exe, VersionAsString])
 
 proc xz(args: string) =
   bundleNimbleSrc()
   bundleNimsuggest(false)
-  exec("$3 cc -r $2 --var:version=$1 --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini" %
-       [VersionAsString, compileNimInst, findNim()])
+  nimexec("cc -r $2 --var:version=$1 --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini" %
+       [VersionAsString, compileNimInst])
   exec("$# --var:version=$# --var:mingw=none --main:compiler/nim.nim xz compiler/installer.ini" %
        ["tools" / "niminst" / "niminst".exe, VersionAsString])
 
 proc buildTool(toolname, args: string) =
-  exec("$# cc $# $#" % [findNim(), args, toolname])
+  nimexec("cc $# $#" % [args, toolname])
   copyFile(dest="bin"/ splitFile(toolname).name.exe, source=toolname.exe)
 
+proc buildTools() =
+  if not dirExists"dist/nimble":
+    echo "[Error] 'koch tools' only works for the tarball."
+  else:
+    let nimbleExe = "bin/nimble".exe
+    nimexec "c --noNimblePath -p:compiler -o:" & nimbleExe &
+        " dist/nimble/src/nimble.nim"
+
+    let nimsugExe = "bin/nimsuggest".exe
+    nimexec "c --noNimblePath -p:compiler -d:release -o:" & nimsugExe &
+        " dist/nimsuggest/nimsuggest.nim"
+
+    let nimgrepExe = "bin/nimgrep".exe
+    nimexec "c -o:" & nimgrepExe & " tools/nimgrep.nim"
+
 proc nsis(args: string) =
   bundleNimbleExe()
   bundleNimsuggest(true)
@@ -210,21 +253,21 @@ proc nsis(args: string) =
         " nsis compiler/installer.ini") % [VersionAsString, $(sizeof(pointer)*8)])
 
 proc geninstall(args="") =
-  exec("$# cc -r $# --var:version=$# --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini $#" %
-       [findNim(), compileNimInst, VersionAsString, args])
+  nimexec("cc -r $# --var:version=$# --var:mingw=none --main:compiler/nim.nim scripts compiler/installer.ini $#" %
+       [compileNimInst, VersionAsString, args])
 
 proc install(args: string) =
   geninstall()
   exec("sh ./install.sh $#" % args)
 
 proc web(args: string) =
-  exec("$# js tools/dochack/dochack.nim" % findNim())
-  exec("$# cc -r tools/nimweb.nim $# web/website.ini --putenv:nimversion=$#" %
-       [findNim(), args, VersionAsString])
+  nimexec("js tools/dochack/dochack.nim")
+  nimexec("cc -r tools/nimweb.nim $# web/website.ini --putenv:nimversion=$#" %
+       [args, VersionAsString])
 
 proc website(args: string) =
-  exec("$# cc -r tools/nimweb.nim $# --website web/website.ini --putenv:nimversion=$#" %
-       [findNim(), args, VersionAsString])
+  nimexec("cc -r tools/nimweb.nim $# --website web/website.ini --putenv:nimversion=$#" %
+       [args, VersionAsString])
 
 proc pdf(args="") =
   exec("$# cc -r tools/nimweb.nim $# --pdf web/website.ini --putenv:nimversion=$#" %
@@ -314,7 +357,6 @@ proc removePattern(pattern: string) =
     removeFile(f)
 
 proc clean(args: string) =
-  if existsFile("koch.dat"): removeFile("koch.dat")
   removePattern("web/*.html")
   removePattern("doc/*.html")
   cleanAux(getCurrentDir())
@@ -335,11 +377,10 @@ template `|`(a, b): string = (if a.len > 0: a else: b)
 proc tests(args: string) =
   # we compile the tester with taintMode:on to have a basic
   # taint mode test :-)
-  let nimexe = findNim()
-  exec nimexe & " cc --taintMode:on tests/testament/tester"
+  nimexec "cc --taintMode:on tests/testament/tester"
   # Since tests take a long time (on my machine), and we want to defy Murhpys
   # law - lets make sure the compiler really is freshly compiled!
-  exec nimexe & " c --lib:lib -d:release --opt:speed compiler/nim.nim"
+  nimexec "c --lib:lib -d:release --opt:speed compiler/nim.nim"
   let tester = quoteShell(getCurrentDir() / "tests/testament/tester".exe)
   let success = tryExec tester & " " & (args|"all")
   if not existsEnv("TRAVIS") and not existsEnv("APPVEYOR"):
@@ -369,6 +410,7 @@ of cmdArgument:
   of "boot": boot(op.cmdLineRest)
   of "clean": clean(op.cmdLineRest)
   of "web": web(op.cmdLineRest)
+  of "doc", "docs": web("--onlyDocs " & op.cmdLineRest)
   of "json2": web("--json2 " & op.cmdLineRest)
   of "website": website(op.cmdLineRest & " --googleAnalytics:UA-48159761-1")
   of "web0":
@@ -386,5 +428,7 @@ of cmdArgument:
   of "test", "tests": tests(op.cmdLineRest)
   of "temp": temp(op.cmdLineRest)
   of "winrelease": winRelease()
+  of "nimble": buildNimble()
+  of "tools": buildTools()
   else: showHelp()
 of cmdEnd: showHelp()
diff --git a/lib/core/macros.nim b/lib/core/macros.nim
index 19452b4a8..292e8dd3c 100644
--- a/lib/core/macros.nim
+++ b/lib/core/macros.nim
@@ -92,7 +92,7 @@ type
     ntyUInt, ntyUInt8, ntyUInt16, ntyUInt32, ntyUInt64,
     ntyBigNum,
     ntyConst, ntyMutable, ntyVarargs,
-    ntyIter,
+    ntyUnused,
     ntyError,
     ntyBuiltinTypeClass, ntyConcept, ntyConceptInst, ntyComposite,
     ntyAnd, ntyOr, ntyNot
diff --git a/lib/pure/collections/sequtils.nim b/lib/pure/collections/sequtils.nim
index f458b7636..45a148fbf 100644
--- a/lib/pure/collections/sequtils.nim
+++ b/lib/pure/collections/sequtils.nim
@@ -228,7 +228,7 @@ proc apply*[T](data: var seq[T], op: proc (x: var T) {.closure.})
   ##   var a = @["1", "2", "3", "4"]
   ##   echo repr(a)
   ##   # --> ["1", "2", "3", "4"]
-  ##   map(a, proc(x: var string) = x &= "42")
+  ##   apply(a, proc(x: var string) = x &= "42")
   ##   echo repr(a)
   ##   # --> ["142", "242", "342", "442"]
   ##
@@ -247,7 +247,7 @@ proc apply*[T](data: var seq[T], op: proc (x: T): T {.closure.})
   ##   var a = @["1", "2", "3", "4"]
   ##   echo repr(a)
   ##   # --> ["1", "2", "3", "4"]
-  ##   map(a, proc(x: string): string = x & "42")
+  ##   apply(a, proc(x: string): string = x & "42")
   ##   echo repr(a)
   ##   # --> ["142", "242", "342", "442"]
   ##
diff --git a/lib/pure/os.nim b/lib/pure/os.nim
index cdbe170cc..001d3d250 100644
--- a/lib/pure/os.nim
+++ b/lib/pure/os.nim
@@ -50,6 +50,8 @@ proc c_getenv(env: cstring): cstring {.
   importc: "getenv", header: "<stdlib.h>".}
 proc c_putenv(env: cstring): cint {.
   importc: "putenv", header: "<stdlib.h>".}
+proc c_free(p: pointer) {.
+  importc: "free", header: "<stdlib.h>".}
 
 var errno {.importc, header: "<errno.h>".}: cint
 
@@ -303,24 +305,47 @@ proc fileNewer*(a, b: string): bool {.rtl, extern: "nos$1".} =
 
 proc getCurrentDir*(): string {.rtl, extern: "nos$1", tags: [].} =
   ## Returns the `current working directory`:idx:.
-  const bufsize = 512 # should be enough
   when defined(windows):
+    var bufsize = MAX_PATH.int32
     when useWinUnicode:
       var res = newWideCString("", bufsize)
-      var L = getCurrentDirectoryW(bufsize, res)
-      if L == 0'i32: raiseOSError(osLastError())
-      result = res$L
+      while true:
+        var L = getCurrentDirectoryW(bufsize, res)
+        if L == 0'i32:
+          raiseOSError(osLastError())
+        elif L > bufsize:
+          res = newWideCString("", L)
+          bufsize = L
+        else:
+          result = res$L
+          break
     else:
       result = newString(bufsize)
-      var L = getCurrentDirectoryA(bufsize, result)
-      if L == 0'i32: raiseOSError(osLastError())
-      setLen(result, L)
+      while true:
+        var L = getCurrentDirectoryA(bufsize, result)
+        if L == 0'i32:
+          raiseOSError(osLastError())
+        elif L > bufsize:
+          result = newString(L)
+          bufsize = L
+        else:
+          setLen(result, L)
+          break
   else:
+    var bufsize = 1024 # should be enough
     result = newString(bufsize)
-    if getcwd(result, bufsize) != nil:
-      setLen(result, c_strlen(result))
-    else:
-      raiseOSError(osLastError())
+    while true:
+      if getcwd(result, bufsize) != nil:
+        setLen(result, c_strlen(result))
+        break
+      else:
+        let err = osLastError()
+        if err.int32 == ERANGE:
+          bufsize = bufsize shl 1
+          doAssert(bufsize >= 0)
+          result = newString(bufsize)
+        else:
+          raiseOSError(osLastError())
 
 proc setCurrentDir*(newDir: string) {.inline, tags: [].} =
   ## Sets the `current working directory`:idx:; `OSError` is raised if
@@ -336,28 +361,45 @@ proc setCurrentDir*(newDir: string) {.inline, tags: [].} =
 
 proc expandFilename*(filename: string): string {.rtl, extern: "nos$1",
   tags: [ReadDirEffect].} =
-  ## Returns the full (`absolute`:idx:) path of the file `filename`, raises OSError in case of an error.
+  ## Returns the full (`absolute`:idx:) path of the file `filename`,
+  ## raises OSError in case of an error.
   when defined(windows):
-    const bufsize = 3072'i32
+    var bufsize = MAX_PATH.int32
     when useWinUnicode:
-      var unused: WideCString
-      var res = newWideCString("", bufsize div 2)
-      var L = getFullPathNameW(newWideCString(filename), bufsize, res, unused)
-      if L <= 0'i32 or L >= bufsize:
-        raiseOSError(osLastError())
-      result = res$L
+      var unused: WideCString = nil
+      var res = newWideCString("", bufsize)
+      while true:
+        var L = getFullPathNameW(newWideCString(filename), bufsize, res, unused)
+        if L == 0'i32:
+          raiseOSError(osLastError())
+        elif L > bufsize:
+          res = newWideCString("", L)
+          bufsize = L
+        else:
+          result = res$L
+          break
     else:
-      var unused: cstring
+      var unused: cstring = nil
       result = newString(bufsize)
-      var L = getFullPathNameA(filename, bufsize, result, unused)
-      if L <= 0'i32 or L >= bufsize: raiseOSError(osLastError())
-      setLen(result, L)
+      while true:
+        var L = getFullPathNameA(filename, bufsize, result, unused)
+        if L == 0'i32:
+          raiseOSError(osLastError())
+        elif L > bufsize:
+          result = newString(L)
+          bufsize = L
+        else:
+          setLen(result, L)
+          break
   else:
-    # careful, realpath needs to take an allocated buffer according to Posix:
-    result = newString(pathMax)
-    var r = realpath(filename, result)
-    if r.isNil: raiseOSError(osLastError())
-    setLen(result, c_strlen(result))
+    # according to Posix we don't need to allocate space for result pathname.
+    # But we need to free return value with free(3).
+    var r = realpath(filename, nil)
+    if r.isNil:
+      raiseOSError(osLastError())
+    else:
+      result = $r
+      c_free(cast[pointer](r))
 
 when defined(Windows):
   proc openHandle(path: string, followSymlink=true): Handle =
@@ -1382,6 +1424,35 @@ when declared(paramCount) or defined(nimdoc):
     for i in 1..paramCount():
       result.add(paramStr(i))
 
+when defined(freebsd):
+  proc sysctl(name: ptr cint, namelen: cuint, oldp: pointer, oldplen: ptr csize,
+              newp: pointer, newplen: csize): cint
+       {.importc: "sysctl",header: """#include <sys/types.h>
+                                      #include <sys/sysctl.h>"""}
+  const
+    CTL_KERN = 1
+    KERN_PROC = 14
+    KERN_PROC_PATHNAME = 12
+    MAX_PATH = 1024
+
+  proc getApplFreebsd(): string =
+    var pathLength = csize(MAX_PATH)
+    result = newString(pathLength)
+    var req = [CTL_KERN.cint, KERN_PROC.cint, KERN_PROC_PATHNAME.cint, -1.cint]
+    while true:
+      let res = sysctl(addr req[0], 4, cast[pointer](addr result[0]),
+                       addr pathLength, nil, 0)
+      if res < 0:
+        let err = osLastError()
+        if err.int32 == ENOMEM:
+          result = newString(pathLength)
+        else:
+          result.setLen(0) # error!
+          break
+      else:
+        result.setLen(pathLength)
+        break
+
 when defined(linux) or defined(solaris) or defined(bsd) or defined(aix):
   proc getApplAux(procPath: string): string =
     result = newString(256)
@@ -1426,16 +1497,34 @@ proc getAppFilename*(): string {.rtl, extern: "nos$1", tags: [ReadIOEffect].} =
   # Solaris:
   # /proc/<pid>/object/a.out (filename only)
   # /proc/<pid>/path/a.out (complete pathname)
-  # FreeBSD: /proc/<pid>/file
   when defined(windows):
+    var bufsize = int32(MAX_PATH)
     when useWinUnicode:
-      var buf = newWideCString("", 256)
-      var len = getModuleFileNameW(0, buf, 256)
-      result = buf$len
+      var buf = newWideCString("", bufsize)
+      while true:
+        var L = getModuleFileNameW(0, buf, bufsize)
+        if L == 0'i32:
+          result = "" # error!
+          break
+        elif L > bufsize:
+          buf = newWideCString("", L)
+          bufsize = L
+        else:
+          result = buf$L
+          break
     else:
-      result = newString(256)
-      var len = getModuleFileNameA(0, result, 256)
-      setlen(result, int(len))
+      result = newString(bufsize)
+      while true:
+        var L = getModuleFileNameA(0, result, bufsize)
+        if L == 0'i32:
+          result = "" # error!
+          break
+        elif L > bufsize:
+          result = newString(L)
+          bufsize = L
+        else:
+          setLen(result, L)
+          break
   elif defined(macosx):
     var size: cuint32
     getExecPath1(nil, size)
@@ -1450,7 +1539,7 @@ proc getAppFilename*(): string {.rtl, extern: "nos$1", tags: [ReadIOEffect].} =
     elif defined(solaris):
       result = getApplAux("/proc/" & $getpid() & "/path/a.out")
     elif defined(freebsd):
-      result = getApplAux("/proc/" & $getpid() & "/file")
+      result = getApplFreebsd()
     # little heuristic that may work on other POSIX-like systems:
     if result.len == 0:
       result = getApplHeuristic()
diff --git a/lib/pure/unittest.nim b/lib/pure/unittest.nim
index 0fc2e441e..12553e3da 100644
--- a/lib/pure/unittest.nim
+++ b/lib/pure/unittest.nim
@@ -11,11 +11,21 @@
 ##
 ## This module implements boilerplate to make unit testing easy.
 ##
+## The test status and name is printed after any output or traceback.
+##
 ## Example:
 ##
 ## .. code:: nim
 ##
 ##   suite "description for this stuff":
+##     echo "suite setup: run once before the tests"
+##
+##     setup:
+##       echo "run before each test"
+##
+##     teardown:
+##       echo "run after each test":
+##
 ##     test "essential truths":
 ##       # give up and stop if this fails
 ##       require(true)
@@ -30,6 +40,13 @@
 ##       let v = @[1, 2, 3]  # you can do initialization here
 ##       expect(IndexError):
 ##         discard v[4]
+##
+##     echo "suite teardown: run once after the tests"
+##
+##
+## Tests can be nested, however failure of a nested test will not mark the
+## parent test as failed. Setup and teardown are inherited. Setup can be
+## overridden locally.
 
 import
   macros
@@ -226,10 +243,11 @@ template fail* =
   checkpoints = @[]
 
 template skip* =
-  ## Makes test to be skipped. Should be used directly
+  ## Mark the test as skipped. Should be used directly
   ## in case when it is not possible to perform test
   ## for reasons depending on outer environment,
   ## or certain application logic conditions or configurations.
+  ## The test code is still executed.
   ##
   ## .. code-block:: nim
   ##
@@ -250,12 +268,12 @@ macro check*(conditions: untyped): untyped =
   ##
   ##  import strutils
   ##
-  ##  check("AKB48".toLower() == "akb48")
+  ##  check("AKB48".toLowerAscii() == "akb48")
   ##
   ##  let teams = {'A', 'K', 'B', '4', '8'}
   ##
   ##  check:
-  ##    "AKB48".toLower() == "akb48"
+  ##    "AKB48".toLowerAscii() == "akb48"
   ##    'C' in teams
   let checked = callsite()[1]
   var
diff --git a/finish.nim b/tools/finish.nim
index 18216cfb2..8b9acfc56 100644
--- a/finish.nim
+++ b/tools/finish.nim
@@ -69,10 +69,10 @@ when defined(windows):
     if askBool("Would like to add Nim-" & NimVersion &
                " to your start menu? (y/n) "):
       createDir(dest)
-      createShortcut(getCurrentDir() / "start.bat", dest / "Nim",
+      createShortcut(getCurrentDir() / "tools" / "start.bat", dest / "Nim",
                      getCurrentDir() / r"icons\nim.ico")
       if fileExists("doc/overview.html"):
-        createShortcut(getCurrentDir() / "doc" / "overview.html",
+        createShortcut(getCurrentDir() / "doc" / "html" / "overview.html",
                        dest / "Overview")
       if dirExists(r"dist\aporia-0.4.0"):
         createShortcut(getCurrentDir() / r"dist\aporia-0.4.0\bin\aporia.exe",
diff --git a/tools/niminst/niminst.nim b/tools/niminst/niminst.nim
index 66ea52447..e0b8ad9b3 100644
--- a/tools/niminst/niminst.nim
+++ b/tools/niminst/niminst.nim
@@ -313,7 +313,7 @@ proc parseIniFile(c: var ConfigData) =
       of cfgSectionStart:
         section = normalize(k.section)
       of cfgKeyValuePair:
-        var v = `%`(k.value, c.vars, {useEnvironment})
+        var v = `%`(k.value, c.vars, {useEnvironment, useEmpty})
         c.vars[k.key] = v
 
         case section
diff --git a/tools/nimweb.nim b/tools/nimweb.nim
index c3bba3f0a..9a21a0fb5 100644
--- a/tools/nimweb.nim
+++ b/tools/nimweb.nim
@@ -29,7 +29,7 @@ type
   TRssItem = object
     year, month, day, title, url, content: string
   TAction = enum
-    actAll, actOnlyWebsite, actPdf, actJson2
+    actAll, actOnlyWebsite, actPdf, actJson2, actOnlyDocs
 
   Sponsor = object
     logo: string
@@ -72,7 +72,7 @@ include "website.tmpl"
 # ------------------------- configuration file -------------------------------
 
 const
-  version = "0.7"
+  version = "0.8"
   usage = "nimweb - Nim Website Generator Version " & version & """
 
   (c) 2015 Andreas Rumpf
@@ -85,6 +85,8 @@ Options:
   -v, --version       shows the version
   --website           only build the website, not the full documentation
   --pdf               build the PDF version of the documentation
+  --json2             build JSON of the documentation
+  --onlyDocs          build only the documentation
 Compile_options:
   will be passed to the Nim compiler
 """
@@ -157,6 +159,7 @@ proc parseCmdLine(c: var TConfigData) =
       of "website": action = actOnlyWebsite
       of "pdf": action = actPdf
       of "json2": action = actJson2
+      of "onlydocs": action = actOnlyDocs
       of "googleanalytics":
         c.gaId = val
         c.nimArgs.add("--doc.googleAnalytics:" & val & " ")
@@ -315,6 +318,7 @@ proc buildDoc(c: var TConfigData, destPath: string) =
   exec(findNim() & " buildIndex -o:$1/theindex.html $1" % [destPath])
 
 proc buildPdfDoc(c: var TConfigData, destPath: string) =
+  createDir(destPath)
   if os.execShellCmd("pdflatex -version") != 0:
     echo "pdflatex not found; no PDF documentation generated"
   else:
@@ -507,8 +511,14 @@ proc main(c: var TConfigData) =
   buildAddDoc(c, docup)
   buildDocSamples(c, docup)
   buildDoc(c, docup)
-  buildDocSamples(c, "doc")
-  buildDoc(c, "doc")
+  createDir("doc/html")
+  buildDocSamples(c, "doc/html")
+  buildDoc(c, "doc/html")
+
+proc onlyDocs(c: var TConfigData) =
+  createDir("doc/html")
+  buildDocSamples(c, "doc/html")
+  buildDoc(c, "doc/html")
 
 proc json2(c: var TConfigData) =
   const destPath = "web/json2"
@@ -529,6 +539,7 @@ parseCmdLine(c)
 parseIniFile(c)
 case action
 of actOnlyWebsite: buildWebsite(c)
-of actPdf: buildPdfDoc(c, "doc")
+of actPdf: buildPdfDoc(c, "doc/pdf")
+of actOnlyDocs: onlyDocs(c)
 of actAll: main(c)
 of actJson2: json2(c)
diff --git a/tools/noprefix.nim b/tools/noprefix.nim
deleted file mode 100644
index d16c2b520..000000000
--- a/tools/noprefix.nim
+++ /dev/null
@@ -1,32 +0,0 @@
-# strip those silly GTK/ATK prefixes...
-
-import
-  expandimportc, os
-
-const
-  filelist = [
-    ("sdl/sdl", "sdl"),
-    ("sdl/sdl_net", "sdl"),
-    ("sdl/sdl_gfx", "sdl"),
-    ("sdl/sdl_image", "sdl"),
-    ("sdl/sdl_mixer_nosmpeg", "sdl"),
-    ("sdl/sdl_mixer", "sdl"),
-    ("sdl/sdl_ttf", "sdl"),
-    ("sdl/smpeg", "sdl"),
-
-    ("libcurl", "curl"),
-    ("mysql", "mysql"),
-    ("postgres", ""),
-    ("sqlite3", "sqlite3"),
-
-    ("pcre/pcre", "pcre")
-  ]
-
-proc createDirs =
-  createDir("lib/newwrap/sdl")
-  createDir("lib/newwrap/pcre")
-
-for filename, prefix in items(filelist):
-  var f = addFileExt(filename, "nim")
-  main("lib/wrappers" / f, "lib/newwrap" / f, prefix)
-
diff --git a/start.bat b/tools/start.bat
index 685932c47..a4475fac7 100644
--- a/start.bat
+++ b/tools/start.bat
@@ -1,6 +1,8 @@
 @echo off

 REM COLOR 0A

-SET NIMPATH=%~dp0

+SET NIMPATH=%~dp0\..

 SET PATH=%NIMPATH%\bin;%NIMPATH%\dist\mingw\bin;%PATH%

-cmd

+cd %NIMPATH%

+cmd 

+

 

diff --git a/web/download.rst b/web/download.rst
index c9aaea9fc..b9874f1b1 100644
--- a/web/download.rst
+++ b/web/download.rst
@@ -12,9 +12,9 @@ Zips
 We now encourage you to install via the provided zipfiles:
 
 * | 32 bit: `nim-0.15.2_x32.zip <download/nim-0.15.2_x32.zip>`_
-  | SHA-256
+  | SHA-256  0f1bfb74751f55e090140a361c08e9f39f1dd03f1f0c070c061f2d5049ab9f96
 * | 64 bit: `nim-0.15.2_x64.zip <download/nim-0.15.2_x64.zip>`_
-  | SHA-256
+  | SHA-256  ceea42de6ebcd41032ee51f04526dc4cf2cbb0958ca6ad2321cf21944e05f553
 
 Unzip these where you want and optionally run ``finish.exe`` to
 detect your MingW environment.
@@ -28,9 +28,9 @@ so will unlikely to be provided further in the future. These
 installers have everything you need to use Nim, including a C compiler.
 
 * | 32 bit: `nim-0.15.2_x32.exe <download/nim-0.15.2_x32.exe>`_
-  | SHA-256
+  | SHA-256  8d648295dbd59cb315c98926a1da9f1f68773a1a2ef3d9d4c91c59387167efa3
 * | 64 bit: `nim-0.15.2_x64.exe <download/nim-0.15.2_x64.exe>`_
-  | SHA-256
+  | SHA-256  8c7efc6571921c2d2e5e995f801d4229ea1de19fbdabdcba1628307bd4612392
 
 These installers also include Aporia, Nimble and other useful Nim tools to get
 you started with Nim development!
@@ -49,7 +49,7 @@ like systems.
 Firstly, download this archive:
 
 * | `nim-0.15.2.tar.xz (4.5MB) <download/nim-0.15.2.tar.xz>`_
-  | SHA-256
+  | SHA-256  905df2316262aa2cbacae067acf45fc05c2a71c8c6fde1f2a70c927ebafcfe8a
 
 Extract the archive. Then copy the extracted files into your chosen installation
 directory, ideally somewhere in your home directory.
diff --git a/web/news/e028_version_0_15_2.rst b/web/news/e028_version_0_15_2.rst
index 376fb4dde..601a26646 100644
--- a/web/news/e028_version_0_15_2.rst
+++ b/web/news/e028_version_0_15_2.rst
@@ -16,10 +16,17 @@ regressions of 0.15.0. For Windows we now provide zipfiles in addition to the
 NSIS based installer which proves to be hard to maintain and after all these
 months still has serious issues. So we encourage you download the .zip
 file instead of the .exe file! Unzip it somewhere, run ``finish.exe`` to
-detect your MingW installation, done.
+detect your MingW installation, done. ``finish.exe`` can also set your PATH
+environment variable.
 
-To see a full list of changes, take a look at the
-detailed changelog `below <#changelog>`_.
+
+Bugfixes
+--------
+
+The list below has been generated based on the commits in Nim's git
+repository. As such it lists only the issues which have been closed
+via a commit, for a full list see
+`this link on Github <https://github.com/nim-lang/Nim/issues?utf8=%E2%9C%93&q=is%3Aissue+closed%3A%222016-09-30+..+2016-10-23%22+>`_.
 
 
 - Fixed "`NimMain` not exported in DLL, but `NimMainInner` is"
diff --git a/web/website.ini b/web/website.ini
index 833122ecb..0d1be4b63 100644
--- a/web/website.ini
+++ b/web/website.ini
@@ -31,7 +31,7 @@ file: ticker.html
 [Documentation]
 doc: "endb;intern;apis;lib;manual.rst;tut1.rst;tut2.rst;nimc;overview;filters"
 doc: "tools;niminst;nimgrep;gc;estp;idetools;docgen;koch;backends.rst"
-doc: "nimfix.rst;nimsuggest.rst;nep1.rst;nims.rst"
+doc: "nimfix.rst;nimsuggest.rst;nep1.rst;nims.rst;contributing.rst"
 pdf: "manual.rst;lib.rst;tut1.rst;tut2.rst;nimc.rst;niminst.rst;gc.rst"
 srcdoc2: "system.nim;system/nimscript;pure/ospaths"
 srcdoc2: "core/macros;pure/marshal;core/typeinfo"