fixes the recently discovered GC memory leaks
This revision is intended as comparison point between the old and the new GC The used GC can be switched in mmdisp and various statistics will be gathered during execution (these will be removed/disabled in later revisions)
This commit is contained in:
parent
d0edb1826b
commit
083d4f4708
12 changed files with 1939 additions and 364 deletions
|
|
@ -10,8 +10,10 @@
|
|||
# Efficient set of pointers for the GC (and repr)
|
||||
|
||||
type
|
||||
TRefCount = int
|
||||
|
||||
TCell {.pure.} = object
|
||||
refcount: int # the refcount and some flags
|
||||
refcount: TRefCount # the refcount and some flags
|
||||
typ: PNimType
|
||||
when trackAllocationSource:
|
||||
filename: cstring
|
||||
|
|
|
|||
1039
lib/system/gc.nim
1039
lib/system/gc.nim
File diff suppressed because it is too large
Load diff
|
|
@ -13,11 +13,19 @@ when defined(NimString):
|
|||
else:
|
||||
{.pragma: codegenType.}
|
||||
|
||||
type # This should be he same as ast.TTypeKind
|
||||
# many enum fields are not used at runtime
|
||||
type
|
||||
# This should be he same as ast.TTypeKind
|
||||
# many enum fields are not used at runtime
|
||||
TNimKind = enum
|
||||
tyNone, tyBool, tyChar,
|
||||
tyEmpty, tyArrayConstr, tyNil, tyExpr, tyStmt, tyTypeDesc,
|
||||
tyNone,
|
||||
tyBool,
|
||||
tyChar,
|
||||
tyEmpty,
|
||||
tyArrayConstr,
|
||||
tyNil,
|
||||
tyExpr,
|
||||
tyStmt,
|
||||
tyTypeDesc,
|
||||
tyGenericInvokation, # ``T[a, b]`` for types to invoke
|
||||
tyGenericBody, # ``T[a, b, body]`` last parameter is the body
|
||||
tyGenericInst, # ``T[a, b, realInstance]`` instantiated generic type
|
||||
|
|
@ -30,15 +38,30 @@ type # This should be he same as ast.TTypeKind
|
|||
tyTuple, # WARNING: The compiler uses tyTuple for pure objects!
|
||||
tySet,
|
||||
tyRange,
|
||||
tyPtr, tyRef,
|
||||
tyPtr,
|
||||
tyRef,
|
||||
tyVar,
|
||||
tySequence,
|
||||
tyProc,
|
||||
tyPointer, tyOpenArray,
|
||||
tyString, tyCString, tyForward,
|
||||
tyInt, tyInt8, tyInt16, tyInt32, tyInt64,
|
||||
tyFloat, tyFloat32, tyFloat64, tyFloat128,
|
||||
tyUInt, tyUInt8, tyUInt16, tyUInt32, tyUInt64,
|
||||
tyPointer,
|
||||
tyOpenArray,
|
||||
tyString,
|
||||
tyCString,
|
||||
tyForward,
|
||||
tyInt,
|
||||
tyInt8,
|
||||
tyInt16,
|
||||
tyInt32,
|
||||
tyInt64,
|
||||
tyFloat,
|
||||
tyFloat32,
|
||||
tyFloat64,
|
||||
tyFloat128,
|
||||
tyUInt,
|
||||
tyUInt8,
|
||||
tyUInt16,
|
||||
tyUInt32,
|
||||
tyUInt64,
|
||||
tyBigNum,
|
||||
|
||||
TNimNodeKind = enum nkNone, nkSlot, nkList, nkCase
|
||||
|
|
|
|||
|
|
@ -14,9 +14,9 @@
|
|||
{.push checks:off.}
|
||||
|
||||
const
|
||||
debugGC = false # we wish to debug the GC...
|
||||
debugGC = true # we wish to debug the GC...
|
||||
logGC = false
|
||||
traceGC = false # extensive debugging
|
||||
traceGC = true # extensive debugging
|
||||
alwaysCycleGC = false
|
||||
alwaysGC = false # collect after every memory allocation (for debugging)
|
||||
leakDetector = false
|
||||
|
|
@ -307,7 +307,10 @@ else:
|
|||
include "system/cellsets"
|
||||
when not leakDetector:
|
||||
sysAssert(sizeof(TCell) == sizeof(TFreeCell), "sizeof TFreeCell")
|
||||
include "system/gc"
|
||||
when true:
|
||||
include "system/gc"
|
||||
else:
|
||||
include "system/oldgc"
|
||||
|
||||
{.pop.}
|
||||
|
||||
|
|
|
|||
1044
lib/system/oldgc.nim
Normal file
1044
lib/system/oldgc.nim
Normal file
File diff suppressed because it is too large
Load diff
|
|
@ -204,9 +204,16 @@ proc setLengthSeq(seq: PGenericSeq, elemSize, newLen: int): PGenericSeq {.
|
|||
# we need to decref here, otherwise the GC leaks!
|
||||
when not defined(boehmGC) and not defined(nogc):
|
||||
for i in newLen..result.len-1:
|
||||
let len0 = gch.tempStack.len
|
||||
forAllChildrenAux(cast[pointer](cast[TAddress](result) +%
|
||||
GenericSeqSize +% (i*%elemSize)),
|
||||
extGetCellType(result).base, waZctDecRef)
|
||||
extGetCellType(result).base, waPush)
|
||||
let len1 = gch.tempStack.len
|
||||
for i in len0 .. <len1:
|
||||
doDecRef(gch.tempStack.d[i], LocalHeap, MaybeCyclic)
|
||||
gch.tempStack.len = len0
|
||||
|
||||
# XXX add a proper addCycleRoot barrier here!
|
||||
# and set the memory to nil:
|
||||
zeroMem(cast[pointer](cast[TAddress](result) +% GenericSeqSize +%
|
||||
(newLen*%elemSize)), (result.len-%newLen) *% elemSize)
|
||||
|
|
|
|||
|
|
@ -44,10 +44,11 @@ elif defined(macosx):
|
|||
|
||||
proc getTicks(): TTicks {.inline.} =
|
||||
result = TTicks(mach_absolute_time())
|
||||
|
||||
|
||||
var timeBaseInfo: TMachTimebaseInfoData
|
||||
mach_timebase_info(timeBaseInfo)
|
||||
|
||||
proc `-`(a, b: TTicks): TNanos =
|
||||
var timeBaseInfo: TMachTimebaseInfoData
|
||||
mach_timebase_info(timeBaseInfo)
|
||||
result = (a.int64 - b.int64) * timeBaseInfo.numer div timeBaseInfo.denom
|
||||
|
||||
elif defined(posixRealtime):
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue