summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/commands.nim3
-rw-r--r--compiler/condsyms.nim46
-rw-r--r--compiler/llstream.nim2
-rw-r--r--compiler/nimrod.nim2
-rw-r--r--compiler/semexprs.nim14
-rw-r--r--compiler/testability.nim2
-rw-r--r--compiler/vm.nim4
-rw-r--r--doc/basicopt.txt1
-rw-r--r--lib/core/typeinfo.nim2
-rw-r--r--lib/impure/re.nim2
-rw-r--r--lib/pure/math.nim2
-rw-r--r--lib/pure/nimprof.nim10
-rw-r--r--lib/pure/os.nim18
-rw-r--r--lib/pure/osproc.nim2
-rw-r--r--lib/pure/parseopt.nim4
-rw-r--r--lib/pure/parseopt2.nim2
-rw-r--r--lib/pure/pegs.nim2
-rw-r--r--lib/pure/unittest.nim6
-rw-r--r--lib/system.nim39
-rw-r--r--lib/system/ansi_c.nim4
-rw-r--r--lib/system/arithm.nim12
-rw-r--r--lib/system/atomics.nim6
-rw-r--r--lib/system/channels.nim2
-rw-r--r--lib/system/deepcopy.nim2
-rw-r--r--lib/system/excpt.nim4
-rw-r--r--lib/system/gc.nim4
-rw-r--r--lib/system/gc2.nim2
-rw-r--r--lib/system/hti.nim2
-rw-r--r--lib/system/repr.nim12
-rw-r--r--lib/system/sysspawn.nim2
-rw-r--r--lib/system/sysstr.nim4
-rw-r--r--lib/system/threads.nim12
-rw-r--r--lib/system/widestrs.nim4
-rw-r--r--lib/wrappers/sdl/sdl_ttf.nim10
-rw-r--r--todo.txt2
-rw-r--r--web/news.txt4
36 files changed, 155 insertions, 96 deletions
diff --git a/compiler/commands.nim b/compiler/commands.nim
index 7219c168a..c15cc674c 100644
--- a/compiler/commands.nim
+++ b/compiler/commands.nim
@@ -315,6 +315,9 @@ proc processSwitch(switch, arg: string, pass: TCmdLinePass, info: TLineInfo) =
   of "undef", "u": 
     expectArg(switch, arg, pass, info)
     undefSymbol(arg)
+  of "symbol":
+    expectArg(switch, arg, pass, info)
+    declareSymbol(arg)  
   of "compile": 
     expectArg(switch, arg, pass, info)
     if pass in {passCmd2, passPP}: processCompile(arg)
diff --git a/compiler/condsyms.nim b/compiler/condsyms.nim
index 76026a59d..5eb951e26 100644
--- a/compiler/condsyms.nim
+++ b/compiler/condsyms.nim
@@ -19,6 +19,9 @@ var gSymbols: PStringTable
 proc defineSymbol*(symbol: string) = 
   gSymbols[symbol] = "true"
 
+proc declareSymbol*(symbol: string) = 
+  gSymbols[symbol] = "unknown"
+
 proc undefSymbol*(symbol: string) = 
   gSymbols[symbol] = "false"
 
@@ -27,6 +30,7 @@ proc isDefined*(symbol: string): bool =
     result = gSymbols[symbol] == "true"
   
 proc isDefined*(symbol: PIdent): bool = isDefined(symbol.s)
+proc isDeclared*(symbol: PIdent): bool = gSymbols.hasKey(symbol.s)
 
 iterator definedSymbolNames*: string =
   for key, val in pairs(gSymbols):
@@ -37,6 +41,36 @@ proc countDefinedSymbols*(): int =
   for key, val in pairs(gSymbols):
     if val == "true": inc(result)
 
+# For ease of bootstrapping, we keep there here and not in the global config
+# file for now:
+const
+  additionalSymbols = """
+    x86 itanium x8664
+    msdos mswindows win32 unix posix sunos bsd macintosh RISCOS doslike hpux
+    mac
+
+    hppa hp9000 hp9000s300 hp9000s700 hp9000s800 hp9000s820 ELATE sparcv9
+
+    ecmascript js nimrodvm nimffi nimdoc cpp objc
+    gcc llvmgcc clang lcc bcc dmc wcc vcc tcc pcc ucc icl
+    boehmgc gcmarkandsweep gcgenerational nogc gcUseBitvectors
+    endb profiler
+    executable guiapp consoleapp library dll staticlib
+
+    quick nimbabel
+    release debug
+    useWinAnsi useFork useNimRtl useMalloc useRealtimeGC ssl memProfiler
+    nodejs kwin
+
+    usesysassert usegcassert tinyC useFFI
+    useStdoutAsStdmsg createNimRtl
+    booting fulldebug corruption nimsuperops noSignalHandler useGnuReadline
+    noCaas noDocGen noBusyWaiting nativeStackTrace useNodeIds selftest
+    reportMissedDeadlines avoidTimeMachine useClone ignoreAllocationSize
+    debugExecProcesses pcreDll useLipzipSrc
+    preventDeadlocks UNICODE winUnicode trackGcHeaders posixRealtime
+  """.split
+
 proc initDefines*() = 
   gSymbols = newStringTable(modeStyleInsensitive)
   defineSymbol("nimrod") # 'nimrod' is always defined
