From 1e29796278c1d14bba77f8dad74f761e9b3461ee Mon Sep 17 00:00:00 2001 From: Mattia Giambirtone Date: Fri, 4 Nov 2022 15:30:22 +0100 Subject: [PATCH] Simplified reallocate() and more failed attempts at fixing GC issues --- src/backend/vm.nim | 27 ++++++++++----------------- src/config.nim | 2 +- tests/gc.pn | 6 +++--- 3 files changed, 14 insertions(+), 21 deletions(-) diff --git a/src/backend/vm.nim b/src/backend/vm.nim index 689ea94..73dc7be 100644 --- a/src/backend/vm.nim +++ b/src/backend/vm.nim @@ -114,7 +114,7 @@ proc collect*(self: var PeonVM) proc reallocate*(self: var PeonVM, p: pointer, oldSize: int, newSize: int): pointer = - ## Simple wrapper around realloc/dealloc with + ## Simple wrapper around realloc with ## built-in garbage collection self.gc.bytesAllocated.current += newSize - oldSize try: @@ -124,14 +124,7 @@ proc reallocate*(self: var PeonVM, p: pointer, oldSize: int, newSize: int): poin echo &"DEBUG - Memory manager: Deallocating {oldSize} bytes of memory" else: echo "DEBUG - Memory manager: Deallocating 1 byte of memory" - dealloc(p) elif (oldSize > 0 and not p.isNil() and newSize > oldSize) or oldSize == 0: - self.gc.bytesAllocated.total += newSize - oldSize - when debugStressGC: - self.collect() - else: - if self.gc.bytesAllocated.current > self.gc.nextGC: - self.collect() when debugMem: if oldSize == 0: if newSize > 1: @@ -140,18 +133,18 @@ proc reallocate*(self: var PeonVM, p: pointer, oldSize: int, newSize: int): poin echo "DEBUG - Memory manager: Allocating 1 byte of memory" else: echo &"DEBUG - Memory manager: Resizing {oldSize} bytes of memory to {newSize} bytes" - result = realloc(p, newSize) - when debugMem: - if p.isNil() and newSize == 0: - echo &"DEBUG - Memory manager: Warning, asked to dealloc() nil pointer from {oldSize} to {newSize} bytes, ignoring request" - elif oldSize > 0 and p.isNil(): - echo &"DEBUG - Memory manager: Warning, asked to realloc() nil pointer from {oldSize} to {newSize} bytes, ignoring request" + self.gc.bytesAllocated.total += newSize - oldSize + when debugStressGC: + self.collect() + else: + if self.gc.bytesAllocated.current > self.gc.nextGC: + self.collect() + result = realloc(p, newSize) except NilAccessDefect: - stderr.write("Peon: could not manage memory, segmentation fault\n") + stderr.writeLine("Peon: could not manage memory, segmentation fault") quit(139) # For now, there's not much we can do if we can't get the memory we need, so we exit - template resizeArray*(self: var PeonVM, kind: untyped, p: pointer, oldCount, newCount: int): untyped = ## Handy template to resize a dynamic array cast[ptr UncheckedArray[kind]](reallocate(self, p, sizeof(kind) * oldCount, sizeof(kind) * newCount)) @@ -178,9 +171,9 @@ proc allocate*(self: var PeonVM, kind: ObjectKind, size: typedesc, count: int): of String: result.str = cast[ptr UncheckedArray[char]](self.reallocate(nil, 0, sizeof(size) * count)) result.len = count - self.gc.bytesAllocated.current += sizeof(size) * count else: discard # TODO + self.gc.bytesAllocated.current += sizeof(size) * count self.gc.objects.add(result) self.gc.pointers.incl(cast[uint64](result)) diff --git a/src/config.nim b/src/config.nim index bbc53a7..f7d8567 100644 --- a/src/config.nim +++ b/src/config.nim @@ -26,7 +26,7 @@ const debugSerializer* {.booldefine.} = false # Validate the bytecode serialize const debugStressGC* {.booldefine.} = false # Make the GC run a collection at every allocation (VERY SLOW!) const PeonBytecodeMarker* = "PEON_BYTECODE" # Magic value at the beginning of bytecode files const HeapGrowFactor* = 2 # The growth factor used by the GC to schedule the next collection -const FirstGC* = 1024 * 1024; # How many bytes to allocate before running the first GC +const FirstGC* = 1024; # How many bytes to allocate before running the first GC const enableVMChecks* {.booldefine.} = true; # Enables all types of compiler (nim-wise) checks in the VM # List of paths where peon looks for modules, in order (empty path means current directory, which always takes precedence) const moduleLookupPaths*: seq[string] = @["", "src/peon/stdlib"] diff --git a/tests/gc.pn b/tests/gc.pn index 311ec39..9f0b330 100644 --- a/tests/gc.pn +++ b/tests/gc.pn @@ -1,14 +1,14 @@ import std; -var x: uint64 = 1000000'u64; +var x = 10000; var y = "just a test"; print(y); print("Starting GC torture test"); print(x); -while x > 0'u64 { +while x > 0 { "hello"; - x = x - 1'u64; + x = x - 1; } print("END"); print(y);