summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/ccgexprs.nim33
-rw-r--r--compiler/lexer.nim10
-rw-r--r--compiler/magicsys.nim15
-rw-r--r--compiler/msgs.nim22
-rw-r--r--compiler/nimconf.nim7
-rw-r--r--compiler/nimrod.ini1
-rw-r--r--compiler/options.nim1
-rw-r--r--compiler/parser.nim1
-rw-r--r--compiler/renderer.nim12
-rw-r--r--compiler/semcall.nim9
-rw-r--r--compiler/semexprs.nim3
-rw-r--r--compiler/semfold.nim7
-rw-r--r--compiler/semstmts.nim11
-rw-r--r--compiler/semtypes.nim2
-rw-r--r--compiler/service.nim35
-rw-r--r--compiler/sigmatch.nim12
-rw-r--r--compiler/types.nim3
-rw-r--r--compiler/vmdef.nim3
-rw-r--r--compiler/vmdeps.nim15
-rw-r--r--config/nimrod.cfg3
-rw-r--r--install.txt43
-rw-r--r--koch.nim1
-rw-r--r--lib/core/typeinfo.nim2
-rw-r--r--lib/packages/docutils/rstgen.nim4
-rw-r--r--lib/posix/posix.nim94
-rw-r--r--lib/pure/httpclient.nim67
-rw-r--r--lib/pure/os.nim17
-rw-r--r--lib/pure/strutils.nim12
-rw-r--r--lib/pure/xmltree.nim6
-rw-r--r--lib/system.nim24
-rw-r--r--lib/system/ansi_c.nim2
-rw-r--r--lib/system/gc.nim2
-rw-r--r--lib/system/gc_ms.nim2
-rw-r--r--lib/system/sysio.nim2
-rw-r--r--readme.md5
-rw-r--r--readme.txt5
-rw-r--r--tests/compile/tinheritref.nim27
-rw-r--r--tests/compile/tobjconstr2.nim14
-rw-r--r--tests/compile/tvarious.nim3
-rw-r--r--tests/reject/texprstmt.nim12
-rw-r--r--tests/reject/tinvalidborrow.nim17
-rw-r--r--tests/run/tvarious1.nim17
-rw-r--r--todo.txt1
-rw-r--r--tools/niminst/buildbat.tmpl8
-rw-r--r--tools/niminst/buildsh.tmpl5
-rw-r--r--tools/niminst/deinstall.tmpl6
-rw-r--r--tools/niminst/inno.tmpl6
-rw-r--r--tools/niminst/install.tmpl28
-rw-r--r--tools/niminst/niminst.nim41
49 files changed, 413 insertions, 265 deletions
diff --git a/compiler/ccgexprs.nim b/compiler/ccgexprs.nim
index 635756220..6b3906226 100644
--- a/compiler/ccgexprs.nim
+++ b/compiler/ccgexprs.nim
@@ -303,10 +303,11 @@ proc genAssignment(p: BProc, dest, src: TLoc, flags: TAssignmentFlags) =
       linefmt(p, cpsStmts, "$1 = $2;$n", rdLoc(dest), rdLoc(src))
   of tyObject:
     # XXX: check for subtyping?
-    if needsComplexAssignment(dest.t):
-      if asgnComplexity(dest.t.n) <= 4:
-        discard getTypeDesc(p.module, dest.t)
-        genOptAsgnObject(p, dest, src, flags, dest.t.n)
+    if needsComplexAssignment(ty):
+      if asgnComplexity(ty.n) <= 4:
+        discard getTypeDesc(p.module, ty)
+        internalAssert ty.n != nil
+        genOptAsgnObject(p, dest, src, flags, ty.n)
       else:
         genGenericAsgn(p, dest, src, flags)
     else:
@@ -465,10 +466,11 @@ proc unaryArithOverflow(p: BProc, e: PNode, d: var TLoc, m: TMagic) =
 proc binaryArith(p: BProc, e: PNode, d: var TLoc, op: TMagic) =
   const
     binArithTab: array[mAddF64..mXor, string] = [
-      "($1 + $2)",            # AddF64
-      "($1 - $2)",            # SubF64
-      "($1 * $2)",            # MulF64
-      "($1 / $2)",            # DivF64
+      "(($4)($1) + ($4)($2))", # AddF64
+      "(($4)($1) - ($4)($2))", # SubF64
+      "(($4)($1) * ($4)($2))", # MulF64
+      "(($4)($1) / ($4)($2))", # DivF64
+      
       "($4)((NU$3)($1) >> (NU$3)($2))", # ShrI
       "($4)((NU$3)($1) << (NU$3)($2))", # ShlI
       "($4)($1 & $2)",      # BitandI
@@ -641,14 +643,7 @@ proc genTupleElem(p: BProc, e: PNode, d: var TLoc) =
   case e.sons[1].kind
   of nkIntLit..nkUInt64Lit: i = int(e.sons[1].intVal)
   else: internalError(e.info, "genTupleElem")
-  when false:
-    if ty.n != nil:
-      var field = ty.n.sons[i].sym
-      if field == nil: InternalError(e.info, "genTupleElem")
-      if field.loc.r == nil: InternalError(e.info, "genTupleElem")
-      appf(r, ".$1", [field.loc.r])
-  else:
-    appf(r, ".Field$1", [toRope(i)])
+  appf(r, ".Field$1", [toRope(i)])
   putIntoDest(p, d, ty.sons[i], r)
 
 proc genRecordField(p: BProc, e: PNode, d: var TLoc) =
@@ -839,6 +834,7 @@ proc genAndOr(p: BProc, e: PNode, d: var TLoc, m: TMagic) =
 proc genEcho(p: BProc, n: PNode) =
   # this unusal way of implementing it ensures that e.g. ``echo("hallo", 45)``
   # is threadsafe.
+  discard lists.IncludeStr(p.module.headerFiles, "<stdio.h>")
   var args: PRope = nil
   var a: TLoc
   for i in countup(1, n.len-1):
@@ -1488,8 +1484,9 @@ proc binaryFloatArith(p: BProc, e: PNode, d: var TLoc, m: TMagic) =
     assert(e.sons[2].typ != nil)
     InitLocExpr(p, e.sons[1], a)
     InitLocExpr(p, e.sons[2], b)
-    putIntoDest(p, d, e.typ, rfmt(nil, "($2 $1 $3)",
-                                  toRope(opr[m]), rdLoc(a), rdLoc(b)))
+    putIntoDest(p, d, e.typ, rfmt(nil, "(($4)($2) $1 ($4)($3))",
+                                  toRope(opr[m]), rdLoc(a), rdLoc(b),
+                                  getSimpleTypeDesc(p.module, e[1].typ)))
     if optNanCheck in p.options:
       linefmt(p, cpsStmts, "#nanCheck($1);$n", rdLoc(d))
     if optInfCheck in p.options:
diff --git a/compiler/lexer.nim b/compiler/lexer.nim
index 1d34c59ab..82bfa0ad4 100644
--- a/compiler/lexer.nim
+++ b/compiler/lexer.nim
@@ -408,12 +408,12 @@ proc GetNumber(L: var TLexer): TToken =
         (result.tokType == tkFloat64Lit): 
       result.fnumber = parseFloat(result.literal)
       if result.tokType == tkIntLit: result.tokType = tkFloatLit
-    else: 
-      result.iNumber = ParseBiggestInt(result.literal)
-      if (result.iNumber < low(int32)) or (result.iNumber > high(int32)): 
-        if result.tokType == tkIntLit: 
+    else:
+      result.iNumber = parseBiggestInt(result.literal)
+      if (result.iNumber < low(int32)) or (result.iNumber > high(int32)):
+        if result.tokType == tkIntLit:
           result.tokType = tkInt64Lit
-        elif result.tokType != tkInt64Lit: 
+        elif result.tokType in {tkInt8Lit, tkInt16Lit}:
           lexMessage(L, errInvalidNumber, result.literal)
   except EInvalidValue:
     lexMessage(L, errInvalidNumber, result.literal)
diff --git a/compiler/magicsys.nim b/compiler/magicsys.nim
index 1972dec98..0c0b87222 100644
--- a/compiler/magicsys.nim
+++ b/compiler/magicsys.nim
@@ -74,7 +74,7 @@ proc getSysType(kind: TTypeKind): PType =
     of tyUInt64: result = sysTypeFromName("uint64")
     of tyFloat: result = sysTypeFromName("float")
     of tyFloat32: result = sysTypeFromName("float32")
-    of tyFloat64: result = sysTypeFromName("float64")
+    of tyFloat64: return sysTypeFromName("float64")
     of tyFloat128: result = sysTypeFromName("float128")
     of tyBool: result = sysTypeFromName("bool")
     of tyChar: result = sysTypeFromName("char")
@@ -115,11 +115,16 @@ proc getIntLitType*(literal: PNode): PType =
     result = copyType(ti, ti.owner, false)
     result.n = literal
 
+proc getFloatLitType*(literal: PNode): PType =
+  # for now we do not cache these:
+  result = newSysType(tyFloat, size=8)
+  result.n = literal
+
 proc skipIntLit*(t: PType): PType {.inline.} =
-  if t.kind == tyInt and t.n != nil:
-    result = getSysType(tyInt)
-  else:
-    result = t
+  if t.n != nil:
+    if t.kind in {tyInt, tyFloat}:
+      return getSysType(t.kind)
+  result = t
 
 proc AddSonSkipIntLit*(father, son: PType) =
   if isNil(father.sons): father.sons = @[]
diff --git a/compiler/msgs.nim b/compiler/msgs.nim
index c0b1221ef..5363442b4 100644
--- a/compiler/msgs.nim
+++ b/compiler/msgs.nim
@@ -8,7 +8,10 @@
 #
 
 import
-  options, strutils, os, tables, sockets, ropes, platform
+  options, strutils, os, tables, ropes, platform
+
+when useCaas:
+  import sockets
 
 type 
   TMsgKind* = enum 
@@ -532,14 +535,19 @@ var
   gWarnCounter*: int = 0
   gErrorMax*: int = 1         # stop after gErrorMax errors
   gSilence*: int              # == 0 if we produce any output at all 
-  stdoutSocket*: TSocket
 
-proc SuggestWriteln*(s: string) = 
-  if gSilence == 0: 
-    if isNil(stdoutSocket): Writeln(stdout, s)
-    else: 
+when useCaas:
+  var stdoutSocket*: TSocket
+
+proc SuggestWriteln*(s: string) =
+  if gSilence == 0:
+    when useCaas:
+      if isNil(stdoutSocket): Writeln(stdout, s)
+      else:
+        Writeln(stdout, s)
+        stdoutSocket.send(s & "\c\L")
+    else:
       Writeln(stdout, s)
-      stdoutSocket.send(s & "\c\L")
 
 proc SuggestQuit*() =
   if not isServing:
diff --git a/compiler/nimconf.nim b/compiler/nimconf.nim
index 39375ffd3..507812d9c 100644
--- a/compiler/nimconf.nim
+++ b/compiler/nimconf.nim
@@ -213,8 +213,11 @@ proc getUserConfigPath(filename: string): string =
 proc getSystemConfigPath(filename: string): string =
   # try standard configuration file (installation did not distribute files
   # the UNIX way)
-  result = joinPath([getPrefixDir(), "config", filename])
-  if not ExistsFile(result): result = "/etc/" & filename
+  let p = getPrefixDir()
+  result = joinPath([p, "config", filename])
+  when defined(unix):
+    if not existsFile(result): result = joinPath([p, "etc", filename])
+    if not existsFile(result): result = "/etc/" & filename
 
 proc LoadConfigs*(cfg: string) =
   # set default value (can be overwritten):
diff --git a/compiler/nimrod.ini b/compiler/nimrod.ini
index 49dcd25ba..482fe63c9 100644
--- a/compiler/nimrod.ini
+++ b/compiler/nimrod.ini
@@ -1,7 +1,6 @@
 [Project]
 Name: "Nimrod"
 Version: "$version"
-; Windows and i386 must be first!
 OS: "windows;linux;macosx;solaris;freebsd;netbsd;openbsd"
 CPU: "i386;amd64;powerpc64;arm"  # ;sparc
 Authors: "Andreas Rumpf"
diff --git a/compiler/options.nim b/compiler/options.nim
index 2b25b2650..3c91d4439 100644
--- a/compiler/options.nim
+++ b/compiler/options.nim
@@ -15,6 +15,7 @@ const
   useEffectSystem* = true
   hasFFI* = defined(useFFI)
   newScopeForIf* = true
+  useCaas* = not defined(noCaas)
 
 type                          # please make sure we have under 32 options
                               # (improves code efficiency a lot!)
diff --git a/compiler/parser.nim b/compiler/parser.nim
index d19149073..0d9d27e02 100644
--- a/compiler/parser.nim
+++ b/compiler/parser.nim
@@ -1412,7 +1412,6 @@ proc parseRoutine(p: var TParser, kind: TNodeKind): PNode =
 proc newCommentStmt(p: var TParser): PNode =
   #| commentStmt = COMMENT
   result = newNodeP(nkCommentStmt, p)
-  result.info.line = result.info.line - int16(1) - int16(p.tok.iNumber)
   result.comment = p.tok.literal
   getTok(p)
 
diff --git a/compiler/renderer.nim b/compiler/renderer.nim
index 70ce5c27d..efa4ecaba 100644
--- a/compiler/renderer.nim
+++ b/compiler/renderer.nim
@@ -329,7 +329,7 @@ proc atom(n: PNode): string =
     if n.flags * {nfBase2, nfBase8, nfBase16} == {}: 
       result = $n.floatVal & "\'f32"
     else: 
-      f = n.floatVal
+      f = n.floatVal.float32
       result = litAux(n, (cast[PInt32](addr(f)))[], 4) & "\'f32"
   of nkFloat64Lit: 
     if n.flags * {nfBase2, nfBase8, nfBase16} == {}: 
@@ -407,7 +407,8 @@ proc lsub(n: PNode): int =
     result = result + lcomma(n, 1)
   of nkExprColonExpr: result = lsons(n) + 2
   of nkInfix: result = lsons(n) + 2
-  of nkPrefix: result = lsons(n) + 1
+  of nkPrefix:
+    result = lsons(n)+1+(if n.len > 0 and n.sons[1].kind == nkInfix: 2 else: 0)
   of nkPostfix: result = lsons(n)
   of nkCallStrLit: result = lsons(n)
   of nkPragmaExpr: result = lsub(n.sons[0]) + lcomma(n, 1)
@@ -939,7 +940,12 @@ proc gsub(g: var TSrcGen, n: PNode, c: TContext) =
     gsub(g, n.sons[0])
     if n.len > 1:
       put(g, tkSpaces, space)
-      gsub(g, n.sons[1])
+      if n.sons[1].kind == nkInfix:
+        put(g, tkParLe, "(")
+        gsub(g, n.sons[1])
+        put(g, tkParRi, ")")
+      else:
+        gsub(g, n.sons[1])
   of nkPostfix: 
     gsub(g, n.sons[1])
     gsub(g, n.sons[0])
diff --git a/compiler/semcall.nim b/compiler/semcall.nim
index b2f41d509..c8f150922 100644
--- a/compiler/semcall.nim
+++ b/compiler/semcall.nim
@@ -290,11 +290,14 @@ proc SearchForBorrowProc(c: PContext, startScope: PScope, fn: PSym): PSym =
   # New approach: generate fn(x, y, z) where x, y, z have the proper types
   # and use the overloading resolution mechanism:
   var call = newNode(nkCall)
+  var hasDistinct = false
   call.add(newIdentNode(fn.name, fn.info))
   for i in 1.. <fn.typ.n.len:
     let param = fn.typ.n.sons[i]
     let t = skipTypes(param.typ, abstractVar-{tyTypeDesc})
+    if t.kind == tyDistinct or param.typ.kind == tyDistinct: hasDistinct = true
     call.add(newNodeIT(nkEmpty, fn.info, t.baseOfDistinct))
-  var resolved = semOverloadedCall(c, call, call, {fn.kind})
-  if resolved != nil:
-    result = resolved.sons[0].sym
+  if hasDistinct:
+    var resolved = semOverloadedCall(c, call, call, {fn.kind})
+    if resolved != nil:
+      result = resolved.sons[0].sym
diff --git a/compiler/semexprs.nim b/compiler/semexprs.nim
index 30b28a35d..2681150e0 100644
--- a/compiler/semexprs.nim
+++ b/compiler/semexprs.nim
@@ -1710,6 +1710,7 @@ proc semObjConstr(c: PContext, n: PNode, flags: TExprFlags): PNode =
     var
       check: PNode = nil
       f: PSym
+    t = objType
     while true:
       check = nil
       f = lookupInRecordAndBuildCheck(c, it, t.n, id, check)
@@ -1846,7 +1847,7 @@ proc semExpr(c: PContext, n: PNode, flags: TExprFlags = {}): PNode =
   of nkUInt64Lit: 
     if result.typ == nil: result.typ = getSysType(tyUInt64)
   of nkFloatLit: 
-    if result.typ == nil: result.typ = getSysType(tyFloat)
+    if result.typ == nil: result.typ = getFloatLitType(result)
   of nkFloat32Lit: 
     if result.typ == nil: result.typ = getSysType(tyFloat32)
   of nkFloat64Lit: 
diff --git a/compiler/semfold.nim b/compiler/semfold.nim
index ed7b14684..ca06ea1b6 100644
--- a/compiler/semfold.nim
+++ b/compiler/semfold.nim
@@ -21,7 +21,7 @@ proc getConstExpr*(m: PSym, n: PNode): PNode
 proc evalOp*(m: TMagic, n, a, b, c: PNode): PNode
 proc leValueConv*(a, b: PNode): bool
 proc newIntNodeT*(intVal: BiggestInt, n: PNode): PNode
-proc newFloatNodeT*(floatVal: BiggestFloat, n: PNode): PNode
+proc newFloatNodeT(floatVal: BiggestFloat, n: PNode): PNode
 proc newStrNodeT*(strVal: string, n: PNode): PNode
 
 # implementation
@@ -43,7 +43,10 @@ proc newIntNodeT(intVal: BiggestInt, n: PNode): PNode =
 
 proc newFloatNodeT(floatVal: BiggestFloat, n: PNode): PNode = 
   result = newFloatNode(nkFloatLit, floatVal)
-  result.typ = n.typ
+  if skipTypes(n.typ, abstractVarRange).kind == tyFloat:
+    result.typ = getFloatLitType(result)
+  else:
+    result.typ = n.typ
   result.info = n.info
 
 proc newStrNodeT(strVal: string, n: PNode): PNode = 
diff --git a/compiler/semstmts.nim b/compiler/semstmts.nim
index 022d412ce..0ce58ba5c 100644
--- a/compiler/semstmts.nim
+++ b/compiler/semstmts.nim
@@ -775,9 +775,12 @@ proc typeSectionFinalPass(c: PContext, n: PNode) =
     if aa.kind in {nkRefTy, nkPtrTy} and aa.len == 1 and
        aa.sons[0].kind == nkObjectTy:
       # give anonymous object a dummy symbol:
-      assert s.typ.sons[0].sym == nil
-      s.typ.sons[0].sym = newSym(skType, getIdent(s.name.s & ":ObjectType"), 
-                                 getCurrOwner(), s.info)
+      var st = s.typ
+      if st.kind == tyGenericBody: st = st.lastSon
+      InternalAssert st.kind in {tyPtr, tyRef}
+      InternalAssert st.sons[0].sym == nil
+      st.sons[0].sym = newSym(skType, getIdent(s.name.s & ":ObjectType"),
+                              getCurrOwner(), s.info)
 
 proc SemTypeSection(c: PContext, n: PNode): PNode =
   typeSectionLeftSidePass(c, n)
@@ -1212,7 +1215,7 @@ proc semStmtList(c: PContext, n: PNode): PNode =
       if n.sons[i].typ == EnforceVoidContext or usesResult(n.sons[i]):
         voidContext = true
         n.typ = EnforceVoidContext
-      elif i != last or voidContext:
+      if i != last or voidContext:
         discardCheck(n.sons[i])
       else:
         n.typ = n.sons[i].typ
diff --git a/compiler/semtypes.nim b/compiler/semtypes.nim
index d8846d717..64140274e 100644
--- a/compiler/semtypes.nim
+++ b/compiler/semtypes.nim
@@ -558,7 +558,7 @@ proc semObjectNode(c: PContext, n: PNode, prev: PType): PType =
   checkSonsLen(n, 3)
   if n.sons[1].kind != nkEmpty: 
     base = skipTypes(semTypeNode(c, n.sons[1].sons[0], nil), skipPtrs)
-    var concreteBase = skipGenericInvokation(base)
+    var concreteBase = skipGenericInvokation(base).skipTypes(skipPtrs)
     if concreteBase.kind == tyObject and tfFinal notin concreteBase.flags: 
       addInheritedFields(c, check, pos, concreteBase)
     else:
diff --git a/compiler/service.nim b/compiler/service.nim
index 8e8fe20bf..1de83af7c 100644
--- a/compiler/service.nim
+++ b/compiler/service.nim
@@ -9,11 +9,13 @@
 
 ## Implements the "compiler as a service" feature.
 
-import 
-  sockets,
+import
   times, commands, options, msgs, nimconf,
   extccomp, strutils, os, platform, parseopt
 
+when useCaas:
+  import sockets
+
 # We cache modules and the dependency graph. However, we don't check for
 # file changes but expect the client to tell us about them, otherwise the
 # repeated CRC calculations may turn out to be too slow.
@@ -80,19 +82,22 @@ proc serve*(action: proc (){.nimcall.}) =
       FlushFile(stdout)
 
   of "tcp", "":
-    var server = Socket()
-    let p = getConfigVar("server.port")
-    let port = if p.len > 0: parseInt(p).TPort else: 6000.TPort
-    server.bindAddr(port, getConfigVar("server.address"))
-    var inp = "".TaintedString
-    server.listen()
-    new(stdoutSocket)
-    while true:
-      accept(server, stdoutSocket)
-      stdoutSocket.readLine(inp)
-      execute inp.string
-      stdoutSocket.send("\c\L")
-      stdoutSocket.close()
+    when useCaas:
+      var server = Socket()
+      let p = getConfigVar("server.port")
+      let port = if p.len > 0: parseInt(p).TPort else: 6000.TPort
+      server.bindAddr(port, getConfigVar("server.address"))
+      var inp = "".TaintedString
+      server.listen()
+      new(stdoutSocket)
+      while true:
+        accept(server, stdoutSocket)
+        stdoutSocket.readLine(inp)
+        execute inp.string
+        stdoutSocket.send("\c\L")
+        stdoutSocket.close()
+    else:
+      quit "server.type not supported; compiler built without caas support"
   else:
     echo "Invalid server.type:", typ
     quit 1
diff --git a/compiler/sigmatch.nim b/compiler/sigmatch.nim
index ceb8ad156..318acc660 100644
--- a/compiler/sigmatch.nim
+++ b/compiler/sigmatch.nim
@@ -263,15 +263,19 @@ proc isConvertibleToRange(f, a: PType): bool =
        a.kind in {tyFloat..tyFloat128}:
     result = true
 
-proc handleFloatRange(f, a: PType): TTypeRelation = 
-  if a.kind == f.kind: 
+proc handleFloatRange(f, a: PType): TTypeRelation =
+  if a.kind == f.kind:
     result = isEqual
-  else: 
+  else:
     let ab = skipTypes(a, {tyRange})
     var k = ab.kind
     if k == f.kind: result = isSubrange
+    elif isFloatLit(ab): result = isFromIntLit
     elif isIntLit(ab): result = isConvertible
-    elif k >= tyFloat and k <= tyFloat128: result = isConvertible
+    elif k >= tyFloat and k <= tyFloat128:
+      # conversion to "float32" is not as good:
+      if f.kind == tyFloat32: result = isConvertible
+      else: result = isIntConv
     else: result = isNone
   
 proc isObjectSubtype(a, f: PType): int =
diff --git a/compiler/types.nim b/compiler/types.nim
index 99bedfca7..f9c40e201 100644
--- a/compiler/types.nim
+++ b/compiler/types.nim
@@ -109,6 +109,9 @@ proc getOrdValue(n: PNode): biggestInt =
 proc isIntLit*(t: PType): bool {.inline.} =
   result = t.kind == tyInt and t.n != nil and t.n.kind == nkIntLit
 
+proc isFloatLit*(t: PType): bool {.inline.} =
+  result = t.kind == tyFloat and t.n != nil and t.n.kind == nkFloatLit
+
 proc isCompatibleToCString(a: PType): bool = 
   if a.kind == tyArray: 
     if (firstOrd(a.sons[0]) == 0) and
diff --git a/compiler/vmdef.nim b/compiler/vmdef.nim
index 050caa65c..515f2975b 100644
--- a/compiler/vmdef.nim
+++ b/compiler/vmdef.nim
@@ -122,7 +122,8 @@ type
     opcLdImmInt,  # dest = immediate value
     opcWrGlobal,
     opcWrGlobalRef,
-    opcSetType    # dest.typ = types[Bx]
+    opcSetType,   # dest.typ = types[Bx]
+    opcTypeTrait
 
   TBlock* = object
     label*: PSym
diff --git a/compiler/vmdeps.nim b/compiler/vmdeps.nim
index 0e90a9b14..2a40276d1 100644
--- a/compiler/vmdeps.nim
+++ b/compiler/vmdeps.nim
@@ -35,21 +35,6 @@ proc opSlurp*(file: string, info: TLineInfo, module: PSym): string =
     result = ""
     LocalError(info, errCannotOpenFile, file)
 
-proc opTypeTrait*(n: PNode, context: PSym): PNode =
-  ## XXX: This should be pretty much guaranteed to be true
-  # by the type traits procs' signatures, but until the
-  # code is more mature it doesn't hurt to be extra safe
-  internalAssert n.len >= 2 and n.sons[1].kind == nkSym
-
-  let typ = n.sons[1].sym.typ.skipTypes({tyTypeDesc})
-  case n.sons[0].sym.name.s.normalize
-  of "name":
-    result = newStrNode(nkStrLit, typ.typeToString(preferExported))
-    result.typ = newType(tyString, context)
-    result.info = n.info
-  else:
-    internalAssert false
-
 when false:
   proc opExpandToAst*(c: PEvalContext, original: PNode): PNode =
     var
diff --git a/config/nimrod.cfg b/config/nimrod.cfg
index c50051086..77cc742b2 100644
--- a/config/nimrod.cfg
+++ b/config/nimrod.cfg
@@ -67,7 +67,8 @@ hint[LineTooLong]=off
     gpp.options.linker = "-ldl"
     clang.options.linker = "-ldl"
     tcc.options.linker = "-ldl"
-  @else:
+  @end
+  @if bsd or haiku:
     # BSD got posix_spawn only recently, so we deactivate it for osproc:
     define:useFork
     # at least NetBSD has problems with thread local storage:
diff --git a/install.txt b/install.txt
index eefdfb682..11c502235 100644
--- a/install.txt
+++ b/install.txt
@@ -62,46 +62,3 @@ Currently, the following C compilers are supported under Windows:
   | http://www.digitalmars.com/download/freecompiler.html
 
 However, most testing is done with GCC.
-
-
-
-Bootstrapping from github
--------------------------
-
-To get the source code you need either of these:
-
-* A working web browser + tar(or equivalent):
-  https://github.com/Araq/Nimrod/tarball/master
-* wget + tar:
-  ``wget --no-check-certificate "https://github.com/Araq/Nimrod/tarball/master"``
-* git: ``git clone git://github.com/Araq/Nimrod.git``
-
-After downloading the source (and extracting it), you need to 
-extract ``build/csources.zip``:
-
-* ``cd build``
-* ``unzip csources.zip``
-* ``cd ..``
-
-and then you can bootstrap with:
-
-On Windows
-~~~~~~~~~~
-
-* ``build.bat``
-* ``bin\nimrod c koch``
-* ``koch boot -d:release``
-
-If you want a 64 bit build, make sure that you have a GCC built for Win64 and
-execute ``build64.bat`` instead of ``build.bat``.
-
-
-On UNIX
-~~~~~~~
-
-* ``./build.sh``
-* ``bin/nimrod c koch``
-* ``./koch boot -d:release``
-
-Installation on UNIX can then be done with ``koch install [dir]``.
-
diff --git a/koch.nim b/koch.nim
index 30ad8c597..97fcf5b2c 100644
--- a/koch.nim
+++ b/koch.nim
@@ -52,6 +52,7 @@ Boot options:
                            (not needed on Windows)
   -d:useFFI                build Nimrod with FFI support at compile time
   -d:nativeStacktrace      use native stack traces (only for Mac OS X or Linux)
+  -d:noCaas                build Nimrod without CAAS support
 """
 
 proc exe(f: string): string = return addFileExt(f, ExeExt)
diff --git a/lib/core/typeinfo.nim b/lib/core/typeinfo.nim
index 4ce65ae91..edb4d1188 100644
--- a/lib/core/typeinfo.nim
+++ b/lib/core/typeinfo.nim
@@ -505,7 +505,7 @@ proc setBiggestFloat*(x: TAny, y: biggestFloat) =
   ## some float.
   case skipRange(x.rawtype).kind
   of tyFloat: cast[ptr Float](x.value)[] = y
-  of tyFloat32: cast[ptr Float32](x.value)[] = y
+  of tyFloat32: cast[ptr Float32](x.value)[] = y.float32
   of tyFloat64: cast[ptr Float64](x.value)[] = y
   else: assert false
 
diff --git a/lib/packages/docutils/rstgen.nim b/lib/packages/docutils/rstgen.nim
index a393943fb..364f847cc 100644
--- a/lib/packages/docutils/rstgen.nim
+++ b/lib/packages/docutils/rstgen.nim
@@ -265,12 +265,12 @@ proc renderHeadline(d: PDoc, n: PRstNode, result: var string) =
     d.tocPart[length].header = tmp
     
     dispA(d.target, result,
-        "<h$1><a class=\"toc-backref\" id=\"$2\" href=\"#$2_toc\">$3</a></h$1>", 
+        "\n<h$1><a class=\"toc-backref\" id=\"$2\" href=\"#$2_toc\">$3</a></h$1>", 
         "\\rsth$4{$3}\\label{$2}\n", [$n.level, 
         d.tocPart[length].refname, tmp, 
         $chr(n.level - 1 + ord('A'))])
   else:
-    dispA(d.target, result, "<h$1 id=\"$2\">$3</h$1>", 
+    dispA(d.target, result, "\n<h$1 id=\"$2\">$3</h$1>", 
                             "\\rsth$4{$3}\\label{$2}\n", [
         $n.level, refname, tmp, 
         $chr(n.level - 1 + ord('A'))])
diff --git a/lib/posix/posix.nim b/lib/posix/posix.nim
index 57b683c3a..cf260e9b7 100644
--- a/lib/posix/posix.nim
+++ b/lib/posix/posix.nim
@@ -30,7 +30,7 @@
 from times import TTime
 
 const
-  hasSpawnH = true # should exist for every Posix system really nowadays
+  hasSpawnH = not defined(haiku) # should exist for every Posix system nowadays
   hasAioH = defined(linux)
 
 when false:
@@ -842,48 +842,51 @@ var
   FE_UPWARD* {.importc, header: "<fenv.h>".}: cint
   FE_DFL_ENV* {.importc, header: "<fenv.h>".}: cint
 
-  MM_HARD* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Source of the condition is hardware.
-  MM_SOFT* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Source of the condition is software.
-  MM_FIRM* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Source of the condition is firmware.
-  MM_APPL* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Condition detected by application.
-  MM_UTIL* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Condition detected by utility.
-  MM_OPSYS* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Condition detected by operating system.
-  MM_RECOVER* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Recoverable error.
-  MM_NRECOV* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Non-recoverable error.
-  MM_HALT* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Error causing application to halt.
-  MM_ERROR* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Application has encountered a non-fatal fault.
-  MM_WARNING* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Application has detected unusual non-error condition.
-  MM_INFO* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Informative message.
-  MM_NOSEV* {.importc, header: "<fmtmsg.h>".}: cint
-    ## No severity level provided for the message.
-  MM_PRINT* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Display message on standard error.
-  MM_CONSOLE* {.importc, header: "<fmtmsg.h>".}: cint
-    ## Display message on system console. 
-
-  MM_OK* {.importc, header: "<fmtmsg.h>".}: cint
-    ## The function succeeded.
-  MM_NOTOK* {.importc, header: "<fmtmsg.h>".}: cint
-    ## The function failed completely.
-  MM_NOMSG* {.importc, header: "<fmtmsg.h>".}: cint
-    ## The function was unable to generate a message on standard error, 
-    ## but otherwise succeeded.
-  MM_NOCON* {.importc, header: "<fmtmsg.h>".}: cint
-    ## The function was unable to generate a console message, but 
-    ## otherwise succeeded. 
-    
+when not defined(haiku):
+  var
+    MM_HARD* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Source of the condition is hardware.
+    MM_SOFT* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Source of the condition is software.
+    MM_FIRM* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Source of the condition is firmware.
+    MM_APPL* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Condition detected by application.
+    MM_UTIL* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Condition detected by utility.
+    MM_OPSYS* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Condition detected by operating system.
+    MM_RECOVER* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Recoverable error.
+    MM_NRECOV* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Non-recoverable error.
+    MM_HALT* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Error causing application to halt.
+    MM_ERROR* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Application has encountered a non-fatal fault.
+    MM_WARNING* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Application has detected unusual non-error condition.
+    MM_INFO* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Informative message.
+    MM_NOSEV* {.importc, header: "<fmtmsg.h>".}: cint
+      ## No severity level provided for the message.
+    MM_PRINT* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Display message on standard error.
+    MM_CONSOLE* {.importc, header: "<fmtmsg.h>".}: cint
+      ## Display message on system console. 
+
+    MM_OK* {.importc, header: "<fmtmsg.h>".}: cint
+      ## The function succeeded.
+    MM_NOTOK* {.importc, header: "<fmtmsg.h>".}: cint
+      ## The function failed completely.
+    MM_NOMSG* {.importc, header: "<fmtmsg.h>".}: cint
+      ## The function was unable to generate a message on standard error, 
+      ## but otherwise succeeded.
+    MM_NOCON* {.importc, header: "<fmtmsg.h>".}: cint
+      ## The function was unable to generate a console message, but 
+      ## otherwise succeeded. 
+
+var    
   FNM_NOMATCH* {.importc, header: "<fnmatch.h>".}: cint
     ## The string does not match the specified pattern.
   FNM_PATHNAME* {.importc, header: "<fnmatch.h>".}: cint
@@ -1809,8 +1812,9 @@ proc feholdexcept*(a1: ptr Tfenv): cint {.importc, header: "<fenv.h>".}
 proc fesetenv*(a1: ptr Tfenv): cint {.importc, header: "<fenv.h>".}
 proc feupdateenv*(a1: ptr TFenv): cint {.importc, header: "<fenv.h>".}
 
-proc fmtmsg*(a1: int, a2: cstring, a3: cint,
-            a4, a5, a6: cstring): cint {.importc, header: "<fmtmsg.h>".}
+when not defined(haiku):
+  proc fmtmsg*(a1: int, a2: cstring, a3: cint,
+              a4, a5, a6: cstring): cint {.importc, header: "<fmtmsg.h>".}
             
 proc fnmatch*(a1, a2: cstring, a3: cint): cint {.importc, header: "<fnmatch.h>".}
 proc ftw*(a1: cstring, 
diff --git a/lib/pure/httpclient.nim b/lib/pure/httpclient.nim
index 15cc6abb8..2c0e7b835 100644
--- a/lib/pure/httpclient.nim
+++ b/lib/pure/httpclient.nim
@@ -10,6 +10,11 @@
 ## This module implements a simple HTTP client that can be used to retrieve
 ## webpages/other data.
 ##
+##
+## **Note**: This module is not ideal, connection is not kept alive so sites with
+## many redirects are expensive. As such in the future this module may change,
+## and the current procedures will be deprecated.
+##
 ## Retrieving a website
 ## ====================
 ## 
@@ -62,8 +67,15 @@
 ## that as long as the server is sending data an exception will not be raised,
 ## if however data does not reach client within the specified timeout an ETimeout
 ## exception will then be raised.
+##
+## Proxy
+## =====
+##
+## A proxy can be specified as a param to any of these procedures, the ``newProxy``
+## constructor should be used for this purpose. However,
+## currently only basic authentication is supported.
 
-import sockets, strutils, parseurl, parseutils, strtabs
+import sockets, strutils, parseurl, parseutils, strtabs, base64
 
 type
   TResponse* = tuple[
@@ -72,6 +84,10 @@ type
     headers: PStringTable,
     body: string]
 
+  PProxy* = ref object
+    url*: TUrl
+    auth*: string
+
   EInvalidProtocol* = object of ESynch ## exception that is raised when server
                                        ## does not conform to the implemented
                                        ## protocol
@@ -239,23 +255,34 @@ when not defined(ssl):
 else:
   let defaultSSLContext = newContext(verifyMode = CVerifyNone)
 
+proc newProxy*(url: string, auth = ""): PProxy =
+  ## Constructs a new ``TProxy`` object.
+  result = PProxy(url: parseUrl(url), auth: auth)
+
 proc request*(url: string, httpMethod = httpGET, extraHeaders = "", 
               body = "",
               sslContext: PSSLContext = defaultSSLContext,
-              timeout = -1, userAgent = defUserAgent): TResponse =
+              timeout = -1, userAgent = defUserAgent,
+              proxy: PProxy = nil): TResponse =
   ## | Requests ``url`` with the specified ``httpMethod``.
   ## | Extra headers can be specified and must be seperated by ``\c\L``
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
-  var r = parseUrl(url)
+  var r = if proxy == nil: parseUrl(url) else: proxy.url
   var headers = substr($httpMethod, len("http"))
-  headers.add(" /" & r.path & r.query)
+  if proxy == nil:
+    headers.add(" /" & r.path & r.query)
+  else:
+    headers.add(" " & url)
 
   headers.add(" HTTP/1.1\c\L")
   
   add(headers, "Host: " & r.hostname & "\c\L")
   if userAgent != "":
     add(headers, "User-Agent: " & userAgent & "\c\L")
+  if proxy != nil and proxy.auth != "":
+    let auth = base64.encode(proxy.auth, newline = "")
+    add(headers, "Proxy-Authorization: basic " & auth & "\c\L")
   add(headers, extraHeaders)
   add(headers, "\c\L")
   
@@ -299,30 +326,34 @@ proc getNewLocation(lastUrl: string, headers: PStringTable): string =
   
 proc get*(url: string, extraHeaders = "", maxRedirects = 5,
           sslContext: PSSLContext = defaultSSLContext,
-          timeout = -1, userAgent = defUserAgent): TResponse =
+          timeout = -1, userAgent = defUserAgent,
+          proxy: PProxy = nil): TResponse =
   ## | GETs the ``url`` and returns a ``TResponse`` object
   ## | This proc also handles redirection
   ## | Extra headers can be specified and must be separated by ``\c\L``.
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
-  result = request(url, httpGET, extraHeaders, "", sslContext, timeout, userAgent)
+  result = request(url, httpGET, extraHeaders, "", sslContext, timeout,
+                   userAgent, proxy)
   var lastURL = url
   for i in 1..maxRedirects:
     if result.status.redirection():
       let redirectTo = getNewLocation(lastURL, result.headers)
       result = request(redirectTo, httpGET, extraHeaders, "", sslContext,
-                       timeout, userAgent)
+                       timeout, userAgent, proxy)
       lastUrl = redirectTo
       
 proc getContent*(url: string, extraHeaders = "", maxRedirects = 5,
                  sslContext: PSSLContext = defaultSSLContext,
-                 timeout = -1, userAgent = defUserAgent): string =
+                 timeout = -1, userAgent = defUserAgent,
+                 proxy: PProxy = nil): string =
   ## | GETs the body and returns it as a string.
   ## | Raises exceptions for the status codes ``4xx`` and ``5xx``
   ## | Extra headers can be specified and must be separated by ``\c\L``.
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
-  var r = get(url, extraHeaders, maxRedirects, sslContext, timeout, userAgent)
+  var r = get(url, extraHeaders, maxRedirects, sslContext, timeout, userAgent,
+              proxy)
   if r.status[0] in {'4','5'}:
     raise newException(EHTTPRequestErr, r.status)
   else:
@@ -331,7 +362,8 @@ proc getContent*(url: string, extraHeaders = "", maxRedirects = 5,
 proc post*(url: string, extraHeaders = "", body = "",
            maxRedirects = 5,
            sslContext: PSSLContext = defaultSSLContext,
-           timeout = -1, userAgent = defUserAgent): TResponse =
+           timeout = -1, userAgent = defUserAgent,
+           proxy: PProxy = nil): TResponse =
   ## | POSTs ``body`` to the ``url`` and returns a ``TResponse`` object.
   ## | This proc adds the necessary Content-Length header.
   ## | This proc also handles redirection.
@@ -339,27 +371,29 @@ proc post*(url: string, extraHeaders = "", body = "",
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
   var xh = extraHeaders & "Content-Length: " & $len(body) & "\c\L"
-  result = request(url, httpPOST, xh, body, sslContext, timeout, userAgent)
+  result = request(url, httpPOST, xh, body, sslContext, timeout, userAgent,
+                   proxy)
   var lastUrl = ""
   for i in 1..maxRedirects:
     if result.status.redirection():
       let redirectTo = getNewLocation(lastURL, result.headers)
       var meth = if result.status != "307": httpGet else: httpPost
       result = request(redirectTo, meth, xh, body, sslContext, timeout,
-                       userAgent)
+                       userAgent, proxy)
       lastUrl = redirectTo
   
 proc postContent*(url: string, extraHeaders = "", body = "",
                   maxRedirects = 5,
                   sslContext: PSSLContext = defaultSSLContext,
-                  timeout = -1, userAgent = defUserAgent): string =
+                  timeout = -1, userAgent = defUserAgent,
+                  proxy: PProxy = nil): string =
   ## | POSTs ``body`` to ``url`` and returns the response's body as a string
   ## | Raises exceptions for the status codes ``4xx`` and ``5xx``
   ## | Extra headers can be specified and must be separated by ``\c\L``.
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
   var r = post(url, extraHeaders, body, maxRedirects, sslContext, timeout,
-               userAgent)
+               userAgent, proxy)
   if r.status[0] in {'4','5'}:
     raise newException(EHTTPRequestErr, r.status)
   else:
@@ -367,14 +401,15 @@ proc postContent*(url: string, extraHeaders = "", body = "",
   
 proc downloadFile*(url: string, outputFilename: string,
                    sslContext: PSSLContext = defaultSSLContext,
-                   timeout = -1, userAgent = defUserAgent) =
+                   timeout = -1, userAgent = defUserAgent,
+                   proxy: PProxy = nil) =
   ## | Downloads ``url`` and saves it to ``outputFilename``
   ## | An optional timeout can be specified in miliseconds, if reading from the
   ## server takes longer than specified an ETimeout exception will be raised.
   var f: TFile
   if open(f, outputFilename, fmWrite):
     f.write(getContent(url, sslContext = sslContext, timeout = timeout,
-            userAgent = userAgent))
+            userAgent = userAgent, proxy = proxy))
     f.close()
   else:
     fileError("Unable to open file")
diff --git a/lib/pure/os.nim b/lib/pure/os.nim
index 176439ec7..43bdb16ee 100644
--- a/lib/pure/os.nim
+++ b/lib/pure/os.nim
@@ -164,7 +164,7 @@ else: # UNIX-like operating system
     ScriptExt* = ""
     DynlibFormat* = when defined(macosx): "lib$1.dylib" else: "lib$1.so"
 
-when defined(macosx) or defined(bsd):
+when defined(posix):
   var
     pathMax {.importc: "PATH_MAX", header: "<stdlib.h>".}: cint
 
@@ -674,17 +674,12 @@ proc expandFilename*(filename: string): string {.rtl, extern: "nos$1",
       var L = GetFullPathNameA(filename, bufsize, result, unused)
       if L <= 0'i32 or L >= bufsize: OSError(OSLastError())
       setLen(result, L)
-  elif defined(macosx) or defined(bsd):
-    # On Mac OS X 10.5, realpath does not allocate the buffer on its own
-    var pathBuffer: cstring = newString(pathMax)
-    var resultBuffer = realpath(filename, pathBuffer)
-    if resultBuffer == nil: OSError(OSLastError())
-    result = $resultBuffer
   else:
-    var res = realpath(filename, nil)
-    if res == nil: OSError(OSLastError())
-    result = $res
-    c_free(res)
+    # careful, realpath needs to take an allocated buffer according to Posix:
+    result = newString(pathMax)
+    var r = realpath(filename, result)
+    if r.isNil: OSError(OSLastError())
+    setlen(result, c_strlen(result))
  
 proc ChangeFileExt*(filename, ext: string): string {.
   noSideEffect, rtl, extern: "nos$1".} =
diff --git a/lib/pure/strutils.nim b/lib/pure/strutils.nim
index 73dd9132c..a4aa81578 100644
--- a/lib/pure/strutils.nim
+++ b/lib/pure/strutils.nim
@@ -1030,8 +1030,8 @@ type
     ffScientific       ## use scientific notation (using ``e`` character)

 

 proc formatBiggestFloat*(f: BiggestFloat, format: TFloatFormat = ffDefault,

-                         precision = 16): string {.noSideEffect, operator: 2,

-                                                  rtl, extern: "nsu$1".} =

+                         precision: range[0..32] = 16): string {.
+                         noSideEffect, operator: 2, rtl, extern: "nsu$1".} =

   ## converts a floating point value `f` to a string.

   ##

   ## If ``format == ffDecimal`` then precision is the number of digits to

@@ -1041,11 +1041,11 @@ proc formatBiggestFloat*(f: BiggestFloat, format: TFloatFormat = ffDefault,
   ## `precision`'s default value is the maximum number of meaningful digits

   ## after the decimal point for Nimrod's ``biggestFloat`` type.
   ## 
-  ## If ``precision == 0``, it uses the 

+  ## If ``precision == 0``, it tries to format it nicely.

   const floatFormatToChar: array[TFloatFormat, char] = ['g', 'f', 'e']

   var

     frmtstr {.noinit.}: array[0..5, char]

-    buf: array[0..80, char]

+    buf {.noinit.}: array[0..2500, char]

   frmtstr[0] = '%'

   if precision > 0:

     frmtstr[1] = '#'

@@ -1061,8 +1061,8 @@ proc formatBiggestFloat*(f: BiggestFloat, format: TFloatFormat = ffDefault,
   result = $buf

 

 proc formatFloat*(f: float, format: TFloatFormat = ffDefault,

-                  precision = 16): string {.noSideEffect, operator: 2,

-                                           rtl, extern: "nsu$1".} =

+                  precision: range[0..32] = 16): string {.
+                  noSideEffect, operator: 2, rtl, extern: "nsu$1".} =

   ## converts a floating point value `f` to a string.

   ##

   ## If ``format == ffDecimal`` then precision is the number of digits to

diff --git a/lib/pure/xmltree.nim b/lib/pure/xmltree.nim
index 7621094f3..95b48a850 100644
--- a/lib/pure/xmltree.nim
+++ b/lib/pure/xmltree.nim
@@ -273,7 +273,7 @@ macro `<>`*(x: expr): expr {.immediate.} =
   ## Constructor macro for XML. Example usage:
   ##
   ## .. code-block:: nimrod
-  ##   <>a(href="http://nimrod-code.org", "Nimrod rules.")
+  ##   <>a(href="http://nimrod-code.org", newText("Nimrod rules."))
   ##
   ## Produces an XML tree for::
   ##
@@ -334,3 +334,7 @@ proc findAll*(n: PXmlNode, tag: string): seq[PXmlNode] =
   ##     process(imgTag)
   newSeq(result, 0)
   findAll(n, tag, result)
+
+when isMainModule:
+  assert """<a href="http://nimrod-code.org">Nimrod rules.</a>""" ==
+    $(<>a(href="http://nimrod-code.org", newText("Nimrod rules.")))
diff --git a/lib/system.nim b/lib/system.nim
index 749124ac9..4ff1f1577 100644
--- a/lib/system.nim
+++ b/lib/system.nim
@@ -28,7 +28,9 @@ type
   uint64* {.magic: UInt64.} ## unsigned 64 bit integer type
   float* {.magic: Float.} ## default floating point type
   float32* {.magic: Float32.} ## 32 bit floating point type
-  float64* {.magic: Float64.} ## 64 bit floating point type
+  float64* {.magic: Float.} ## 64 bit floating point type
+
+# 'float64' is now an alias to 'float'; this solves many problems
 
 type # we need to start a new type section here, so that ``0`` can have a type
   bool* {.magic: Bool.} = enum ## built-in boolean type
@@ -638,6 +640,14 @@ proc `<%` *(x, y: Int64): bool {.magic: "LtU64", noSideEffect.}
 
 
 # floating point operations:
+
+proc `+` *(x: float32): float32 {.magic: "UnaryPlusF64", noSideEffect.}
+proc `-` *(x: float32): float32 {.magic: "UnaryMinusF64", noSideEffect.}
+proc `+` *(x, y: float32): float32 {.magic: "AddF64", noSideEffect.}
+proc `-` *(x, y: float32): float32 {.magic: "SubF64", noSideEffect.}
+proc `*` *(x, y: float32): float32 {.magic: "MulF64", noSideEffect.}
+proc `/` *(x, y: float32): float32 {.magic: "DivF64", noSideEffect.}
+
 proc `+` *(x: float): float {.magic: "UnaryPlusF64", noSideEffect.}
 proc `-` *(x: float): float {.magic: "UnaryMinusF64", noSideEffect.}
 proc `+` *(x, y: float): float {.magic: "AddF64", noSideEffect.}
@@ -646,6 +656,10 @@ proc `*` *(x, y: float): float {.magic: "MulF64", noSideEffect.}
 proc `/` *(x, y: float): float {.magic: "DivF64", noSideEffect.}
   ## computes the floating point division
 
+proc `==` *(x, y: float32): bool {.magic: "EqF64", noSideEffect.}
+proc `<=` *(x, y: float32): bool {.magic: "LeF64", noSideEffect.}
+proc `<`  *(x, y: float32): bool {.magic: "LtF64", noSideEffect.}
+
 proc `==` *(x, y: float): bool {.magic: "EqF64", noSideEffect.}
 proc `<=` *(x, y: float): bool {.magic: "LeF64", noSideEffect.}
 proc `<`  *(x, y: float): bool {.magic: "LtF64", noSideEffect.}
@@ -1450,6 +1464,12 @@ proc isNil*[T: proc](x: T): bool {.noSideEffect, magic: "IsNil".}
   ## Fast check whether `x` is nil. This is sometimes more efficient than
   ## ``== nil``.
 
+proc `==` *[I, T](x, y: array[I, T]): bool =
+  for f in low(x)..high(x):
+    if x[f] != y[f]:
+      return
+  result = true
+
 proc `@`*[T](a: openArray[T]): seq[T] = 
   ## turns an openarray into a sequence. This is not as efficient as turning
   ## a fixed length array into a sequence as it always copies every element
@@ -1996,7 +2016,7 @@ when not defined(JS): #and not defined(NimrodVM):
       ## `content` completely to the file and closes the file afterwards.
       ## Raises an IO exception in case of an error.
 
-    proc write*(f: TFile, r: float) {.tags: [FWriteIO].}
+    proc write*(f: TFile, r: float32) {.tags: [FWriteIO].}
     proc write*(f: TFile, i: int) {.tags: [FWriteIO].}
     proc write*(f: TFile, i: biggestInt) {.tags: [FWriteIO].}
     proc write*(f: TFile, r: biggestFloat) {.tags: [FWriteIO].}
diff --git a/lib/system/ansi_c.nim b/lib/system/ansi_c.nim
index 06da34926..13e8496d2 100644
--- a/lib/system/ansi_c.nim
+++ b/lib/system/ansi_c.nim
@@ -58,7 +58,7 @@ else:
 
 proc c_longjmp(jmpb: C_JmpBuf, retval: cint) {.
   header: "<setjmp.h>", importc: "longjmp".}
-proc c_setjmp(jmpb: var C_JmpBuf): cint {.
+proc c_setjmp(jmpb: C_JmpBuf): cint {.
   header: "<setjmp.h>", importc: "setjmp".}
 
 proc c_signal(sig: cint, handler: proc (a: cint) {.noconv.}) {.
diff --git a/lib/system/gc.nim b/lib/system/gc.nim
index 36c008bef..f5b68b9db 100644
--- a/lib/system/gc.nim
+++ b/lib/system/gc.nim
@@ -759,7 +759,7 @@ else:
     # Used to traverse the stack and registers assuming
     # that 'setjmp' will save registers in the C stack.
     type PStackSlice = ptr array [0..7, pointer]
-    var registers: C_JmpBuf
+    var registers {.noinit.}: C_JmpBuf
     if c_setjmp(registers) == 0'i32: # To fill the C stack with registers.
       var max = cast[TAddress](gch.stackBottom)
       var sp = cast[TAddress](addr(registers))
diff --git a/lib/system/gc_ms.nim b/lib/system/gc_ms.nim
index 9ebc27a9f..2e3596985 100644
--- a/lib/system/gc_ms.nim
+++ b/lib/system/gc_ms.nim
@@ -449,7 +449,7 @@ else:
     # Used to traverse the stack and registers assuming
     # that 'setjmp' will save registers in the C stack.
     type PStackSlice = ptr array [0..7, pointer]
-    var registers: C_JmpBuf
+    var registers {.noinit.}: C_JmpBuf
     if c_setjmp(registers) == 0'i32: # To fill the C stack with registers.
       var max = cast[TAddress](gch.stackBottom)
       var sp = cast[TAddress](addr(registers))
diff --git a/lib/system/sysio.nim b/lib/system/sysio.nim
index 5407e0618..a877f8b28 100644
--- a/lib/system/sysio.nim
+++ b/lib/system/sysio.nim
@@ -91,7 +91,7 @@ proc write(f: TFile, i: biggestInt) =
 proc write(f: TFile, b: bool) =
   if b: write(f, "true")
   else: write(f, "false")
-proc write(f: TFile, r: float) = fprintf(f, "%g", r)
+proc write(f: TFile, r: float32) = fprintf(f, "%g", r)
 proc write(f: TFile, r: biggestFloat) = fprintf(f, "%g", r)
 
 proc write(f: TFile, c: Char) = putc(c, f)
diff --git a/readme.md b/readme.md
index 59546653b..f74f81283 100644
--- a/readme.md
+++ b/readme.md
@@ -6,8 +6,7 @@ documentation.
 Compiling the Nimrod compiler is quite straightforward. Because
 the Nimrod compiler itself is written in the Nimrod programming language
 the C source of an older version of the compiler are needed to bootstrap the
-latest version. The C sources are however included with this repository under
-the build directory.
+latest version. The C sources are available in a separate repo [here](http://github.com/nimrod-code/csources).
 
 Pre-compiled snapshots of the compiler are also available on
 [Nimbuild](http://build.nimrod-code.org/). Your platform however may not 
@@ -53,7 +52,7 @@ and you can also get help in the IRC channel
 on [Freenode](irc://irc.freenode.net/nimrod) in #nimrod.
 
 ## License
-The compiler and the standard library is licensed under the MIT license, 
+The compiler and the standard library are licensed under the MIT license, 
 except for some modules where the documentation suggests otherwise. This means 
 that you can use any license for your own programs developed with Nimrod, 
 allowing you to create commercial applications.
diff --git a/readme.txt b/readme.txt
index 59546653b..f74f81283 100644
--- a/readme.txt
+++ b/readme.txt
@@ -6,8 +6,7 @@ documentation.
 Compiling the Nimrod compiler is quite straightforward. Because
 the Nimrod compiler itself is written in the Nimrod programming language
 the C source of an older version of the compiler are needed to bootstrap the
-latest version. The C sources are however included with this repository under
-the build directory.
+latest version. The C sources are available in a separate repo [here](http://github.com/nimrod-code/csources).
 
 Pre-compiled snapshots of the compiler are also available on
 [Nimbuild](http://build.nimrod-code.org/). Your platform however may not 
@@ -53,7 +52,7 @@ and you can also get help in the IRC channel
 on [Freenode](irc://irc.freenode.net/nimrod) in #nimrod.
 
 ## License
-The compiler and the standard library is licensed under the MIT license, 
+The compiler and the standard library are licensed under the MIT license, 
 except for some modules where the documentation suggests otherwise. This means 
 that you can use any license for your own programs developed with Nimrod, 
 allowing you to create commercial applications.
diff --git a/tests/compile/tinheritref.nim b/tests/compile/tinheritref.nim
new file mode 100644
index 000000000..e5de6a4be
--- /dev/null
+++ b/tests/compile/tinheritref.nim
@@ -0,0 +1,27 @@
+discard """
+  output: "23"
+"""
+
+# bug #554, #179
+
+type T[E] =
+  ref object
+    elem: E
+
+var ob: T[int]
+
+ob = T[int](elem: 23)
+echo ob.elem
+
+type
+  TTreeIteratorA* = ref object {.inheritable.}
+
+  TKeysIteratorA* = ref object of TTreeIteratorA  #compiles
+
+  TTreeIterator* [T,D] = ref object {.inheritable.}
+
+  TKeysIterator* [T,D] = ref object of TTreeIterator[T,D]  #this not
+  
+var
+  it: TKeysIterator[int, string] = nil
+
diff --git a/tests/compile/tobjconstr2.nim b/tests/compile/tobjconstr2.nim
index ef5446999..cb47e146d 100644
--- a/tests/compile/tobjconstr2.nim
+++ b/tests/compile/tobjconstr2.nim
@@ -6,3 +6,17 @@ var s{.exportc.}: seq[TFoo] = @[]
 s.add TFoo(x: 42)
 
 echo s[0].x
+
+
+# bug #563
+type
+  Foo =
+    object {.inheritable.}
+      x: int
+
+  Bar =
+    object of Foo
+      y: int
+
+var a = Bar(y: 100, x: 200) # works
+var b = Bar(x: 100, y: 200) # used to fail
diff --git a/tests/compile/tvarious.nim b/tests/compile/tvarious.nim
index e91de9245..25f48bb30 100644
--- a/tests/compile/tvarious.nim
+++ b/tests/compile/tvarious.nim
@@ -1,4 +1,7 @@
 # Test various aspects

+
+# bug #572
+var a=12345678901'u64
 

 var x = (x: 42, y: (a: 8, z: 10))
 echo x.y
diff --git a/tests/reject/texprstmt.nim b/tests/reject/texprstmt.nim
new file mode 100644
index 000000000..b32394d8d
--- /dev/null
+++ b/tests/reject/texprstmt.nim
@@ -0,0 +1,12 @@
+discard """
+  line: 10
+  errormsg: "value returned by statement has to be discarded"
+"""
+
+# bug #578
+
+proc test: string =
+  result = "blah"
+  result[1 .. -1]
+
+echo test()
diff --git a/tests/reject/tinvalidborrow.nim b/tests/reject/tinvalidborrow.nim
new file mode 100644
index 000000000..9ab9e8d64
--- /dev/null
+++ b/tests/reject/tinvalidborrow.nim
@@ -0,0 +1,17 @@
+discard """
+  line: 11
+  errormsg: "no symbol to borrow from found"
+"""
+
+# bug #516
+
+type
+  TAtom = culong
+
+proc `==`*(a, b: TAtom): bool {.borrow.}
+
+var
+  d, e: TAtom
+
+echo( $(d == e) )
+
diff --git a/tests/run/tvarious1.nim b/tests/run/tvarious1.nim
index d30d91234..9dd4af606 100644
--- a/tests/run/tvarious1.nim
+++ b/tests/run/tvarious1.nim
@@ -1,7 +1,8 @@
 discard """
   file: "tlenopenarray.nim"
   output: '''1
-0'''
+0
+Whopie'''
 """
 
 echo len([1_000_000]) #OUT 1
@@ -12,3 +13,17 @@ type
 proc `[]`(v: TVector; idx: int): int = TArray(v)[idx]
 var v: TVector
 echo v[2]
+
+# bug #569
+
+import queues
+
+type
+  TWidget = object
+    names: TQueue[string]
+
+var w = TWidget(names: initQueue[string]())
+
+add(w.names, "Whopie")
+
+for n in w.names: echo(n)
diff --git a/todo.txt b/todo.txt
index 6fce93290..732045a5e 100644
--- a/todo.txt
+++ b/todo.txt
@@ -22,6 +22,7 @@ version 0.9.4
 Bugs
 ====
 
+- compilation of niminst takes way too long. looks like a regression
 - simple closure iterator doesn't work
 - docgen: sometimes effects are listed twice
 - 'result' is not properly cleaned for NRVO --> use uninit checking instead
diff --git a/tools/niminst/buildbat.tmpl b/tools/niminst/buildbat.tmpl
index 256f61b3d..f7ccbcbfa 100644
--- a/tools/niminst/buildbat.tmpl
+++ b/tools/niminst/buildbat.tmpl
@@ -1,11 +1,11 @@
 #! stdtmpl(subsChar='?') | standard
-#proc GenerateBuildBatchScript(c: TConfigData, target: TTarget): string = 
+#proc GenerateBuildBatchScript(c: TConfigData, winIndex, cpuIndex: int): string = 
 #  result = "@echo off\nREM Generated by niminst\n"
 SET CC=gcc
 SET LINKER=gcc
 SET COMP_FLAGS=?{c.ccompiler.flags}
 SET LINK_FLAGS=?{c.linker.flags}
-SET BIN_DIR=?{firstBinPath(c)}
+SET BIN_DIR=?{firstBinPath(c).slashify}
 
 if EXIST ..\koch.nim SET BIN_DIR=..\bin
 
@@ -15,8 +15,8 @@ REM call the compiler:
 
 #  block win32:
 #    var linkCmd = ""
-#    for ff in items(c.cfiles[1][ord(target)]):
-#      let f = ff.replace('/', '\\')
+#    for ff in items(c.cfiles[winIndex][cpuIndex]):
+#      let f = ff.slashify
 ECHO %CC% %COMP_FLAGS% -Isrc -c ?{f} -o ?{changeFileExt(f, "o")}
 %CC% %COMP_FLAGS% -Isrc -c ?{f} -o ?{changeFileExt(f, "o")}
 #      linkCmd.add(" " & changeFileExt(f, "o"))
diff --git a/tools/niminst/buildsh.tmpl b/tools/niminst/buildsh.tmpl
index 1ce182b63..244d73710 100644
--- a/tools/niminst/buildsh.tmpl
+++ b/tools/niminst/buildsh.tmpl
@@ -35,7 +35,7 @@ LINK_FLAGS="?{c.linker.flags}"
 ucpu=`uname -m`
 uos=`uname`
 #  add(result, "# bin dir detection\n")
-binDir=?{firstBinPath(c)}
+binDir=?{firstBinPath(c).slashify}
 
 if [ -s ../koch.nim ]; then
   binDir="../bin"
@@ -126,7 +126,8 @@ case $myos in
 #    for cpuA in 1..c.cpus.len:
   ?{c.cpus[cpuA-1]})
 #      var linkCmd = ""
-#      for f in items(c.cfiles[osA][cpuA]):
+#      for ff in items(c.cfiles[osA][cpuA]):
+#        let f = ff.slashify
     echo "$CC $COMP_FLAGS -Isrc -c ?{f} -o ?{changeFileExt(f, "o")}"
     $CC $COMP_FLAGS -Isrc -c ?{f} -o ?{changeFileExt(f, "o")}
 #        add(linkCmd, " \\\n" & changeFileExt(f, "o"))
diff --git a/tools/niminst/deinstall.tmpl b/tools/niminst/deinstall.tmpl
index 61141f78e..c961ac07a 100644
--- a/tools/niminst/deinstall.tmpl
+++ b/tools/niminst/deinstall.tmpl
@@ -39,10 +39,12 @@ if [ $# -eq 1 ] ; then
   esac
   echo "removing files..."
 
-#for f in items(c.cat[fcUnixBin]):
+#for ff in items(c.cat[fcUnixBin]):
+  #let f = ff.slashify
   rm -f $bindir/?f.skipRoot
 #end for
-#for f in items(c.cat[fcConfig]): 
+#for ff in items(c.cat[fcConfig]): 
+  #let f = ff.slashify
   rm -f $configdir/?f.skipRoot
 #end for
   rm -rf $docdir
diff --git a/tools/niminst/inno.tmpl b/tools/niminst/inno.tmpl
index df1460e42..0219dea1f 100644
--- a/tools/niminst/inno.tmpl
+++ b/tools/niminst/inno.tmpl
@@ -21,7 +21,7 @@ Name: english; MessagesFile: compiler:Default.isl
 [Files] 
   #for i in low(TFileCategory)..fcWindows:
   #  for f in items(c.cat[i]):
-Source: ${expandFilename(f)}; DestDir: {app}\${splitFile(f).dir}; Flags: ignoreversion
+Source: ${expandFilename(f).slashify}; DestDir: {app}\${splitFile(f).dir.slashify}; Flags: ignoreversion
   #  end for
   #end for
 
@@ -32,7 +32,7 @@ Name: {group}\Console for $c.displayName; Filename: {cmd}
 Name: {group}\$c.displayName; Filename: {app}\${c.name}.exe
   #end if
   #for f in items(c.cat[fcDocStart]):
-Name: {group}\Documentation; Filename: {app}\$f
+Name: {group}\Documentation; Filename: {app}\${f.slashify}
   #end for
 Name: {group}\{cm:UninstallProgram,$c.displayName}; Filename: {uninstallexe}
 
@@ -65,7 +65,7 @@ begin
   setArrayLength(result, $c.binPaths.len);
     #var i = 0
     #for b in items(c.binPaths):
-  result[$i] := ExpandConstant('{app}') + '\$b';
+  result[$i] := ExpandConstant('{app}') + '\${b.slashify}';
       #inc(i)
     #end for
 end;
diff --git a/tools/niminst/install.tmpl b/tools/niminst/install.tmpl
index bfba024c7..3eb07b8af 100644
--- a/tools/niminst/install.tmpl
+++ b/tools/niminst/install.tmpl
@@ -7,7 +7,7 @@ set -e
 
 if [ $# -eq 1 ] ; then
 # if c.cat[fcUnixBin].len > 0:
-  if test -f ?{c.cat[fcUnixBin][0]}
+  if test -f ?{c.cat[fcUnixBin][0].slashify}
   then 
     echo "?c.displayName build detected"
   else
@@ -65,35 +65,35 @@ if [ $# -eq 1 ] ; then
 #      mk = unixDirVars[cat] & "/" & mk
 #      if not createdDirs.hasKey(mk):
 #        createdDirs[mk] = "true"
-  mkdir -p ?mk
+  mkdir -p ?{mk.slashify}
 #      end if
 #    end if
 #  end for
 #end for
 
 #for f in items(c.cat[fcUnixBin]):
-  cp ?f $bindir/?f.skipRoot
-  chmod 755 $bindir/?f.skipRoot
+  cp ?f.slashify $bindir/?f.skipRoot.slashify
+  chmod 755 $bindir/?f.skipRoot.slashify
 #end for
 #for f in items(c.cat[fcConfig]): 
-  cp ?f $configdir/?f.skipRoot
-  chmod 644 $configdir/?f.skipRoot
+  cp ?f.slashify $configdir/?f.skipRoot.slashify
+  chmod 644 $configdir/?f.skipRoot.slashify
 #end for
 #for f in items(c.cat[fcData]): 
-  if [ -f ?f ]; then
-    cp ?f $datadir/?f.skipRoot
-    chmod 644 $datadir/?f.skipRoot
+  if [ -f ?f.slashify ]; then
+    cp ?f.slashify $datadir/?f.skipRoot.slashify
+    chmod 644 $datadir/?f.skipRoot.slashify
   fi
 #end for
 #for f in items(c.cat[fcDoc]):
-  if [ -f ?f ]; then
-    cp ?f $docdir/?f.skipRoot
-    chmod 644 $docdir/?f.skipRoot
+  if [ -f ?f.slashify ]; then
+    cp ?f.slashify $docdir/?f.skipRoot.slashify
+    chmod 644 $docdir/?f.skipRoot.slashify
   fi
 #end for
 #for f in items(c.cat[fcLib]):
-  cp ?f $libdir/?f.skipRoot
-  chmod 644 $libdir/?f.skipRoot
+  cp ?f.slashify $libdir/?f.skipRoot.slashify
+  chmod 644 $libdir/?f.skipRoot.slashify
 #end for
   
   echo "installation successful"
diff --git a/tools/niminst/niminst.nim b/tools/niminst/niminst.nim
index faad2fb15..4da734d13 100644
--- a/tools/niminst/niminst.nim
+++ b/tools/niminst/niminst.nim
@@ -27,7 +27,6 @@ const
 
 type
   TAppType = enum appConsole, appGUI
-  TTarget = enum tWin32 = 1, tWin64 = 2
   TAction = enum
     actionNone,   # action not yet known
     actionCSource # action: create C sources
@@ -103,6 +102,9 @@ proc firstBinPath(c: TConfigData): string =
 proc `\`(a, b: string): string =
   result = if a.len == 0: b else: a & '\\' & b
 
+proc slashify(s: string): string =
+  when defined(unix): s.replace('\\', '/') else: s.replace('/', '\\')
+
 proc skipRoot(f: string): string =
   # "abc/def/xyz" --> "def/xyz"
   var i = 0
@@ -382,33 +384,41 @@ proc removeDuplicateFiles(c: var TConfigData) =
           for cpuB in 1..c.cpus.len:
             if osB != osA or cpuB != cpuA:
               var orig = buildDir(osB, cpuB) / f
-              if ExistsFile(orig) and ExistsFile(dup) and
+              if existsFile(orig) and existsFile(dup) and
                   sameFileContent(orig, dup):
                 # file is identical, so delete duplicate:
-                RemoveFile(dup)
+                removeFile(dup)
                 c.cfiles[osA][cpuA][i] = orig
 
 proc writeInstallScripts(c: var TConfigData) =
   if c.installScript:
-    writeFile(installShFile, GenerateInstallScript(c), "\10")
+    writeFile(installShFile, generateInstallScript(c), "\10")
   if c.uninstallScript:
-    writeFile(deinstallShFile, GenerateDeinstallScript(c), "\10")
+    writeFile(deinstallShFile, generateDeinstallScript(c), "\10")
 
 proc srcdist(c: var TConfigData) =
   if not existsDir(getOutputDir(c) / "src"):
     createDir(getOutputDir(c) / "src")
   for x in walkFiles(c.libpath / "lib/*.h"):
     echo(getOutputDir(c) / "src" / extractFilename(x))
-    CopyFile(dest=getOutputDir(c) / "src" / extractFilename(x), source=x)
+    copyFile(dest=getOutputDir(c) / "src" / extractFilename(x), source=x)
+  var winIndex = -1
+  var intel32Index = -1
+  var intel64Index = -1
   for osA in 1..c.oses.len:
+    let osname = c.oses[osA-1]
+    if osname.cmpIgnoreStyle("windows") == 0: winIndex = osA-1
     for cpuA in 1..c.cpus.len:
+      let cpuname = c.cpus[cpuA-1]
+      if cpuname.cmpIgnoreStyle("i386") == 0: intel32Index = cpuA-1
+      elif cpuname.cmpIgnoreStyle("amd64") == 0: intel64Index = cpuA-1
       var dir = getOutputDir(c) / buildDir(osA, cpuA)
       if existsDir(dir): removeDir(dir)
       createDir(dir)
       var cmd = ("nimrod compile -f --symbolfiles:off --compileonly " &
                  "--gen_mapping --cc:gcc --skipUserCfg" &
                  " --os:$# --cpu:$# $# $#") %
-                 [c.oses[osA-1], c.cpus[cpuA-1], c.nimrodArgs,
+                 [osname, cpuname, c.nimrodArgs,
                  changeFileExt(c.infile, "nim")]
       echo(cmd)
       if execShellCmd(cmd) != 0:
@@ -417,18 +427,23 @@ proc srcdist(c: var TConfigData) =
       for i in 0 .. c.cfiles[osA][cpuA].len-1:
         let dest = dir / extractFilename(c.cfiles[osA][cpuA][i])
         let relDest = buildDir(osA, cpuA) / extractFilename(c.cfiles[osA][cpuA][i])
-        CopyFile(dest=dest, source=c.cfiles[osA][cpuA][i])
+        copyFile(dest=dest, source=c.cfiles[osA][cpuA][i])
         c.cfiles[osA][cpuA][i] = relDest
   # second pass: remove duplicate files
   removeDuplicateFiles(c)
-  writeFile(getOutputDir(c) / buildShFile, GenerateBuildShellScript(c), "\10")
-  writeFile(getOutputDir(c) / buildBatFile32, GenerateBuildBatchScript(c, tWin32), "\13\10")
-  writeFile(getOutputDir(c) / buildBatFile64, GenerateBuildBatchScript(c, tWin64), "\13\10")
+  writeFile(getOutputDir(c) / buildShFile, generateBuildShellScript(c), "\10")
+  if winIndex >= 0:
+    if intel32Index >= 0:
+      writeFile(getOutputDir(c) / buildBatFile32,
+                generateBuildBatchScript(c, winIndex, intel32Index), "\13\10")
+    if intel64Index >= 0:
+      writeFile(getOutputDir(c) / buildBatFile64,
+                generateBuildBatchScript(c, winIndex, intel64Index), "\13\10")
   writeInstallScripts(c)
 
 # --------------------- generate inno setup -----------------------------------
 proc setupDist(c: var TConfigData) =
-  var scrpt = GenerateInnoSetup(c)
+  var scrpt = generateInnoSetup(c)
   var n = "build" / "install_$#_$#.iss" % [toLower(c.name), c.version]
   writeFile(n, scrpt, "\13\10")
   when defined(windows):
@@ -437,7 +452,7 @@ proc setupDist(c: var TConfigData) =
     var outcmd = if c.outdir.len == 0: "build" else: c.outdir
     var cmd = "$# $# /O$# $#" % [quoteIfContainsWhite(c.innoSetup.path),
                                  c.innoSetup.flags, outcmd, n]
-    Echo(cmd)
+    echo(cmd)
     if execShellCmd(cmd) == 0:
       removeFile(n)
     else: