added GC_addCycleRoot
This commit is contained in:
parent
5e7dd69b00
commit
0f2aa053d9
3 changed files with 16 additions and 4 deletions
|
|
@ -520,7 +520,7 @@ type
|
||||||
TNodeSeq* = seq[PNode]
|
TNodeSeq* = seq[PNode]
|
||||||
PType* = ref TType
|
PType* = ref TType
|
||||||
PSym* = ref TSym
|
PSym* = ref TSym
|
||||||
TNode*{.final.} = object # on a 32bit machine, this takes 32 bytes
|
TNode*{.final, acyclic.} = object # on a 32bit machine, this takes 32 bytes
|
||||||
typ*: PType
|
typ*: PType
|
||||||
comment*: string
|
comment*: string
|
||||||
info*: TLineInfo
|
info*: TLineInfo
|
||||||
|
|
@ -605,7 +605,7 @@ type
|
||||||
PInstantiation* = ref TInstantiation
|
PInstantiation* = ref TInstantiation
|
||||||
|
|
||||||
PLib* = ref TLib
|
PLib* = ref TLib
|
||||||
TSym* = object of TIdObj
|
TSym* {.acyclic.} = object of TIdObj
|
||||||
# proc and type instantiations are cached in the generic symbol
|
# proc and type instantiations are cached in the generic symbol
|
||||||
case kind*: TSymKind
|
case kind*: TSymKind
|
||||||
of skType:
|
of skType:
|
||||||
|
|
@ -653,7 +653,8 @@ type
|
||||||
constraint*: PNode # additional constraints like 'lit|result'
|
constraint*: PNode # additional constraints like 'lit|result'
|
||||||
|
|
||||||
TTypeSeq* = seq[PType]
|
TTypeSeq* = seq[PType]
|
||||||
TType* = object of TIdObj # types are identical iff they have the
|
TType* {.acyclic.} = object of TIdObj # \
|
||||||
|
# types are identical iff they have the
|
||||||
# same id; there may be multiple copies of a type
|
# same id; there may be multiple copies of a type
|
||||||
# in memory!
|
# in memory!
|
||||||
kind*: TTypeKind # kind of type
|
kind*: TTypeKind # kind of type
|
||||||
|
|
|
||||||
|
|
@ -28,6 +28,11 @@ compiler analyses the types for their possibility to build cycles, but often
|
||||||
it is necessary to help this analysis with the ``acyclic`` pragma (see
|
it is necessary to help this analysis with the ``acyclic`` pragma (see
|
||||||
`acyclic <manual.html#acyclic-pragma>`_ for further information).
|
`acyclic <manual.html#acyclic-pragma>`_ for further information).
|
||||||
|
|
||||||
|
You can also use the ``acyclic`` pragma for data that is cyclic in reality and
|
||||||
|
then break up the cycles explicitly with ``GC_addCycleRoot``. This can be a
|
||||||
|
very good optimization; the Nimrod compiler itself relies on this optimization
|
||||||
|
trick to improve performance.
|
||||||
|
|
||||||
To force a full collection call ``GC_fullCollect``. Note that it is generally
|
To force a full collection call ``GC_fullCollect``. Note that it is generally
|
||||||
better to let the GC do its work and not enforce a full collection.
|
better to let the GC do its work and not enforce a full collection.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -207,6 +207,12 @@ proc incRef(c: PCell) {.inline.} =
|
||||||
proc nimGCref(p: pointer) {.compilerProc, inline.} = incRef(usrToCell(p))
|
proc nimGCref(p: pointer) {.compilerProc, inline.} = incRef(usrToCell(p))
|
||||||
proc nimGCunref(p: pointer) {.compilerProc, inline.} = decRef(usrToCell(p))
|
proc nimGCunref(p: pointer) {.compilerProc, inline.} = decRef(usrToCell(p))
|
||||||
|
|
||||||
|
proc GC_addCycleRoot*[T](p: ref T) {.inline.} =
|
||||||
|
## adds 'p' to the cycle candidate set for the cycle collector. It is
|
||||||
|
## necessary if you used the 'acyclic' pragma for optimization
|
||||||
|
## purposes and need to break cycles manually.
|
||||||
|
rtlAddCycleRoot(usrToCell(cast[pointer](p)))
|
||||||
|
|
||||||
proc nimGCunrefNoCycle(p: pointer) {.compilerProc, inline.} =
|
proc nimGCunrefNoCycle(p: pointer) {.compilerProc, inline.} =
|
||||||
sysAssert(allocInv(gch.region), "begin nimGCunrefNoCycle")
|
sysAssert(allocInv(gch.region), "begin nimGCunrefNoCycle")
|
||||||
var c = usrToCell(p)
|
var c = usrToCell(p)
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue