summary refs log tree commit diff stats
path: root/lib/system.nim
diff options
context:
space:
mode:
Diffstat (limited to 'lib/system.nim')
-rw-r--r--lib/system.nim101
1 files changed, 94 insertions, 7 deletions
diff --git a/lib/system.nim b/lib/system.nim
index 1ac6a8445..67a4221f1 100644
--- a/lib/system.nim
+++ b/lib/system.nim
@@ -14,8 +14,8 @@
 ## explicitly. Because of this there can not be a user-defined module named
 ## ``system``.
 ##
-##   *"The good thing about reinventing the wheel is that you can get a
-##   round one."*
+##   *The good thing about reinventing the wheel is that you can get a
+##   round one.*
 
 {.push hints: off.}
 
@@ -1044,8 +1044,9 @@ proc isNil*(x: cstring): bool {.noSideEffect, magic: "IsNil".}
 
 
 # Fixup some magic symbols here:
-{.fixup_system.} # This is an undocumented pragma that can only be used
-                 # once in the system module.
+#{.fixup_system.} 
+# This is an undocumented pragma that can only be used
+# once in the system module.
 
 proc `&` *[T](x, y: seq[T]): seq[T] {.noSideEffect.} =
   newSeq(result, x.len + y.len)
@@ -1099,6 +1100,13 @@ proc find*[T, S](a: T, item: S): int {.inline.} =
     inc(result)
   result = -1
 
+proc pop*[T](s: var seq[T]): T {.inline.} = 
+  ## returns the last item of `s` and decreases ``s.len`` by one. This treats
+  ## `s` as a stack and implements the common *pop* operation.
+  var L = s.len-1
+  result = s[L]
+  setLen(s, L)
+
 # ----------------- FPU ------------------------------------------------------
 
 #proc disableFPUExceptions*()
@@ -1401,16 +1409,95 @@ when not defined(EcmaScript) and not defined(NimrodVM):
   # as it would recurse endlessly!
   include arithm
   {.pop.} # stack trace
+  include dyncalls
 
   const
     GenericSeqSize = (2 * sizeof(int))
-
-  when not defined(boehmgc) and not defined(nogc):
+    
+  proc reprAny(p: pointer, typ: PNimType): string {.compilerproc.}
+
+  proc getDiscriminant(aa: Pointer, n: ptr TNimNode): int =
+    assert(n.kind == nkCase)
+    var d: int
+    var a = cast[TAddress](aa)
+    case n.typ.size
+    of 1: d = ze(cast[ptr int8](a +% n.offset)^)
+    of 2: d = ze(cast[ptr int16](a +% n.offset)^)
+    of 4: d = int(cast[ptr int32](a +% n.offset)^)
+    else: assert(false)
+    return d
+
+  proc selectBranch(aa: Pointer, n: ptr TNimNode): ptr TNimNode =
+    var discr = getDiscriminant(aa, n)
+    if discr <% n.len:
+      result = n.sons[discr]
+      if result == nil: result = n.sons[n.len]
+      # n.sons[n.len] contains the ``else`` part (but may be nil)
+    else:
+      result = n.sons[n.len]
+
+  when defined(boehmgc):
+    const
+      boehmLib = "/opt/lib/libgc.so"
+  
+    proc boehmGC_disable {.importc: "GC_disable", dynlib: boehmLib.} 
+    proc boehmGC_enable {.importc: "GC_enable", dynlib: boehmLib.} 
+    proc boehmGCincremental {.
+      importc: "GC_enable_incremental", dynlib: boehmLib.} 
+    proc boehmGCfullCollect {.importc: "GC_gcollect", dynlib: boehmLib.}  
+    proc boehmAlloc(size: int): pointer {.
+      importc: "GC_malloc", dynlib: boehmLib.}
+    proc boehmAllocAtomic(size: int): pointer {.
+      importc: "GC_malloc_atomic", dynlib: boehmLib.}
+    proc boehmRealloc(p: pointer, size: int): pointer {.
+      importc: "GC_realloc", dynlib: boehmLib.}
+    proc boehmDealloc(p: pointer) {.importc: "GC_free", dynlib: boehmLib.}
+      
+  include cellsets
+  
+  when defined(boehmGC):
+    proc initGC() = nil
+    
+    #boehmGCincremental()
+
+    proc GC_disable() = boehmGC_disable()
+    proc GC_enable() = boehmGC_enable()
+    proc GC_fullCollect() = boehmGCfullCollect()
+    proc GC_setStrategy(strategy: TGC_Strategy) = nil
+    proc GC_enableMarkAndSweep() = nil
+    proc GC_disableMarkAndSweep() = nil
+    proc GC_getStatistics(): string = return ""
+    
+    proc getOccupiedMem(): int = return -1
+    proc getFreeMem(): int = return -1
+    proc getTotalMem(): int = return -1
+      
+    proc growObj(old: pointer, newsize: int): pointer {.inline.} = 
+      result = boehmRealloc(old, newsize)
+    proc newObj(size: int): pointer {.compilerproc.} =
+      result = boehmAlloc(size)      
+    proc newSeq(baseSize, len: int): pointer {.compilerproc.} =
+      # XXX: overflow checks!
+      result = newObj(len * baseSize + GenericSeqSize)
+      cast[PGenericSeq](result).len = len
+      cast[PGenericSeq](result).space = len
+
+    proc setStackBottom(theStackBottom: pointer) {.compilerproc.} = nil
+    proc nimGCref(p: pointer) {.compilerproc, inline.} = nil
+    proc nimGCunref(p: pointer) {.compilerproc, inline.} = nil
+    
+    proc unsureAsgnRef(dest: ppointer, src: pointer) {.compilerproc, inline.} =
+      dest^ = src
+    proc asgnRef(dest: ppointer, src: pointer) {.compilerproc, inline.} =
+      dest^ = src
+    proc asgnRefNoCycle(dest: ppointer, src: pointer) {.compilerproc, inline.} =
+      dest^ = src
+
+  elif not defined(nogc):
     include gc
 
   include sysstr
   include assign
-  include dyncalls
   include repr
 
   # we have to implement it here after gentostr for the cstrToNimStrDummy proc