summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/installer.ini8
-rw-r--r--compiler/nim.nim4
-rw-r--r--config/nimrod.cfg136
-rw-r--r--doc/lib.txt9
-rw-r--r--examples/cross_calculator/nim_backend/backend.nim (renamed from examples/cross_calculator/nimrod_backend/backend.nim)0
-rw-r--r--examples/cross_calculator/nim_commandline/nim.cfg (renamed from examples/cross_todo/nimrod_commandline/nimrod.cfg)2
-rw-r--r--examples/cross_calculator/nim_commandline/nimcalculator.nim (renamed from examples/cross_calculator/nimrod_commandline/nimcalculator.nim)6
-rw-r--r--examples/cross_calculator/nim_commandline/readme.txt (renamed from examples/cross_calculator/nimrod_commandline/readme.txt)6
-rw-r--r--examples/cross_todo/nim_backend/backend.nim (renamed from examples/cross_todo/nimrod_backend/backend.nim)14
-rw-r--r--examples/cross_todo/nim_backend/readme.txt (renamed from examples/cross_todo/nimrod_backend/readme.txt)4
-rw-r--r--examples/cross_todo/nim_backend/testbackend.nim (renamed from examples/cross_todo/nimrod_backend/testbackend.nim)0
-rw-r--r--examples/cross_todo/nim_commandline/nim.cfg (renamed from examples/cross_calculator/nimrod_commandline/nimrod.cfg)2
-rw-r--r--examples/cross_todo/nim_commandline/nimtodo.nim (renamed from examples/cross_todo/nimrod_commandline/nimtodo.nim)10
-rw-r--r--examples/cross_todo/nim_commandline/readme.txt (renamed from examples/cross_todo/nimrod_commandline/readme.txt)0
-rw-r--r--icons/nim.ico (renamed from icons/nimrod.ico)bin30319 -> 30319 bytes
-rw-r--r--icons/nim.rc3
-rw-r--r--icons/nim.res (renamed from icons/nimrod.res)bin30830 -> 30830 bytes
-rw-r--r--icons/nim_icon.o (renamed from icons/nimrod_icon.o)bin30830 -> 30830 bytes
-rw-r--r--icons/nimrod.rc3
-rw-r--r--lib/pure/basic3d.nim2
-rw-r--r--lib/pure/collections/sets.nim14
-rw-r--r--lib/pure/collections/tables.nim218
-rw-r--r--lib/pure/matchers.nim2
-rw-r--r--lib/pure/unicode.nim5
-rw-r--r--lib/system/threads.nim4
-rw-r--r--readme.md2
-rw-r--r--tests/collections/ttables.nim2
-rw-r--r--tests/manyloc/argument_parser/argument_parser.nim2
-rw-r--r--tests/manyloc/keineschweine/enet_server/nim.cfg (renamed from tests/manyloc/keineschweine/enet_server/nimrod.cfg)0
-rw-r--r--tests/manyloc/keineschweine/server/nim.cfg (renamed from tests/manyloc/keineschweine/server/nimrod.cfg)0
-rw-r--r--tests/rodfiles/nim.cfg (renamed from tests/rodfiles/nimrod.cfg)0
-rw-r--r--tools/niminst/nsis.tmpl4
-rw-r--r--web/website.ini1
33 files changed, 209 insertions, 254 deletions
diff --git a/compiler/installer.ini b/compiler/installer.ini
index dcf9aa52f..48cd0b3b9 100644
--- a/compiler/installer.ini
+++ b/compiler/installer.ini
@@ -51,10 +51,10 @@ Files: "configure;makefile"
 Files: "*.ini"
 Files: "koch.nim"
 
-Files: "icons/nimrod.ico"
-Files: "icons/nimrod.rc"
-Files: "icons/nimrod.res"
-Files: "icons/nimrod_icon.o"
+Files: "icons/nim.ico"
+Files: "icons/nim.rc"
+Files: "icons/nim.res"
+Files: "icons/nim_icon.o"
 Files: "icons/koch.ico"
 Files: "icons/koch.rc"
 Files: "icons/koch.res"
diff --git a/compiler/nim.nim b/compiler/nim.nim
index 617758b2d..215f1986e 100644
--- a/compiler/nim.nim
+++ b/compiler/nim.nim
@@ -9,9 +9,9 @@
 
 when defined(gcc) and defined(windows):
   when defined(x86):
-    {.link: "icons/nimrod.res".}
+    {.link: "icons/nim.res".}
   else:
-    {.link: "icons/nimrod_icon.o".}
+    {.link: "icons/nim_icon.o".}
 
 import
   commands, lexer, condsyms, options, msgs, nversion, nimconf, ropes,