@@ -53,6 +87,17 @@ proc initDefines*() =
   defineSymbol("nimparsebiggestfloatmagic")
   
   # add platform specific symbols:
+  for c in low(CPU)..high(CPU):
+    declareSymbol("cpu" & $CPU[c].bit)
+    declareSymbol(normalize(EndianToStr[CPU[c].endian]))
+    declareSymbol(CPU[c].name)
+  for o in low(platform.OS)..high(platform.OS):
+    declareSymbol(platform.OS[o].name)
+
+  for a in additionalSymbols:
+    declareSymbol(a)
+
+  # -----------------------------------------------------------
   case targetCPU
   of cpuI386: defineSymbol("x86")
   of cpuIa64: defineSymbol("itanium")
@@ -88,5 +133,6 @@ proc initDefines*() =
   defineSymbol(normalize(EndianToStr[CPU[targetCPU].endian]))
   defineSymbol(CPU[targetCPU].name)
   defineSymbol(platform.OS[targetOS].name)
+  declareSymbol("emulatedthreadvars")
   if platform.OS[targetOS].props.contains(ospLacksThreadVars):
     defineSymbol("emulatedthreadvars")
diff --git a/compiler/llstream.nim b/compiler/llstream.nim
index 86bfeaabd..5aefd468a 100644
--- a/compiler/llstream.nim
+++ b/compiler/llstream.nim
@@ -77,7 +77,7 @@ proc llStreamClose(s: PLLStream) =
   of llsFile: 
     close(s.f)
 
-when not defined(readLineFromStdin): 
+when not declared(readLineFromStdin): 
   # fallback implementation:
   proc readLineFromStdin(prompt: string, line: var string): bool =
     stdout.write(prompt)
diff --git a/compiler/nimrod.nim b/compiler/nimrod.nim
index ea7621b09..618d98698 100644
--- a/compiler/nimrod.nim
+++ b/compiler/nimrod.nim
@@ -79,7 +79,7 @@ proc handleCmdLine() =
           var ex = quoteShell(binPath)
           execExternalProgram(ex & ' ' & service.arguments)
 
-when defined(GC_setMaxPause):
+when declared(GC_setMaxPause):
   GC_setMaxPause 2_000
 
 when compileOption("gc", "v2") or compileOption("gc", "refc"):
diff --git a/compiler/semexprs.nim b/compiler/semexprs.nim
index 7e97eb293..ad8554500 100644
--- a/compiler/semexprs.nim
+++ b/compiler/semexprs.nim
@@ -1393,10 +1393,16 @@ proc semDefined(c: PContext, n: PNode, onlyCurrentScope: bool): PNode =
   checkSonsLen(n, 2)
   # we replace this node by a 'true' or 'false' node:
   result = newIntNode(nkIntLit, 0)
-  if lookUpForDefined(c, n.sons[1], onlyCurrentScope) != nil: 
-    result.intVal = 1
-  elif not onlyCurrentScope and (n.sons[1].kind == nkIdent) and
-      condsyms.isDefined(n.sons[1].ident): 
+  if not onlyCurrentScope and considerQuotedIdent(n[0]).s == "defined":
+    if n.sons[1].kind != nkIdent:
+      localError(n.info, "obsolete usage of 'defined', use 'declared' instead")
+    elif condsyms.isDefined(n.sons[1].ident):
+      result.intVal = 1
+    elif not condsyms.isDeclared(n.sons[1].ident):
+      message(n.info, warnUser,
+        "undeclared conditional symbol; use --symbol to declare it: " &
+        n[1].ident.s)
+  elif lookUpForDefined(c, n.sons[1], onlyCurrentScope) != nil: 
     result.intVal = 1
   result.info = n.info
   result.typ = getSysType(tyBool)
diff --git a/compiler/testability.nim b/compiler/testability.nim
index ceefd0a5e..4587a5344 100644
--- a/compiler/testability.nim
+++ b/compiler/testability.nim
@@ -1,5 +1,5 @@
 template tests*(body: stmt) {.immediate.} =
   when defined(selftest):
-    when not defined(unittest): import unittest
+    when not declared(unittest): import unittest
     body
 
diff --git a/compiler/vm.nim b/compiler/vm.nim
index aedbb92b4..a06d10f81 100644
--- a/compiler/vm.nim
+++ b/compiler/vm.nim
@@ -87,9 +87,7 @@ proc bailOut(c: PCtx; tos: PStackFrame) =
 when not defined(nimComputedGoto):
   {.pragma: computedGoto.}
 
-proc myreset(n: var TFullReg) =
-  when defined(system.reset): 
-    reset(n)
+proc myreset(n: var TFullReg) = reset(n)
 
 template ensureKind(k: expr) {.immediate, dirty.} =
   if regs[ra].kind != k:
diff --git a/doc/basicopt.txt b/doc/basicopt.txt
index 3a29b7829..fdb0e36e1 100644
--- a/doc/basicopt.txt
+++ b/doc/basicopt.txt
@@ -13,6 +13,7 @@ Options:
   -p, --path:PATH           add path to search paths
   -d, --define:SYMBOL       define a conditional symbol
   -u, --undef:SYMBOL        undefine a conditional symbol
+  --symbol:SYMBOL           declare a conditional symbol
   -f, --forceBuild          force rebuilding of all modules
   --stackTrace:on|off       turn stack tracing on|off
   --lineTrace:on|off        turn line tracing on|off
diff --git a/lib/core/typeinfo.nim b/lib/core/typeinfo.nim
index 57e11664b..8df1b3dfb 100644
--- a/lib/core/typeinfo.nim
+++ b/lib/core/typeinfo.nim
@@ -102,7 +102,7 @@ proc newAny(value: pointer, rawType: PNimType): TAny =
   result.value = value
   result.rawType = rawType
 
-when defined(system.TVarSlot):
+when declared(system.TVarSlot):
   proc toAny*(x: TVarSlot): TAny {.inline.} =
     ## constructs a ``TAny`` object from a variable slot ``x``. 
     ## This captures `x`'s address, so `x` can be modified with its
diff --git a/lib/impure/re.nim b/lib/impure/re.nim
index f6511dab4..ac07b2d6b 100644
--- a/lib/impure/re.nim
+++ b/lib/impure/re.nim
@@ -243,7 +243,7 @@ template `=~` *(s: string, pattern: TRegex): expr =
   ##     echo("syntax error")
   ##
   bind maxSubPatterns
-  when not definedInScope(matches):
+  when not declaredInScope(matches):
     var matches {.inject.}: array[0..MaxSubpatterns-1, string]
   match(s, pattern, matches)
 
diff --git a/lib/pure/math.nim b/lib/pure/math.nim
index 2f7a696b9..e76e96da5 100644
--- a/lib/pure/math.nim
+++ b/lib/pure/math.nim
@@ -219,7 +219,7 @@ when not defined(JS):
 
   proc randomize(seed: int) =
     srand(cint(seed))
-    when defined(srand48): srand48(seed)
+    when declared(srand48): srand48(seed)
   proc random(max: int): int =
     result = int(rand()) mod max
 
diff --git a/lib/pure/nimprof.nim b/lib/pure/nimprof.nim
index ab7cd1944..6f94d0656 100644
--- a/lib/pure/nimprof.nim
+++ b/lib/pure/nimprof.nim
@@ -26,7 +26,7 @@ const
   withThreads = compileOption("threads")
   tickCountCorrection = 50_000
 
-when not defined(system.TStackTrace):
+when not declared(system.TStackTrace):
   type TStackTrace = array [0..20, cstring]
 
 # We use a simple hash table of bounded size to keep track of the stack traces:
@@ -146,7 +146,7 @@ proc `//`(a, b: int): string =
   result = format("$1/$2 = $3%", a, b, formatFloat(a / b * 100.0, ffDefault, 2))
 
 proc writeProfile() {.noconv.} =
-  when defined(system.TStackTrace):
+  when declared(system.TStackTrace):
     system.profilerHook = nil
   const filename = "profile_results.txt"
   echo "writing " & filename & "..."
@@ -189,16 +189,16 @@ var
   disabled: int
 
 proc disableProfiling*() =
-  when defined(system.TStackTrace):
+  when declared(system.TStackTrace):
     atomicDec disabled
     system.profilerHook = nil
 
 proc enableProfiling*() =
-  when defined(system.TStackTrace):
+  when declared(system.TStackTrace):
     if atomicInc(disabled) >= 0:
       system.profilerHook = hook
 
-when defined(system.TStackTrace):
+when declared(system.TStackTrace):
   system.profilerHook = hook
   addQuitProc(writeProfile)
 