diff --git a/config/nimrod.cfg b/config/nimrod.cfg
deleted file mode 100644
index 62a7b16cc..000000000
--- a/config/nimrod.cfg
+++ /dev/null
@@ -1,136 +0,0 @@
-# Configuration file for the Nim Compiler.
-# (c) 2015 Andreas Rumpf
-
-# Feel free to edit the default values as you need.
-
-# You may set environment variables with
-# @putenv "key" "val"
-# Environment variables cannot be used in the options, however!
-
-cc = gcc
-
-# example of how to setup a cross-compiler:
-arm.linux.gcc.exe = "arm-linux-gcc"
-arm.linux.gcc.linkerexe = "arm-linux-gcc"
-
-cs:partial
-
-path="$lib/core"
-path="$lib/pure"
-path="$lib/pure/collections"
-path="$lib/pure/concurrency"
-path="$lib/impure"
-path="$lib/wrappers"
-# path="$lib/wrappers/cairo"
-# path="$lib/wrappers/gtk"
-# path="$lib/wrappers/lua"
-# path="$lib/wrappers/opengl"
-path="$lib/wrappers/pcre"
-path="$lib/wrappers/readline"
-path="$lib/wrappers/sdl"
-# path="$lib/wrappers/x11"
-path="$lib/wrappers/zip"
-path="$lib/wrappers/libffi"
-path="$lib/windows"
-path="$lib/posix"
-path="$lib/js"
-path="$lib/pure/unidecode"
-
-@if nimbabel:
-  babelpath="$home/.babel/pkgs/"
-@end
-
-@if release or quick:
-  obj_checks:off
-  field_checks:off
-  range_checks:off
-  bound_checks:off
-  overflow_checks:off
-  assertions:off
-  stacktrace:off
-  linetrace:off
-  debugger:off
-  line_dir:off
-  dead_code_elim:on
-@end
-
-@if release:
-  opt:speed
-@end
-
-# additional options always passed to the compiler:
---parallel_build: "0" # 0 to auto-detect number of processors
-
-hint[LineTooLong]=off
-#hint[XDeclaredButNotUsed]=off
-
-@if unix:
-  @if not bsd:
-    # -fopenmp
-    gcc.options.linker = "-ldl"
-    gpp.options.linker = "-ldl"
-    clang.options.linker = "-ldl"
-    tcc.options.linker = "-ldl"
-  @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:
-    tlsEmulation:on
-  @end
-@end
-
-# Configuration for the Intel C/C++ compiler:
-@if windows:
-  icl.options.speed = "/Ox /arch:SSE2"
-  icl.options.always = "/nologo"
-@end
-
-# Configuration for the GNU C/C++ compiler:
-@if windows:
-  #gcc.path = r"$nimrod\dist\mingw\bin"
-  @if gcc:
-    tlsEmulation:on
-  @end
-@end
-
-@if macosx:
-  cc = clang
-  tlsEmulation:on
-  gcc.options.always = "-w -fasm-blocks"
-  gpp.options.always = "-w -fasm-blocks -fpermissive"
-@else:
-  gcc.options.always = "-w"
-  gpp.options.always = "-w -fpermissive"
-@end
-
-gcc.options.speed = "-O3 -fno-strict-aliasing"
-gcc.options.size = "-Os"
-gcc.options.debug = "-g3 -O0"
-
-gpp.options.speed = "-O3 -fno-strict-aliasing"
-gpp.options.size = "-Os"
-gpp.options.debug = "-g3 -O0"
-#passl = "-pg"
-
-# Configuration for the LLVM GCC compiler:
-llvm_gcc.options.debug = "-g"
-llvm_gcc.options.always = "-w"
-llvm_gcc.options.speed = "-O2"
-llvm_gcc.options.size = "-Os"
-
-# Configuration for the LLVM CLang compiler:
-clang.options.debug = "-g"
-clang.options.always = "-w"
-clang.options.speed = "-O3"
-clang.options.size = "-Os"
-
-# Configuration for the Visual C/C++ compiler:
-vcc.options.linker = "/DEBUG /Zi /Fd\"$projectName.pdb\" /F33554432" # set the stack size to 8 MB
-vcc.options.debug = "/Zi /Fd\"$projectName.pdb\""
-vcc.options.always = "/nologo"
-vcc.options.speed = "/Ox /arch:SSE2"
-vcc.options.size = "/O1"
-
-# Configuration for the Tiny C Compiler:
-tcc.options.always = "-w"
diff --git a/doc/lib.txt b/doc/lib.txt
index b7c94b505..4185e6f74 100644
--- a/doc/lib.txt
+++ b/doc/lib.txt
@@ -189,6 +189,12 @@ Math libraries
   Floating-point environment. Handling of floating-point rounding and
   exceptions (overflow, zero-devide, etc.).
 
+* `basic2d <basic2d.html>`_
+  Basic 2d support with vectors, points, matrices and some basic utilities.
+
+* `basic3d <basic3d.html>`_
+  Basic 3d support with vectors, points, matrices and some basic utilities.
+
 
 Internet Protocols and Support
 ------------------------------
@@ -218,9 +224,6 @@ Internet Protocols and Support
 * `smtp <smtp.html>`_
   This module implement a simple SMTP client. 
 
-* `irc <irc.html>`_
-  This module implements an asynchronous IRC client.
-
 * `ftpclient <ftpclient.html>`_
   This module implements an FTP client.
 
diff --git a/examples/cross_calculator/nimrod_backend/backend.nim b/examples/cross_calculator/nim_backend/backend.nim
index ffa4311f9..ffa4311f9 100644
--- a/examples/cross_calculator/nimrod_backend/backend.nim
+++ b/examples/cross_calculator/nim_backend/backend.nim
diff --git a/examples/cross_todo/nimrod_commandline/nimrod.cfg b/examples/cross_calculator/nim_commandline/nim.cfg
index c1aedcf6a..41c034430 100644
--- a/examples/cross_todo/nimrod_commandline/nimrod.cfg
+++ b/examples/cross_calculator/nim_commandline/nim.cfg
@@ -1,4 +1,4 @@
 # Nimrod configuration file.
 # The file is used only to add the path of the backend to the compiler options.
 
-path="../nimrod_backend"
+path="../nim_backend"
diff --git a/examples/cross_calculator/nimrod_commandline/nimcalculator.nim b/examples/cross_calculator/nim_commandline/nimcalculator.nim
index 440834ca8..69d62a90c 100644
--- a/examples/cross_calculator/nimrod_commandline/nimcalculator.nim
+++ b/examples/cross_calculator/nim_commandline/nimcalculator.nim
@@ -21,7 +21,7 @@ type
     cmdParams,          # Two valid parameters were provided
     cmdInteractive      # No parameters were provided, run interactive mode
 
-  TParamConfig = object of TObject
+  TParamConfig = object of RootObj
     action: TCommand      # store the type of operation
     paramA, paramB: int   # possibly store the valid parameters
 
@@ -63,7 +63,7 @@ proc parseCmdLine(): TParamConfig =
           stdout.write USAGE
           quit "Unexpected option: " & key, 2
       of cmdEnd: break
-  except EInvalidValue:
+  except ValueError:
     stdout.write USAGE
     quit "Invalid value " & val &  " for parameter " & key, 3
 
@@ -85,7 +85,7 @@ proc parseUserInput(question: string): int =
     try:
       result = input.parseInt
       break
-    except EInvalidValue:
+    except ValueError:
       if input.len < 1: quit "Blank line detected, quitting.", 0
       echo "Sorry, `$1' doesn't seem to be a valid integer" % input
 
diff --git a/examples/cross_calculator/nimrod_commandline/readme.txt b/examples/cross_calculator/nim_commandline/readme.txt
index 5430e7b47..f95bd962e 100644
--- a/examples/cross_calculator/nimrod_commandline/readme.txt
+++ b/examples/cross_calculator/nim_commandline/readme.txt
@@ -1,10 +1,10 @@
-In this directory you will find the nimrod commandline version of the
+In this directory you will find the nim commandline version of the
 cross-calculator sample.
 
 The commandline interface can be used non interactively through switches, or
 interactively when running the command without parameters.
 
 Compilation is fairly easy despite having the source split in different
-directories. Thanks to the nimrod.cfg file, which adds the ../nimrod_backend
+directories. Thanks to the nim.cfg file, which adds the ../nim_backend
 directory as a search path, you can compile and run the example just fine from
-the command line with 'nimrod c -r nimcalculator.nim'.
+the command line with 'nim c -r nimcalculator.nim'.
diff --git a/examples/cross_todo/nimrod_backend/backend.nim b/examples/cross_todo/nim_backend/backend.nim
index 89e7d0b7e..9c7d2bafa 100644
--- a/examples/cross_todo/nimrod_backend/backend.nim
+++ b/examples/cross_todo/nim_backend/backend.nim
@@ -13,7 +13,7 @@ type
     text*: string             ## Description of the task to do.
     priority*: int            ## The priority can be any user defined integer.
     isDone*: bool             ## Done todos are still kept marked.