diff --git a/lib/pure/os.nim b/lib/pure/os.nim
index 44673d3e0..13b9cab3f 100644
--- a/lib/pure/os.nim
+++ b/lib/pure/os.nim
@@ -997,7 +997,7 @@ proc moveFile*(source, dest: string) {.rtl, extern: "nos$1",
   if c_rename(source, dest) != 0'i32:
     raise newException(EOS, $strerror(errno))
 
-when not defined(ENOENT) and not defined(Windows):
+when not declared(ENOENT) and not defined(Windows):
   when NoFakeVars:
     const ENOENT = cint(2) # 2 on most systems including Solaris
   else:
@@ -1615,11 +1615,11 @@ when defined(nimdoc):
     ##
     ## **Availability**: On Posix there is no portable way to get the command
     ## line from a DLL and thus the proc isn't defined in this environment. You
-    ## can test for its availability with `defined() <system.html#defined>`_.
+    ## can test for its availability with `declared() <system.html#declared>`_.
     ## Example:
     ##
     ## .. code-block:: nimrod
-    ##   when defined(paramCount):
+    ##   when declared(paramCount):
     ##     # Use paramCount() here
     ##   else:
     ##     # Do something else!
@@ -1638,11 +1638,11 @@ when defined(nimdoc):
     ##
     ## **Availability**: On Posix there is no portable way to get the command
     ## line from a DLL and thus the proc isn't defined in this environment. You
-    ## can test for its availability with `defined() <system.html#defined>`_.
+    ## can test for its availability with `declared() <system.html#declared>`_.
     ## Example:
     ##
     ## .. code-block:: nimrod
-    ##   when defined(paramStr):
+    ##   when declared(paramStr):
     ##     # Use paramStr() here
     ##   else:
     ##     # Do something else!
@@ -1682,7 +1682,7 @@ elif not defined(createNimRtl):
     # Docstring in nimdoc block.
     result = cmdCount-1
 
-when defined(paramCount) or defined(nimdoc):
+when declared(paramCount) or defined(nimdoc):
   proc commandLineParams*(): seq[TaintedString] =
     ## Convenience proc which returns the command line parameters.
     ##
@@ -1691,11 +1691,11 @@ when defined(paramCount) or defined(nimdoc):
     ##
     ## **Availability**: On Posix there is no portable way to get the command
     ## line from a DLL and thus the proc isn't defined in this environment. You
-    ## can test for its availability with `defined() <system.html#defined>`_.
+    ## can test for its availability with `declared() <system.html#declared>`_.
     ## Example:
     ##
     ## .. code-block:: nimrod
-    ##   when defined(commandLineParams):
+    ##   when declared(commandLineParams):
     ##     # Use commandLineParams() here
     ##   else:
     ##     # Do something else!
@@ -1714,7 +1714,7 @@ when defined(linux) or defined(solaris) or defined(bsd) or defined(aix):
 
 when not (defined(windows) or defined(macosx)):
   proc getApplHeuristic(): string =
-    when defined(paramStr):
+    when declared(paramStr):
       result = string(paramStr(0))
       # POSIX guaranties that this contains the executable
       # as it has been executed by the calling process
diff --git a/lib/pure/osproc.nim b/lib/pure/osproc.nim
index c74fa1ceb..3c181bf53 100644
--- a/lib/pure/osproc.nim
+++ b/lib/pure/osproc.nim
@@ -643,7 +643,7 @@ elif not defined(useNimRtl):
     data.workingDir = workingDir
 
 
-    when defined(posix_spawn) and not defined(useFork) and 
+    when declared(posix_spawn) and not defined(useFork) and 
         not defined(useClone) and not defined(linux):
       pid = startProcessAuxSpawn(data)
     else:
diff --git a/lib/pure/parseopt.nim b/lib/pure/parseopt.nim
index 68ae537c7..f43853fe6 100644
--- a/lib/pure/parseopt.nim
+++ b/lib/pure/parseopt.nim
@@ -37,7 +37,7 @@ type
                               ## or the argument, ``value`` is not "" if
                               ## the option was given a value
 
-when defined(os.paramCount):
+when declared(os.paramCount):
   # we cannot provide this for NimRtl creation on Posix, because we can't 
   # access the command line arguments then!
 
@@ -127,7 +127,7 @@ proc cmdLineRest*(p: TOptParser): TaintedString {.
   ## retrieves the rest of the command line that has not been parsed yet.
   result = strip(substr(p.cmd, p.pos, len(p.cmd) - 1)).TaintedString
 
-when defined(initOptParser):
+when declared(initOptParser):
 
   iterator getopt*(): tuple[kind: TCmdLineKind, key, val: TaintedString] =
     ## This is an convenience iterator for iterating over the command line.
diff --git a/lib/pure/parseopt2.nim b/lib/pure/parseopt2.nim
index 5e79d8a18..7638171d1 100644
--- a/lib/pure/parseopt2.nim
+++ b/lib/pure/parseopt2.nim
@@ -119,7 +119,7 @@ proc cmdLineRest*(p: TOptParser): TaintedString {.rtl, extern: "npo$1", deprecat
 type
   TGetoptResult* = tuple[kind: TCmdLineKind, key, val: TaintedString]
 
-when defined(paramCount):
+when declared(paramCount):
   iterator getopt*(): TGetoptResult =
     ## This is an convenience iterator for iterating over the command line.
     ## This uses the TOptParser object. Example:
diff --git a/lib/pure/pegs.nim b/lib/pure/pegs.nim
index 68b1ab223..efe169c1d 100644
--- a/lib/pure/pegs.nim
+++ b/lib/pure/pegs.nim
@@ -870,7 +870,7 @@ template `=~`*(s: string, pattern: TPeg): bool =
   ##     echo("syntax error")
   ##  
   bind maxSubpatterns
-  when not definedInScope(matches):
+  when not declaredInScope(matches):
     var matches {.inject.}: array[0..MaxSubpatterns-1, string]
   match(s, pattern, matches)
 
diff --git a/lib/pure/unittest.nim b/lib/pure/unittest.nim
index f5640a1b4..7cc95f0ad 100644
--- a/lib/pure/unittest.nim
+++ b/lib/pure/unittest.nim
@@ -19,7 +19,7 @@
 import
   macros
 
-when defined(stdout):
+when declared(stdout):
   import os
 
 when not defined(ECMAScript):
@@ -99,7 +99,7 @@ template fail* =
   when not defined(ECMAScript):
     if AbortOnError: quit(1)
  
-  when defined(TestStatusIMPL):
+  when declared(TestStatusIMPL):
     TestStatusIMPL = FAILED
   else:
     program_result += 1
@@ -188,7 +188,7 @@ macro expect*(exceptions: varargs[expr], body: stmt): stmt {.immediate.} =
   result = getAst(expectBody(errorTypes, exp.lineinfo, body))
 
 
-when defined(stdout):
+when declared(stdout):
   ## Reading settings
   var envOutLvl = os.getEnv("NIMTEST_OUTPUT_LVL").string
 
diff --git a/lib/system.nim b/lib/system.nim
index 1f09a6d2b..03275b8fa 100644
--- a/lib/system.nim
+++ b/lib/system.nim
@@ -98,16 +98,8 @@ type
 
 proc defined*(x: expr): bool {.magic: "Defined", noSideEffect.}
   ## Special compile-time procedure that checks whether `x` is
-  ## defined. `x` has to be an identifier or a qualified identifier.
-  ## This can be used to check whether a library provides a certain
-  ## feature or not:
-  ##
-  ## .. code-block:: Nimrod
-  ##   when not defined(strutils.toUpper):
-  ##     # provide our own toUpper proc here, because strutils is
-  ##     # missing it.
-  ##
-  ## You can also check external symbols introduced through the compiler's
+  ## defined.
+  ## `x` is an external symbol introduced through the compiler's
   ## `-d:x switch <nimrodc.html#compile-time-symbols>`_ to enable build time
   ## conditionals:
   ##
@@ -116,13 +108,28 @@ proc defined*(x: expr): bool {.magic: "Defined", noSideEffect.}
   ##     # Do here programmer friendly expensive sanity checks.
   ##   # Put here the normal code
 
+proc declared*(x: expr): bool {.magic: "Defined", noSideEffect.}
+  ## Special compile-time procedure that checks whether `x` is
+  ## declared. `x` has to be an identifier or a qualified identifier.
+  ## This can be used to check whether a library provides a certain
+  ## feature or not:
+  ##
+  ## .. code-block:: Nimrod
+  ##   when not defined(strutils.toUpper):
+  ##     # provide our own toUpper proc here, because strutils is
+  ##     # missing it.
+
 when defined(useNimRtl):
   {.deadCodeElim: on.}
 
 proc definedInScope*(x: expr): bool {.
-  magic: "DefinedInScope", noSideEffect.}
+  magic: "DefinedInScope", noSideEffect, deprecated.}
+  ## **Deprecated since version 0.9.6**: Use ``declaredInScope`` instead.
+
+proc declaredInScope*(x: expr): bool {.
+  magic: "DefinedInScope", noSideEffect, deprecated.}
   ## Special compile-time procedure that checks whether `x` is
-  ## defined in the current scope. `x` has to be an identifier.
+  ## declared in the current scope. `x` has to be an identifier.
 
 proc `not` *(x: bool): bool {.magic: "Not", noSideEffect.}
   ## Boolean not; returns true iff ``x == false``.
@@ -2118,7 +2125,7 @@ template newException*(exceptn: typedesc, message: string): expr =
 when hostOS == "standalone":
   include panicoverride
 
-when not defined(sysFatal):
+when not declared(sysFatal):
   template sysFatal(exceptn: typedesc, message: string) =
     when hostOS == "standalone":
       panic(message)
@@ -2170,7 +2177,7 @@ when not defined(JS): #and not defined(NimrodVM):
       # WARNING: This is very fragile! An array size of 8 does not work on my
       # Linux 64bit system. -- That's because the stack direction is the other
       # way round.
-      when defined(setStackBottom):
+      when declared(setStackBottom):
         var locals {.volatile.}: pointer
         locals = addr(locals)
         setStackBottom(locals)
@@ -2443,7 +2450,7 @@ when not defined(JS): #and not defined(NimrodVM):
       hasRaiseAction: bool
       raiseAction: proc (e: ref E_Base): bool {.closure.}
   
-  when defined(initAllocator):
+  when declared(initAllocator):
     initAllocator()
   when hasThreadSupport:
     include "system/syslocks"
@@ -3016,7 +3023,7 @@ proc compiles*(x): bool {.magic: "Compiles", noSideEffect.} =
   ##     echo "'+' for integers is available"
   discard
 
-when defined(initDebugger):
+when declared(initDebugger):
   initDebugger()
 
 when hostOS != "standalone":
diff --git a/lib/system/ansi_c.nim b/lib/system/ansi_c.nim
index 511a006d3..e012697ae 100644
--- a/lib/system/ansi_c.nim
+++ b/lib/system/ansi_c.nim
@@ -39,7 +39,7 @@ var
   c_stderr {.importc: "stderr", nodecl.}: C_TextFileStar
 
 # constants faked as variables:
-when not defined(SIGINT):
+when not declared(SIGINT):
   when NoFakeVars:
     when defined(windows):
       const
@@ -132,7 +132,7 @@ proc c_realloc(p: pointer, newsize: int): pointer {.
   importc: "realloc", header: "<stdlib.h>".}
 
 when hostOS != "standalone":
-  when not defined(errno):
+  when not declared(errno):
     when defined(NimrodVM):
       var vmErrnoWrapper {.importc.}: ptr cint
       template errno: expr = 
diff --git a/lib/system/arithm.nim b/lib/system/arithm.nim
index d9b3aebac..bb15360fd 100644
--- a/lib/system/arithm.nim
+++ b/lib/system/arithm.nim
@@ -241,26 +241,26 @@ elif false: # asmVersion and (defined(gcc) or defined(llvm_gcc)):
     """
 
 # Platform independent versions of the above (slower!)
-when not defined(addInt):
+when not declared(addInt):
   proc addInt(a, b: int): int {.compilerProc, inline.} =
     result = a +% b
     if (result xor a) >= 0 or (result xor b) >= 0:
       return result
     raiseOverflow()
 
-when not defined(subInt):
+when not declared(subInt):
   proc subInt(a, b: int): int {.compilerProc, inline.} =
     result = a -% b
     if (result xor a) >= 0 or (result xor not b) >= 0:
       return result
     raiseOverflow()
 
-when not defined(negInt):
+when not declared(negInt):
   proc negInt(a: int): int {.compilerProc, inline.} =
     if a != low(int): return -a
     raiseOverflow()
 
-when not defined(divInt):
+when not declared(divInt):
   proc divInt(a, b: int): int {.compilerProc, inline.} =
     if b == 0:
       raiseDivByZero()
@@ -268,13 +268,13 @@ when not defined(divInt):
       raiseOverflow()
     return a div b
 
-when not defined(modInt):
+when not declared(modInt):
   proc modInt(a, b: int): int {.compilerProc, inline.} =
     if b == 0:
       raiseDivByZero()
     return a mod b
 
-when not defined(mulInt):
+when not declared(mulInt):
   #
   # This code has been inspired by Python's source code.
   # The native int product x*y is either exactly right or *way* off, being
diff --git a/lib/system/atomics.nim b/lib/system/atomics.nim
index 82ec5dbde..695a5f63e 100644
--- a/lib/system/atomics.nim
+++ b/lib/system/atomics.nim
@@ -174,7 +174,7 @@ proc atomicInc*(memLoc: var int, x: int = 1): int =
   
 proc atomicDec*(memLoc: var int, x: int = 1): int =
   when defined(gcc) and hasThreadSupport:
-    when defined(atomic_sub_fetch):
+    when declared(atomic_sub_fetch):
       result = atomic_sub_fetch(memLoc.addr, x, ATOMIC_RELAXED)
     else:
       result = atomic_add_fetch(memLoc.addr, -x, ATOMIC_RELAXED)
@@ -201,14 +201,14 @@ when (defined(x86) or defined(amd64)) and (defined(gcc) or defined(llvm_gcc)):
     {.emit: """asm volatile("pause" ::: "memory");""".}
 elif (defined(x86) or defined(amd64)) and defined(vcc):
   proc cpuRelax {.importc: "YieldProcessor", header: "<windows.h>".}
-elif defined(intelc):
+elif defined(icl):
   proc cpuRelax {.importc: "_mm_pause", header: "xmmintrin.h".}
 elif false:
   from os import sleep
 
   proc cpuRelax {.inline.} = os.sleep(1)
 
-when not defined(fence) and hasThreadSupport:
+when not declared(fence) and hasThreadSupport:
   # XXX fixme
   proc fence*() {.inline.} =
     var dummy: bool
diff --git a/lib/system/channels.nim b/lib/system/channels.nim
index e5535dbdc..df46922e4 100644
--- a/lib/system/channels.nim
+++ b/lib/system/channels.nim
@@ -14,7 +14,7 @@
 ## **Note:** The current implementation of message passing is slow and does

 ## not work with cyclic data structures.

   
-when not defined(NimString): 
+when not declared(NimString):
   {.error: "You must not import this module explicitly".}
 

 type

diff --git a/lib/system/deepcopy.nim b/lib/system/deepcopy.nim
index bd8d00527..e7eb1cdb4 100644
--- a/lib/system/deepcopy.nim
+++ b/lib/system/deepcopy.nim
@@ -93,7 +93,7 @@ proc genericDeepCopyAux(dest, src: pointer, mt: PNimType) =
       if s2 == nil:
         unsureAsgnRef(cast[PPointer](dest), s2)
         return
-      when defined(usrToCell):
+      when declared(usrToCell):
         # unfortunately we only have cycle detection for our native GCs.
         let x = usrToCell(s2)
         let forw = cast[int](x.typ)
diff --git a/lib/system/excpt.nim b/lib/system/excpt.nim
index e1a5a958f..c3586be0f 100644
--- a/lib/system/excpt.nim
+++ b/lib/system/excpt.nim
@@ -307,7 +307,7 @@ when not defined(noSignalHandler):
         action("SIGBUS: Illegal storage access. (Attempt to read from nil?)\n")
       else:
         block platformSpecificSignal:
-          when defined(SIGPIPE):
+          when declared(SIGPIPE):
             if s == SIGPIPE:
               action("SIGPIPE: Pipe closed.\n")
               break platformSpecificSignal
@@ -336,7 +336,7 @@ when not defined(noSignalHandler):
     c_signal(SIGFPE, signalHandler)
     c_signal(SIGILL, signalHandler)
     c_signal(SIGBUS, signalHandler)
-    when defined(SIGPIPE):
+    when declared(SIGPIPE):
       c_signal(SIGPIPE, signalHandler)
 
   registerSignalHandler() # call it in initialization section
diff --git a/lib/system/gc.nim b/lib/system/gc.nim
index 3b85fe600..0c1fc7748 100644
--- a/lib/system/gc.nim
+++ b/lib/system/gc.nim
@@ -30,7 +30,7 @@ const
                                           # cycles instead of the complex
                                           # algorithm
 
-when withRealTime and not defined(getTicks):
+when withRealTime and not declared(getTicks):
   include "system/timers"
 when defined(memProfiler):
   proc nimProfile(requestedSize: int)
@@ -413,7 +413,7 @@ proc addNewObjToZCT(res: PCell, gch: var TGcHeap) {.inline.} =
 {.push stackTrace: off, profiler:off.}
 proc gcInvariant*() =
   sysAssert(allocInv(gch.region), "injected")
-  when defined(markForDebug):
+  when declared(markForDebug):
     markForDebug(gch)
 {.pop.}
 
diff --git a/lib/system/gc2.nim b/lib/system/gc2.nim
index 31c99a601..132da9885 100644
--- a/lib/system/gc2.nim
+++ b/lib/system/gc2.nim
@@ -26,7 +26,7 @@ const
                       # this seems to be a good value
   withRealTime = defined(useRealtimeGC)
 
-when withRealTime and not defined(getTicks):
+when withRealTime and not declared(getTicks):
   include "system/timers"
 when defined(memProfiler):
   proc nimProfile(requestedSize: int)
diff --git a/lib/system/hti.nim b/lib/system/hti.nim
index 5689f92b3..ef8f50831 100644
--- a/lib/system/hti.nim
+++ b/lib/system/hti.nim
@@ -7,7 +7,7 @@
 #    distribution, for details about the copyright.
 #
 
-when defined(NimString): 
+when declared(NimString): 
   # we are in system module:
   {.pragma: codegenType, compilerproc.}
 else:
diff --git a/lib/system/repr.nim b/lib/system/repr.nim
index f8f949668..d6df61fd3 100644
--- a/lib/system/repr.nim
+++ b/lib/system/repr.nim
@@ -121,7 +121,7 @@ proc reprSet(p: pointer, typ: PNimType): string {.compilerRtl.} =
 type
   TReprClosure {.final.} = object # we cannot use a global variable here
                                   # as this wouldn't be thread-safe
-    when defined(TCellSet):
+    when declared(TCellSet):
       marked: TCellSet
     recdepth: int       # do not recurse endlessly
     indent: int         # indentation
@@ -130,16 +130,16 @@ when not defined(useNimRtl):
   proc initReprClosure(cl: var TReprClosure) =
     # Important: cellsets does not lock the heap when doing allocations! We
     # have to do it here ...
-    when hasThreadSupport and hasSharedHeap and defined(heapLock):
+    when hasThreadSupport and hasSharedHeap and declared(heapLock):
       AcquireSys(HeapLock)
-    when defined(TCellSet):
+    when declared(TCellSet):
       init(cl.marked)
     cl.recdepth = -1      # default is to display everything!
     cl.indent = 0
 
   proc deinitReprClosure(cl: var TReprClosure) =
-    when defined(TCellSet): deinit(cl.marked)
-    when hasThreadSupport and hasSharedHeap and defined(heapLock): 
+    when declared(TCellSet): deinit(cl.marked)
+    when hasThreadSupport and hasSharedHeap and declared(heapLock): 
       ReleaseSys(HeapLock)
 
   proc reprBreak(result: var string, cl: TReprClosure) =
@@ -201,7 +201,7 @@ when not defined(useNimRtl):
   proc reprRef(result: var string, p: pointer, typ: PNimType,
                cl: var TReprClosure) =
     # we know that p is not nil here:
-    when defined(TCellSet):
+    when declared(TCellSet):
       when defined(boehmGC) or defined(nogc):
         var cell = cast[PCell](p)
       else:
diff --git a/lib/system/sysspawn.nim b/lib/system/sysspawn.nim
index 95cdba65d..5161104a9 100644
--- a/lib/system/sysspawn.nim
+++ b/lib/system/sysspawn.nim
@@ -9,7 +9,7 @@
 
 ## Implements Nimrod's 'spawn'.
 
-when not defined(NimString): 
+when not declared(NimString): 
   {.error: "You must not import this module explicitly".}
 
 {.push stackTrace:off.}
diff --git a/lib/system/sysstr.nim b/lib/system/sysstr.nim
index 9db8ce378..bc79bb254 100644
--- a/lib/system/sysstr.nim
+++ b/lib/system/sysstr.nim
@@ -32,7 +32,7 @@ proc eqStrings(a, b: NimString): bool {.inline, compilerProc.} =
   return a.len == b.len and
     c_memcmp(a.data, b.data, a.len * sizeof(char)) == 0'i32
 
-when defined(allocAtomic):
+when declared(allocAtomic):
   template allocStr(size: expr): expr =
     cast[NimString](allocAtomic(size))
 else:
@@ -85,7 +85,7 @@ proc copyStringRC1(src: NimString): NimString {.compilerRtl.} =
   if src != nil:
     var s = src.space
     if s < 8: s = 7
-    when defined(newObjRC1):
+    when declared(newObjRC1):
       result = cast[NimString](newObjRC1(addr(strDesc), sizeof(TGenericSeq) +
                                s+1))
     else:
diff --git a/lib/system/threads.nim b/lib/system/threads.nim
index d3b3aa457..4717659e5 100644
--- a/lib/system/threads.nim
+++ b/lib/system/threads.nim
@@ -39,7 +39,7 @@
 ##    createThread(thr[i], threadFunc, (i*10, i*10+5))
 ##  joinThreads(thr)
   
-when not defined(NimString): 
+when not declared(NimString): 
   {.error: "You must not import this module explicitly".}
 
 const
@@ -267,7 +267,7 @@ when not defined(boehmgc) and not hasSharedHeap:
   proc deallocOsPages()
 
 template threadProcWrapperBody(closure: expr) {.immediate.} =
-  when defined(globalsSlot): ThreadVarSetValue(globalsSlot, closure)
+  when declared(globalsSlot): ThreadVarSetValue(globalsSlot, closure)
   var t = cast[ptr TThread[TArg]](closure)
   when useStackMaskHack:
     var tls: TThreadLocalStorage
@@ -275,13 +275,13 @@ template threadProcWrapperBody(closure: expr) {.immediate.} =
     # init the GC for this thread:
     setStackBottom(addr(t))
     initGC()
-  when defined(registerThread):
+  when declared(registerThread):
     t.stackBottom = addr(t)
     registerThread(t)
   when TArg is void: t.dataFn()
   else: t.dataFn(t.data)
-  when defined(registerThread): unregisterThread(t)
-  when defined(deallocOsPages): deallocOsPages()
+  when declared(registerThread): unregisterThread(t)
+  when declared(deallocOsPages): deallocOsPages()
   # Since an unhandled exception terminates the whole process (!), there is
   # no need for a ``try finally`` here, nor would it be correct: The current
   # exception is tried to be re-raised by the code-gen after the ``finally``!
@@ -332,7 +332,7 @@ when false:
       discard TerminateThread(t.sys, 1'i32)
     else:
       discard pthread_cancel(t.sys)
-    when defined(registerThread): unregisterThread(addr(t))
+    when declared(registerThread): unregisterThread(addr(t))
     t.dataFn = nil
 
 proc createThread*[TArg](t: var TThread[TArg], 
diff --git a/lib/system/widestrs.nim b/lib/system/widestrs.nim
index e9673888c..cd64ff410 100644
--- a/lib/system/widestrs.nim
+++ b/lib/system/widestrs.nim
@@ -10,7 +10,7 @@
 # Nimrod support for C/C++'s `wide strings`:idx:. This is part of the system
 # module! Do not import it directly!
 
-when not defined(NimString):
+when not declared(NimString):
   {.error: "You must not import this module explicitly".}
 
 type
@@ -103,7 +103,7 @@ proc newWideCString*(source: cstring, L: int): WideCString =
 proc newWideCString*(s: cstring): WideCString =
   if s.isNil: return nil
 
-  when not defined(c_strlen):
+  when not declared(c_strlen):
     proc c_strlen(a: cstring): int {.
       header: "<string.h>", noSideEffect, importc: "strlen".}
 
diff --git a/lib/wrappers/sdl/sdl_ttf.nim b/lib/wrappers/sdl/sdl_ttf.nim
index f501e31d8..45247df4d 100644
--- a/lib/wrappers/sdl/sdl_ttf.nim
+++ b/lib/wrappers/sdl/sdl_ttf.nim
@@ -333,11 +333,5 @@ proc VERSION*(X: var sdl.Tversion) =
   X.patch = PATCHLEVEL
 
 
-when not (defined(Workaround_RenderText_Solid)): 
-  proc RenderText_Solid*(font: PFont, text: cstring, fg: TColor): PSurface{.
-      cdecl, importc: "TTF_RenderText_Solid", dynlib: ttfLibName.}
-else: 
-  proc RenderText_Solid(font: PFont, text: cstring, fg: TColor): PSurface = 
-    var Black: TColor         # initialized to zero
-    result = RenderText_Shaded(font, text, fg, Black)
-
+proc RenderText_Solid*(font: PFont, text: cstring, fg: TColor): PSurface{.
+    cdecl, importc: "TTF_RenderText_Solid", dynlib: ttfLibName.}
diff --git a/todo.txt b/todo.txt
index 6ae5df509..05426d71d 100644
--- a/todo.txt
+++ b/todo.txt
@@ -8,7 +8,7 @@ version 0.9.6
 Concurrency
 -----------
 
-- 'gcsafe' inferrence needs to be fixed
+- 'gcsafe' inference needs to be fixed
 - 'deepCopy' needs to be instantiated for
   generics *when the type is constructed*
 - test 'deepCopy'
diff --git a/web/news.txt b/web/news.txt
index 20e241221..3af154be3 100644
--- a/web/news.txt
+++ b/web/news.txt
@@ -23,6 +23,9 @@ News
   - The ``destructor`` pragma has been deprecated. Use the ``override`` pragma
     instead. The destructor's name has to be ``destroy`` now.
   - ``lambda`` is not a keyword anymore.
+  - **system.defined has been split into system.defined and system.declared**.
+    You have to use ``--symbol`` to declare new conditional symbols that can be
+    set via ``--define``.
 
   Language Additions
   ------------------
@@ -39,6 +42,7 @@ News
   - Added ``algorithm.reversed``
   - Added ``uri.combine`` and ``uri.parseUri``.
 
+
 2014-04-21 Version 0.9.4 released
 =================================