-    modificationDate: TTime   ## The modification time can't be modified from
+    modificationDate: Time    ## The modification time can't be modified from
                               ## outside of this module, use the
                               ## getModificationDate accessor.
 
@@ -64,7 +64,7 @@ proc openDatabase*(path: string): TDbConn =
 # - Procs related to TTodo objects
 #
 proc initFromDB(id: int64; text: string; priority: int, isDone: bool;
-               modificationDate: TTime): TTodo =
+               modificationDate: Time): TTodo =
   ## Returns an initialized TTodo object created from database parameters.
   ##
   ## The proc assumes all values are right. Note this proc is NOT exported.
@@ -81,7 +81,7 @@ proc getId*(todo: TTodo): int64 =
   return todo.id
 
 
-proc getModificationDate*(todo: TTodo): TTime =
+proc getModificationDate*(todo: TTodo): Time =
   ## Returns the last modification date of a TTodo entry.
   return todo.modificationDate
 
@@ -99,14 +99,14 @@ proc update*(todo: var TTodo; conn: TDbConn): bool =
     FROM Todos WHERE id = ?"""
 
   try:
-    let rows = conn.GetAllRows(query, $todo.id)
+    let rows = conn.getAllRows(query, $todo.id)
     if len(rows) < 1:
       return
     assert(1 == len(rows), "Woah, didn't expect so many rows")
     todo.text = rows[0][0]
     todo.priority = rows[0][1].parseInt
     todo.isDone = rows[0][2].parseBool
-    todo.modificationDate = TTime(rows[0][3].parseInt)
+    todo.modificationDate = Time(rows[0][3].parseInt)
     result = true
   except:
     echo("Something went wrong selecting for id " & $todo.id)
@@ -202,12 +202,12 @@ proc getPagedTodos*(conn: TDbConn; params: TPagedParams;
   #echo("Query " & string(query))
   #echo("args: " & args.join(", "))
 
-  var newId: biggestInt
+  var newId: BiggestInt
   for row in conn.fastRows(query, args):
     let numChars = row[0].parseBiggestInt(newId)
     assert(numChars > 0, "Huh, couldn't parse identifier from database?")
     result.add(initFromDB(int64(newId), row[1], row[2].parseInt,
-        row[3].parseBool, TTime(row[4].parseInt)))
+        row[3].parseBool, Time(row[4].parseInt)))
 
 
 proc getTodo*(conn: TDbConn; todoId: int64): ref TTodo =
diff --git a/examples/cross_todo/nimrod_backend/readme.txt b/examples/cross_todo/nim_backend/readme.txt
index 6529f2e67..16cb592fc 100644
--- a/examples/cross_todo/nimrod_backend/readme.txt
+++ b/examples/cross_todo/nim_backend/readme.txt
@@ -1,4 +1,4 @@
-This directory contains the nimrod backend code for the todo cross platform

+This directory contains the nim backend code for the todo cross platform

 example.

 

 Unlike the cross platform calculator example, this backend features more code,

@@ -8,7 +8,7 @@ The test is not embedded directly in the backend.nim file to avoid being able
 to access internal data types and procs not exported and replicate the

 environment of client code.

 

-In a bigger project with several people you could run `nimrod doc backend.nim`

+In a bigger project with several people you could run `nim doc backend.nim`

 (or use the doc2 command for a whole project) and provide the generated html

 documentation to another programer for her to implement an interface without

 having to look at the source code.

diff --git a/examples/cross_todo/nimrod_backend/testbackend.nim b/examples/cross_todo/nim_backend/testbackend.nim
index 131dda1cf..131dda1cf 100644
--- a/examples/cross_todo/nimrod_backend/testbackend.nim
+++ b/examples/cross_todo/nim_backend/testbackend.nim
diff --git a/examples/cross_calculator/nimrod_commandline/nimrod.cfg b/examples/cross_todo/nim_commandline/nim.cfg
index c1aedcf6a..41c034430 100644
--- a/examples/cross_calculator/nimrod_commandline/nimrod.cfg
+++ b/examples/cross_todo/nim_commandline/nim.cfg
@@ -1,4 +1,4 @@
 # Nimrod configuration file.
 # The file is used only to add the path of the backend to the compiler options.
 
-path="../nimrod_backend"
+path="../nim_backend"
diff --git a/examples/cross_todo/nimrod_commandline/nimtodo.nim b/examples/cross_todo/nim_commandline/nimtodo.nim
index 1067177c3..4ab17e7a2 100644
--- a/examples/cross_todo/nimrod_commandline/nimtodo.nim
+++ b/examples/cross_todo/nim_commandline/nimtodo.nim
@@ -69,11 +69,11 @@ template parseTodoIdAndSetCommand(newCommand: TCommand): stmt =
   ## Helper to parse a big todo identifier into todoId and set command.
   try:
     let numChars = val.parseBiggestInt(newId)
-    if numChars < 1: raise newException(EInvalidValue, "Empty string?")
+    if numChars < 1: raise newException(ValueError, "Empty string?")
     result.command = newCommand
     result.todoId = newId
-  except EOverflow:
-    raise newException(EInvalidValue, "Value $1 too big" % val)
+  except OverflowError:
+    raise newException(ValueError, "Value $1 too big" % val)
 
 
 template verifySingleCommand(actions: stmt): stmt =
@@ -111,7 +111,7 @@ proc parseCmdLine(): TParamConfig =
     usesListParams = false
     p = initOptParser()
     key, val: TaintedString
-    newId: biggestInt
+    newId: BiggestInt
 
   result.initDefaults
 
@@ -178,7 +178,7 @@ proc parseCmdLine(): TParamConfig =
           abort("Unexpected option '$1'." % [key], 6)
       of cmdEnd:
         break
-  except EInvalidValue:
+  except ValueError:
     abort("Invalid integer value '$1' for parameter '$2'." % [val, key], 7)
 
   if not specifiedCommand:
diff --git a/examples/cross_todo/nimrod_commandline/readme.txt b/examples/cross_todo/nim_commandline/readme.txt
index ca4b67521..ca4b67521 100644
--- a/examples/cross_todo/nimrod_commandline/readme.txt
+++ b/examples/cross_todo/nim_commandline/readme.txt
diff --git a/icons/nimrod.ico b/icons/nim.ico
index 58cc4314c..58cc4314c 100644
--- a/icons/nimrod.ico
+++ b/icons/nim.ico
Binary files differdiff --git a/icons/nim.rc b/icons/nim.rc
new file mode 100644
index 000000000..c053e08e9
--- /dev/null
+++ b/icons/nim.rc
@@ -0,0 +1,3 @@
+nimicon ICON "nim.ico"
+
+
diff --git a/icons/nimrod.res b/icons/nim.res
index 6eddd053b..6eddd053b 100644
--- a/icons/nimrod.res
+++ b/icons/nim.res
Binary files differdiff --git a/icons/nimrod_icon.o b/icons/nim_icon.o
index c8c364412..c8c364412 100644
--- a/icons/nimrod_icon.o
+++ b/icons/nim_icon.o
Binary files differdiff --git a/icons/nimrod.rc b/icons/nimrod.rc
deleted file mode 100644
index 6f36b8145..000000000
--- a/icons/nimrod.rc
+++ /dev/null
@@ -1,3 +0,0 @@
-nimrodicon ICON "nimrod.ico"
-
-
diff --git a/lib/pure/basic3d.nim b/lib/pure/basic3d.nim
index c00764fc5..9a8e006ec 100644
--- a/lib/pure/basic3d.nim
+++ b/lib/pure/basic3d.nim
@@ -812,7 +812,7 @@ proc bisect*(v1,v2:TVector3d):TVector3d {.noInit.}=
   ## Computes the bisector between v1 and v2 as a normalized vector.
   ## If one of the input vectors has zero length, a normalized version
   ## of the other is returned. If both input vectors has zero length, 
-  ## an arbitrary normalized vector `v1`is returned.
+  ## an arbitrary normalized vector `v1` is returned.
   var
     vmag1=v1.len
     vmag2=v2.len
diff --git a/lib/pure/collections/sets.nim b/lib/pure/collections/sets.nim
index 33fec1a18..4a20d00a4 100644
--- a/lib/pure/collections/sets.nim
+++ b/lib/pure/collections/sets.nim
@@ -276,7 +276,7 @@ proc excl*[A](s: var HashSet[A], key: A) =
         if isEmpty(s.data[i].hcode):   # end of collision cluster; So all done
           return
         r = s.data[i].hcode and msk    # "home" location of key@i
-      s.data[j] = s.data[i]            # data[j] will be marked EMPTY next loop
+      shallowCopy(s.data[j], s.data[i]) # data[j] will be marked EMPTY next loop
 
 proc excl*[A](s: var HashSet[A], other: HashSet[A]) =
   ## Excludes everything in `other` from `s`.
@@ -313,9 +313,9 @@ proc init*[A](s: var HashSet[A], initialSize=64) =
   ## Initializes a hash set.
   ##
   ## The `initialSize` parameter needs to be a power of two. You can use
-  ## `math.nextPowerOfTwo() <math.html#nextPowerOfTwo>`_ to guarantee that at
-  ## runtime. All set variables have to be initialized before you can use them
-  ## with other procs from this module with the exception of `isValid()
+  ## `math.nextPowerOfTwo() <math.html#nextPowerOfTwo>`_ or `rightSize` to
+  ## guarantee that at runtime. All set variables must be initialized before
+  ## use with other procs from this module with the exception of `isValid()
   ## <#isValid,TSet[A]>`_ and `len() <#len,TSet[A]>`_.
   ##
   ## You can call this proc on a previously initialized hash set, which will
@@ -719,9 +719,9 @@ proc init*[A](s: var OrderedSet[A], initialSize=64) =
   ## Initializes an ordered hash set.
   ##
   ## The `initialSize` parameter needs to be a power of two. You can use
-  ## `math.nextPowerOfTwo() <math.html#nextPowerOfTwo>`_ to guarantee that at
-  ## runtime. All set variables have to be initialized before you can use them
-  ## with other procs from this module with the exception of `isValid()
+  ## `math.nextPowerOfTwo() <math.html#nextPowerOfTwo>`_ or `rightSize` to
+  ## guarantee that at runtime. All set variables must be initialized before
+  ## use with other procs from this module with the exception of `isValid()
   ## <#isValid,TOrderedSet[A]>`_ and `len() <#len,TOrderedSet[A]>`_.
   ##
   ## You can call this proc on a previously initialized ordered hash set to
diff --git a/lib/pure/collections/tables.nim b/lib/pure/collections/tables.nim
index 671f767cf..25fe306c0 100644
--- a/lib/pure/collections/tables.nim
+++ b/lib/pure/collections/tables.nim
@@ -71,8 +71,7 @@ import
 {.pragma: myShallow.}
 
 type
-  SlotEnum = enum seEmpty, seFilled, seDeleted
-  KeyValuePair[A, B] = tuple[slot: SlotEnum, key: A, val: B]
+  KeyValuePair[A, B] = tuple[hcode: THash, key: A, val: B]
   KeyValuePairSeq[A, B] = seq[KeyValuePair[A, B]]
   Table* {.myShallow.}[A, B] = object ## generic hash table
     data: KeyValuePairSeq[A, B]
@@ -84,6 +83,14 @@ type
 when not defined(nimhygiene):
   {.pragma: dirty.}
 
+# hcode for real keys cannot be zero.  hcode==0 signifies an empty slot.  These
+# two procs retain clarity of that encoding without the space cost of an enum.
+proc isEmpty(hcode: THash): bool {.inline.} =
+  result = hcode == 0
+
+proc isFilled(hcode: THash): bool {.inline.} =
+  result = hcode != 0
+
 proc len*[A, B](t: Table[A, B]): int =
   ## returns the number of keys in `t`.
   result = t.counter
@@ -91,28 +98,28 @@ proc len*[A, B](t: Table[A, B]): int =
 iterator pairs*[A, B](t: Table[A, B]): tuple[key: A, val: B] =
   ## iterates over any (key, value) pair in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield (t.data[h].key, t.data[h].val)
+    if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
 
 iterator mpairs*[A, B](t: var Table[A, B]): tuple[key: A, val: var B] =
   ## iterates over any (key, value) pair in the table `t`. The values
   ## can be modified.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield (t.data[h].key, t.data[h].val)
+    if isFilled(t.data[h].slot): yield (t.data[h].key, t.data[h].val)
 
 iterator keys*[A, B](t: Table[A, B]): A =
   ## iterates over any key in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].key
+    if isFilled(t.data[h].hcode): yield t.data[h].key
 
 iterator values*[A, B](t: Table[A, B]): B =
   ## iterates over any value in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].val
+    if isFilled(t.data[h].hcode): yield t.data[h].val
 
 iterator mvalues*[A, B](t: var Table[A, B]): var B =
   ## iterates over any value in the table `t`. The values can be modified.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].val
+    if isFilled(t.data[h].hcode): yield t.data[h].val
 
 const
   growthFactor = 2
@@ -121,26 +128,57 @@ proc mustRehash(length, counter: int): bool {.inline.} =
   assert(length > counter)
   result = (length * 2 < counter * 3) or (length - counter < 4)
 
+proc rightSize*(count: int): int {.inline.} =
+  ## Return the value of `initialSize` to support `count` items.
+  ##
+  ## If more items are expected to be added, simply add that
+  ## expected extra amount to the parameter before calling this.
+  ##
+  ## Internally, we want mustRehash(rightSize(x), x) == false.
+  result = nextPowerOfTwo(count * 3 div 2  +  4)
+
 proc nextTry(h, maxHash: THash): THash {.inline.} =
-  result = ((5 * h) + 1) and maxHash
+  result = (h + 1) and maxHash
+
+template rawGetKnownHCImpl() {.dirty.} =
+  var h: THash = hc and high(t.data)   # start with real hash value
+  while isFilled(t.data[h].hcode):
+    # Compare hc THEN key with boolean short circuit. This makes the common case
+    # zero ==key's for missing (e.g.inserts) and exactly one ==key for present.
+    # It does slow down succeeding lookups by one extra THash cmp&and..usually
+    # just a few clock cycles, generally worth it for any non-integer-like A.
+    if t.data[h].hcode == hc and t.data[h].key == key:
+      return h
+    h = nextTry(h, high(t.data))
+  result = -1 - h                   # < 0 => MISSING; insert idx = -1 - result
 
 template rawGetImpl() {.dirty.} =
-  var h: THash = hash(key) and high(t.data) # start with real hash value
-  while t.data[h].slot != seEmpty:
-    if t.data[h].key == key and t.data[h].slot == seFilled:
-      return h
+  hc = hash(key)
+  if hc == 0:       # This almost never taken branch should be very predictable.
+    hc = 314159265  # Value doesn't matter; Any non-zero favorite is fine.
+  rawGetKnownHCImpl()
+
+template rawGetDeepImpl() {.dirty.} =   # Search algo for unconditional add
+  hc = hash(key)
+  if hc == 0:
+    hc = 314159265
+  var h: THash = hc and high(t.data)
+  while isFilled(t.data[h].hcode):
     h = nextTry(h, high(t.data))
-  result = -1
+  result = h
 
 template rawInsertImpl() {.dirty.} =
-  var h: THash = hash(key) and high(data)
-  while data[h].slot == seFilled:
-    h = nextTry(h, high(data))
   data[h].key = key
   data[h].val = val
-  data[h].slot = seFilled
+  data[h].hcode = hc
+
+proc rawGetKnownHC[A, B](t: Table[A, B], key: A, hc: THash): int {.inline.} =
+  rawGetKnownHCImpl()
+
+proc rawGetDeep[A, B](t: Table[A, B], key: A, hc: var THash): int {.inline.} =
+  rawGetDeepImpl()
 
-proc rawGet[A, B](t: Table[A, B], key: A): int =
+proc rawGet[A, B](t: Table[A, B], key: A, hc: var THash): int {.inline.} =
   rawGetImpl()
 
 proc `[]`*[A, B](t: Table[A, B], key: A): B =
@@ -148,55 +186,68 @@ proc `[]`*[A, B](t: Table[A, B], key: A): B =
   ## default empty value for the type `B` is returned
   ## and no exception is raised. One can check with ``hasKey`` whether the key
   ## exists.
-  var index = rawGet(t, key)
+  var hc: THash
+  var index = rawGet(t, key, hc)
   if index >= 0: result = t.data[index].val
 
 proc mget*[A, B](t: var Table[A, B], key: A): var B =
   ## retrieves the value at ``t[key]``. The value can be modified.
   ## If `key` is not in `t`, the ``EInvalidKey`` exception is raised.
-  var index = rawGet(t, key)
+  var hc: THash
+  var index = rawGet(t, key, hc)
   if index >= 0: result = t.data[index].val
   else: raise newException(KeyError, "key not found: " & $key)
 
 iterator allValues*[A, B](t: Table[A, B]; key: A): B =
   ## iterates over any value in the table `t` that belongs to the given `key`.
   var h: THash = hash(key) and high(t.data)
-  while t.data[h].slot != seEmpty:
-    if t.data[h].key == key and t.data[h].slot == seFilled:
+  while isFilled(t.data[h].hcode):
+    if t.data[h].key == key:
       yield t.data[h].val
     h = nextTry(h, high(t.data))
 
 proc hasKey*[A, B](t: Table[A, B], key: A): bool =
   ## returns true iff `key` is in the table `t`.
-  result = rawGet(t, key) >= 0
+  var hc: THash
+  result = rawGet(t, key, hc) >= 0
 
 proc rawInsert[A, B](t: var Table[A, B], data: var KeyValuePairSeq[A, B],
-                     key: A, val: B) =
+                     key: A, val: B, hc: THash, h: THash) =
   rawInsertImpl()
 
 proc enlarge[A, B](t: var Table[A, B]) =
   var n: KeyValuePairSeq[A, B]
   newSeq(n, len(t.data) * growthFactor)
-  for i in countup(0, high(t.data)):
-    if t.data[i].slot == seFilled: rawInsert(t, n, t.data[i].key, t.data[i].val)
   swap(t.data, n)
+  for i in countup(0, high(n)):
+    if isFilled(n[i].hcode):
+      var j = -1 - rawGetKnownHC(t, n[i].key, n[i].hcode)
+      rawInsert(t, t.data, n[i].key, n[i].val, n[i].hcode, j)
 
 template addImpl() {.dirty.} =
   if mustRehash(len(t.data), t.counter): enlarge(t)
-  rawInsert(t, t.data, key, val)
+  var hc: THash
+  var j = rawGetDeep(t, key, hc)
+  rawInsert(t, t.data, key, val, hc, j)
   inc(t.counter)
 
 template putImpl() {.dirty.} =
-  var index = rawGet(t, key)
+  var hc: THash
+  var index = rawGet(t, key, hc)
   if index >= 0:
     t.data[index].val = val
   else:
-    addImpl()
+    if mustRehash(len(t.data), t.counter):
+        enlarge(t)
+        index = rawGetKnownHC(t, key, hc)
+    rawInsert(t, t.data, key, val, hc, -1 - index)
+    inc(t.counter)
 
 when false:
   # not yet used:
   template hasKeyOrPutImpl() {.dirty.} =
-    var index = rawGet(t, key)
+    var hc: THash
+    var index = rawGet(t, key, hc)
     if index >= 0:
       t.data[index].val = val
       result = true
@@ -213,20 +264,37 @@ proc `[]=`*[A, B](t: var Table[A, B], key: A, val: B) =
 proc add*[A, B](t: var Table[A, B], key: A, val: B) =
   ## puts a new (key, value)-pair into `t` even if ``t[key]`` already exists.
   addImpl()
-  
+
+template doWhile(a: expr, b: stmt): stmt =
+  while true:
+    b
+    if not a: break
+
 proc del*[A, B](t: var Table[A, B], key: A) =
   ## deletes `key` from hash table `t`.
-  let index = rawGet(t, key)
-  if index >= 0:
-    t.data[index].slot = seDeleted
+  var hc: THash
+  var i = rawGet(t, key, hc)
+  let msk = high(t.data)
+  if i >= 0:
+    t.data[i].hcode = 0
     dec(t.counter)
+    while true:         # KnuthV3 Algo6.4R adapted for i=i+1 instead of i=i-1
+      var j = i         # The correctness of this depends on (h+1) in nextTry,
+      var r = j         # though may be adaptable to other simple sequences.
+      t.data[i].hcode = 0              # mark current EMPTY
+      doWhile ((i >= r and r > j) or (r > j and j > i) or (j > i and i >= r)):
+        i = (i + 1) and msk            # increment mod table size
+        if isEmpty(t.data[i].hcode):   # end of collision cluster; So all done
+          return
+        r = t.data[i].hcode and msk    # "home" location of key@i
+      shallowCopy(t.data[j], t.data[i]) # data[j] will be marked EMPTY next loop
 
 proc initTable*[A, B](initialSize=64): Table[A, B] =
   ## creates a new hash table that is empty.
   ##
   ## `initialSize` needs to be a power of two. If you need to accept runtime
   ## values for this you could use the ``nextPowerOfTwo`` proc from the
-  ## `math <math.html>`_ module.
+  ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
   assert isPowerOfTwo(initialSize)
   result.counter = 0
   newSeq(result.data, initialSize)
@@ -234,7 +302,7 @@ proc initTable*[A, B](initialSize=64): Table[A, B] =
 proc toTable*[A, B](pairs: openArray[tuple[key: A, 
                     val: B]]): Table[A, B] =
   ## creates a new hash table that contains the given `pairs`.
-  result = initTable[A, B](nextPowerOfTwo(pairs.len+10))
+  result = initTable[A, B](rightSize(pairs.len))
   for key, val in items(pairs): result[key] = val
 
 template dollarImpl(): stmt {.dirty.} =
@@ -252,7 +320,7 @@ template dollarImpl(): stmt {.dirty.} =
 proc `$`*[A, B](t: Table[A, B]): string =
   ## The `$` operator for hash tables.
   dollarImpl()
-  
+
 template equalsImpl() =
   if s.counter == t.counter:
     # different insertion orders mean different 'data' seqs, so we have
@@ -262,10 +330,10 @@ template equalsImpl() =
       if not t.hasKey(key): return false
       if t[key] != val: return false
     return true
-  
+
 proc `==`*[A, B](s, t: Table[A, B]): bool =
   equalsImpl()
-  
+
 proc indexBy*[A, B, C](collection: A, index: proc(x: B): C): Table[C, B] =
   ## Index the collection with the proc provided.
   # TODO: As soon as supported, change collection: A to collection: A[B]
@@ -280,28 +348,28 @@ proc len*[A, B](t: TableRef[A, B]): int =
 iterator pairs*[A, B](t: TableRef[A, B]): tuple[key: A, val: B] =
   ## iterates over any (key, value) pair in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield (t.data[h].key, t.data[h].val)
+    if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
 
 iterator mpairs*[A, B](t: TableRef[A, B]): tuple[key: A, val: var B] =
   ## iterates over any (key, value) pair in the table `t`. The values
   ## can be modified.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield (t.data[h].key, t.data[h].val)
+    if isFilled(t.data[h].hcode): yield (t.data[h].key, t.data[h].val)
 
 iterator keys*[A, B](t: TableRef[A, B]): A =
   ## iterates over any key in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].key
+    if isFilled(t.data[h].hcode): yield t.data[h].key
 
 iterator values*[A, B](t: TableRef[A, B]): B =
   ## iterates over any value in the table `t`.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].val
+    if isFilled(t.data[h].hcode): yield t.data[h].val
 
 iterator mvalues*[A, B](t: TableRef[A, B]): var B =
   ## iterates over any value in the table `t`. The values can be modified.
   for h in 0..high(t.data):
-    if t.data[h].slot == seFilled: yield t.data[h].val
+    if isFilled(t.data[h].hcode): yield t.data[h].val
 
 proc `[]`*[A, B](t: TableRef[A, B], key: A): B =
   ## retrieves the value at ``t[key]``. If `key` is not in `t`,
@@ -326,7 +394,7 @@ proc `[]=`*[A, B](t: TableRef[A, B], key: A, val: B) =
 proc add*[A, B](t: TableRef[A, B], key: A, val: B) =
   ## puts a new (key, value)-pair into `t` even if ``t[key]`` already exists.
   t[].add(key, val)
-  
+
 proc del*[A, B](t: TableRef[A, B], key: A) =
   ## deletes `key` from hash table `t`.
   t[].del(key)
@@ -360,7 +428,7 @@ proc newTableFrom*[A, B, C](collection: A, index: proc(x: B): C): TableRef[C, B]
 
 type
   OrderedKeyValuePair[A, B] = tuple[
-    slot: SlotEnum, next: int, key: A, val: B]
+    hcode: THash, next: int, key: A, val: B]
   OrderedKeyValuePairSeq[A, B] = seq[OrderedKeyValuePair[A, B]]
   OrderedTable* {.
       myShallow.}[A, B] = object ## table that remembers insertion order
@@ -378,7 +446,7 @@ template forAllOrderedPairs(yieldStmt: stmt) {.dirty, immediate.} =
   var h = t.first
   while h >= 0:
     var nxt = t.data[h].next
-    if t.data[h].slot == seFilled: yieldStmt
+    if isFilled(t.data[h].hcode): yieldStmt
     h = nxt
 
 iterator pairs*[A, B](t: OrderedTable[A, B]): tuple[key: A, val: B] =
@@ -409,7 +477,13 @@ iterator mvalues*[A, B](t: var OrderedTable[A, B]): var B =
   forAllOrderedPairs:
     yield t.data[h].val
 
-proc rawGet[A, B](t: OrderedTable[A, B], key: A): int =
+proc rawGetKnownHC[A, B](t: OrderedTable[A, B], key: A, hc: THash): int =
+  rawGetKnownHCImpl()
+
+proc rawGetDeep[A, B](t: OrderedTable[A, B], key: A, hc: var THash): int {.inline.} =
+  rawGetDeepImpl()
+
+proc rawGet[A, B](t: OrderedTable[A, B], key: A, hc: var THash): int =
   rawGetImpl()
 
 proc `[]`*[A, B](t: OrderedTable[A, B], key: A): B =
@@ -417,23 +491,26 @@ proc `[]`*[A, B](t: OrderedTable[A, B], key: A): B =
   ## default empty value for the type `B` is returned
   ## and no exception is raised. One can check with ``hasKey`` whether the key
   ## exists.
-  var index = rawGet(t, key)
+  var hc: THash
+  var index = rawGet(t, key, hc)
   if index >= 0: result = t.data[index].val
 
 proc mget*[A, B](t: var OrderedTable[A, B], key: A): var B =
   ## retrieves the value at ``t[key]``. The value can be modified.
   ## If `key` is not in `t`, the ``EInvalidKey`` exception is raised.
-  var index = rawGet(t, key)
+  var hc: THash
+  var index = rawGet(t, key, hc)
   if index >= 0: result = t.data[index].val
   else: raise newException(KeyError, "key not found: " & $key)
 
 proc hasKey*[A, B](t: OrderedTable[A, B], key: A): bool =
   ## returns true iff `key` is in the table `t`.
-  result = rawGet(t, key) >= 0
+  var hc: THash
+  result = rawGet(t, key, hc) >= 0
 
 proc rawInsert[A, B](t: var OrderedTable[A, B], 
                      data: var OrderedKeyValuePairSeq[A, B],
-                     key: A, val: B) =
+                     key: A, val: B, hc: THash, h: THash) =
   rawInsertImpl()
   data[h].next = -1
   if t.first < 0: t.first = h
@@ -446,12 +523,13 @@ proc enlarge[A, B](t: var OrderedTable[A, B]) =
   var h = t.first
   t.first = -1
   t.last = -1
+  swap(t.data, n)
   while h >= 0:
-    var nxt = t.data[h].next
-    if t.data[h].slot == seFilled: 
-      rawInsert(t, n, t.data[h].key, t.data[h].val)
+    var nxt = n[h].next
+    if isFilled(n[h].hcode):
+      var j = -1 - rawGetKnownHC(t, n[h].key, n[h].hcode)
+      rawInsert(t, t.data, n[h].key, n[h].val, n[h].hcode, j)
     h = nxt
-  swap(t.data, n)
 
 proc `[]=`*[A, B](t: var OrderedTable[A, B], key: A, val: B) =
   ## puts a (key, value)-pair into `t`.
@@ -466,7 +544,7 @@ proc initOrderedTable*[A, B](initialSize=64): OrderedTable[A, B] =
   ##
   ## `initialSize` needs to be a power of two. If you need to accept runtime
   ## values for this you could use the ``nextPowerOfTwo`` proc from the
-  ## `math <math.html>`_ module.
+  ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
   assert isPowerOfTwo(initialSize)
   result.counter = 0
   result.first = -1
@@ -476,7 +554,7 @@ proc initOrderedTable*[A, B](initialSize=64): OrderedTable[A, B] =
 proc toOrderedTable*[A, B](pairs: openArray[tuple[key: A, 
                            val: B]]): OrderedTable[A, B] =
   ## creates a new ordered hash table that contains the given `pairs`.
-  result = initOrderedTable[A, B](nextPowerOfTwo(pairs.len+10))
+  result = initOrderedTable[A, B](rightSize(pairs.len))
   for key, val in items(pairs): result[key] = val
 
 proc `$`*[A, B](t: OrderedTable[A, B]): string =
@@ -537,7 +615,7 @@ template forAllOrderedPairs(yieldStmt: stmt) {.dirty, immediate.} =
   var h = t.first
   while h >= 0:
     var nxt = t.data[h].next
-    if t.data[h].slot == seFilled: yieldStmt
+    if isFilled(t.data[h].hcode): yieldStmt
     h = nxt
 
 iterator pairs*[A, B](t: OrderedTableRef[A, B]): tuple[key: A, val: B] =
@@ -597,14 +675,14 @@ proc newOrderedTable*[A, B](initialSize=64): OrderedTableRef[A, B] =
   ##
   ## `initialSize` needs to be a power of two. If you need to accept runtime
   ## values for this you could use the ``nextPowerOfTwo`` proc from the
-  ## `math <math.html>`_ module.
+  ## `math <math.html>`_ module or the ``rightSize`` proc from this module.
   new(result)
   result[] = initOrderedTable[A, B]()
 
 proc newOrderedTable*[A, B](pairs: openArray[tuple[key: A, 
                            val: B]]): OrderedTableRef[A, B] =
   ## creates a new ordered hash table that contains the given `pairs`.
-  result = newOrderedTable[A, B](nextPowerOfTwo(pairs.len+10))
+  result = newOrderedTable[A, B](rightSize(pairs.len))
   for key, val in items(pairs): result[key] = val
 
 proc `$`*[A, B](t: OrderedTableRef[A, B]): string =
@@ -665,7 +743,7 @@ proc rawGet[A](t: CountTable[A], key: A): int =
   while t.data[h].val != 0:
     if t.data[h].key == key: return h
     h = nextTry(h, high(t.data))
-  result = -1
+  result = -1 - h                   # < 0 => MISSING; insert idx = -1 - result
 
 proc `[]`*[A](t: CountTable[A], key: A): int =
   ## retrieves the value at ``t[key]``. If `key` is not in `t`,
@@ -702,21 +780,27 @@ proc enlarge[A](t: var CountTable[A]) =
 proc `[]=`*[A](t: var CountTable[A], key: A, val: int) =
   ## puts a (key, value)-pair into `t`. `val` has to be positive.
   assert val > 0
-  putImpl()
+  var h = rawGet(t, key)
+  if h >= 0:
+    t.data[h].val = val
+  else:
+    h = -1 - h
+    t.data[h].key = key
+    t.data[h].val = val
 
 proc initCountTable*[A](initialSize=64): CountTable[A] =
   ## creates a new count table that is empty.
   ##
   ## `initialSize` needs to be a power of two. If you need to accept runtime
   ## values for this you could use the ``nextPowerOfTwo`` proc from the
-  ## `math <math.html>`_ module.
+  ## `math <math.html>`_ module or the ``rightSize`` proc in this module.
   assert isPowerOfTwo(initialSize)
   result.counter = 0
   newSeq(result.data, initialSize)
 
 proc toCountTable*[A](keys: openArray[A]): CountTable[A] =
   ## creates a new count table with every key in `keys` having a count of 1.
-  result = initCountTable[A](nextPowerOfTwo(keys.len+10))
+  result = initCountTable[A](rightSize(keys.len))
   for key in items(keys): result[key] = 1
 
 proc `$`*[A](t: CountTable[A]): string =
@@ -827,13 +911,13 @@ proc newCountTable*[A](initialSize=64): CountTableRef[A] =
   ##
   ## `initialSize` needs to be a power of two. If you need to accept runtime
   ## values for this you could use the ``nextPowerOfTwo`` proc from the
-  ## `math <math.html>`_ module.
+  ## `math <math.html>`_ module or the ``rightSize`` method in this module.
   new(result)
   result[] = initCountTable[A](initialSize)
 
 proc newCountTable*[A](keys: openArray[A]): CountTableRef[A] =
   ## creates a new count table with every key in `keys` having a count of 1.
-  result = newCountTable[A](nextPowerOfTwo(keys.len+10))
+  result = newCountTable[A](rightSize(keys.len))
   for key in items(keys): result[key] = 1
 
 proc `$`*[A](t: CountTableRef[A]): string =
diff --git a/lib/pure/matchers.nim b/lib/pure/matchers.nim
index 1188be4ca..d55963c15 100644
--- a/lib/pure/matchers.nim
+++ b/lib/pure/matchers.nim
@@ -42,7 +42,7 @@ proc validEmailAddress*(s: string): bool {.noSideEffect,
   case toLower(x)
   of "com", "org", "net", "gov", "mil", "biz", "info", "mobi", "name",
      "aero", "jobs", "museum": return true
-  return false
+  else: return false
 
 proc parseInt*(s: string, value: var int, validRange: Slice[int]) {.
   noSideEffect, rtl, extern: "nmatchParseInt".} =
diff --git a/lib/pure/unicode.nim b/lib/pure/unicode.nim
index b892ec8b4..42e6a3195 100644
--- a/lib/pure/unicode.nim
+++ b/lib/pure/unicode.nim
@@ -1235,11 +1235,12 @@ proc reversed*(s: string): string =
   ## returns the reverse of `s`, interpreting it as unicode characters. Unicode
   ## combining characters are correctly interpreted as well:
   ##
-  ## .. code-block:
+  ## .. code-block:: nim
+  ##
   ##   assert reversed("Reverse this!") == "!siht esreveR"
   ##   assert reversed("先秦兩漢") == "漢兩秦先"
   ##   assert reversed("as⃝df̅") == "f̅ds⃝a"
-  ## assert reversed("a⃞b⃞c⃞") == "c⃞b⃞a⃞"
+  ##   assert reversed("a⃞b⃞c⃞") == "c⃞b⃞a⃞"
   var
     i = 0
     lastI = 0
diff --git a/lib/system/threads.nim b/lib/system/threads.nim
index 496c31af1..4e0720007 100644
--- a/lib/system/threads.nim
+++ b/lib/system/threads.nim
@@ -95,7 +95,9 @@ when defined(windows):
       importc: "TlsGetValue", stdcall, dynlib: "kernel32".}
   
 else:
-  {.passL: "-pthread".}
+  when not defined(macosx):
+    {.passL: "-pthread".}
+
   {.passC: "-pthread".}
 
   type
diff --git a/readme.md b/readme.md
index b08fa2291..2252ea52b 100644
--- a/readme.md
+++ b/readme.md
@@ -62,7 +62,7 @@ allowing you to create commercial applications.
 
 Read copying.txt for more details.
 
-Copyright (c) 2006-2014 Andreas Rumpf.
+Copyright (c) 2006-2015 Andreas Rumpf.
 All rights reserved.
 
 # Build Status
diff --git a/tests/collections/ttables.nim b/tests/collections/ttables.nim
index de4aaed5e..8534e6767 100644
--- a/tests/collections/ttables.nim
+++ b/tests/collections/ttables.nim
@@ -47,7 +47,7 @@ block tableTest1:
     for y in 0..1:
       assert t[(x,y)] == $x & $y
   assert($t == 
-    "{(x: 0, y: 0): 00, (x: 0, y: 1): 01, (x: 1, y: 0): 10, (x: 1, y: 1): 11}")
+    "{(x: 0, y: 1): 01, (x: 0, y: 0): 00, (x: 1, y: 0): 10, (x: 1, y: 1): 11}")
 
 block tableTest2:
   var t = initTable[string, float]()
diff --git a/tests/manyloc/argument_parser/argument_parser.nim b/tests/manyloc/argument_parser/argument_parser.nim
index af671cd85..a507a08e4 100644
--- a/tests/manyloc/argument_parser/argument_parser.nim
+++ b/tests/manyloc/argument_parser/argument_parser.nim
@@ -302,7 +302,7 @@ template build_specification_lookup():
   ## Returns the table used to keep pointers to all of the specifications.
   var result {.gensym.}: OrderedTable[string, ptr Tparameter_specification]
   result = initOrderedTable[string, ptr Tparameter_specification](
-    nextPowerOfTwo(expected.len))
+    tables.rightSize(expected.len))
   for i in 0..expected.len-1:
     for param_to_detect in expected[i].names:
       if result.hasKey(param_to_detect):
diff --git a/tests/manyloc/keineschweine/enet_server/nimrod.cfg b/tests/manyloc/keineschweine/enet_server/nim.cfg
index 72ef47ee0..72ef47ee0 100644
--- a/tests/manyloc/keineschweine/enet_server/nimrod.cfg
+++ b/tests/manyloc/keineschweine/enet_server/nim.cfg
diff --git a/tests/manyloc/keineschweine/server/nimrod.cfg b/tests/manyloc/keineschweine/server/nim.cfg
index fdc45a8e1..fdc45a8e1 100644
--- a/tests/manyloc/keineschweine/server/nimrod.cfg
+++ b/tests/manyloc/keineschweine/server/nim.cfg
diff --git a/tests/rodfiles/nimrod.cfg b/tests/rodfiles/nim.cfg
index 78fc8db64..78fc8db64 100644
--- a/tests/rodfiles/nimrod.cfg
+++ b/tests/rodfiles/nim.cfg
diff --git a/tools/niminst/nsis.tmpl b/tools/niminst/nsis.tmpl
index 23bbf3ac9..aba1e581f 100644
--- a/tools/niminst/nsis.tmpl
+++ b/tools/niminst/nsis.tmpl
@@ -50,8 +50,8 @@
   SetCompressor /SOLID /FINAL lzma
 
   ; Installer and Uninstaller Icons
-  ; Icon "nimrod.ico"
-  ; UninstallIcon "nimrod.ico"
+  ; Icon "nim.ico"
+  ; UninstallIcon "nim.ico"
 
   ; Set installation details to be shown by default
   ShowInstDetails show
diff --git a/web/website.ini b/web/website.ini
index c0a648c56..6757abcd8 100644
--- a/web/website.ini
+++ b/web/website.ini
@@ -61,6 +61,7 @@ srcdoc2: "pure/rawsockets;pure/asynchttpserver;pure/net;pure/selectors;pure/futu
 srcdoc2: "pure/md5"
 srcdoc2: "posix/posix"
 srcdoc2: "pure/fenv"
+srcdoc2: "pure/basic2d;pure/basic3d"
 
 ; Note: everything under 'webdoc' doesn't get listed in the index, so wrappers
 ; should live here