mirror of
https://github.com/nim-lang/Nim.git
synced 2025-12-30 09:54:49 +00:00
clean up the implementation of the new memfiles.resize
This commit is contained in:
@@ -282,34 +282,34 @@ proc flush*(f: var MemFile; attempts: Natural = 3) =
|
||||
if lastErr != EBUSY.OSErrorCode:
|
||||
raiseOSError(lastErr, "error flushing mapping")
|
||||
|
||||
proc resize*(f: var MemFile, newFileSize: int) =
|
||||
## resize and re-map the file underlying an ``allowRemap MemFile``. NOTE:
|
||||
## this assumes the entire file is mapped read-write at offset zero. Also,
|
||||
## the value of ``.mem`` will probably change.
|
||||
when defined(windows):
|
||||
discard #TODO This needs to be implemented.
|
||||
else:
|
||||
if f.handle == -1:
|
||||
raise newException(IOError,
|
||||
"Cannot resize MemFile opened with allowRemap=false")
|
||||
if ftruncate(f.handle, newFileSize) == -1:
|
||||
raiseOSError(osLastError())
|
||||
when defined(linux): #Maybe NetBSD, too?
|
||||
#On Linux this can be over 100 times faster than a munmap,mmap cycle.
|
||||
proc mremap(old: pointer; oldSize,newSize: csize; flags: cint): pointer {.
|
||||
importc: "mremap", header: "<sys/mman.h>" .}
|
||||
let newAddr = mremap(f.mem, csize(f.size), csize(newFileSize), cint(1))
|
||||
if newAddr == cast[pointer](MAP_FAILED):
|
||||
when defined(posix) or defined(nimdoc):
|
||||
proc resize*(f: var MemFile, newFileSize: int) {.raises: [IOError, OSError].} =
|
||||
## resize and re-map the file underlying an ``allowRemap MemFile``.
|
||||
## **Note**: this assumes the entire file is mapped read-write at offset zero.
|
||||
## Also, the value of ``.mem`` will probably change.
|
||||
## **Note**: This is not (yet) avaiable on Windows.
|
||||
when defined(posix):
|
||||
if f.handle == -1:
|
||||
raise newException(IOError,
|
||||
"Cannot resize MemFile opened with allowRemap=false")
|
||||
if ftruncate(f.handle, newFileSize) == -1:
|
||||
raiseOSError(osLastError())
|
||||
else:
|
||||
if munmap(f.mem, f.size) != 0:
|
||||
raiseOSError(osLastError())
|
||||
let newAddr = mmap(nil, newFileSize, PROT_READ or PROT_WRITE,
|
||||
MAP_SHARED or MAP_POPULATE, f.handle, 0)
|
||||
if newAddr == cast[pointer](MAP_FAILED):
|
||||
raiseOSError(osLastError())
|
||||
f.mem = newAddr
|
||||
f.size = newFileSize
|
||||
when defined(linux): #Maybe NetBSD, too?
|
||||
#On Linux this can be over 100 times faster than a munmap,mmap cycle.
|
||||
proc mremap(old: pointer; oldSize,newSize: csize; flags: cint): pointer {.
|
||||
importc: "mremap", header: "<sys/mman.h>" .}
|
||||
let newAddr = mremap(f.mem, csize(f.size), csize(newFileSize), cint(1))
|
||||
if newAddr == cast[pointer](MAP_FAILED):
|
||||
raiseOSError(osLastError())
|
||||
else:
|
||||
if munmap(f.mem, f.size) != 0:
|
||||
raiseOSError(osLastError())
|
||||
let newAddr = mmap(nil, newFileSize, PROT_READ or PROT_WRITE,
|
||||
MAP_SHARED or MAP_POPULATE, f.handle, 0)
|
||||
if newAddr == cast[pointer](MAP_FAILED):
|
||||
raiseOSError(osLastError())
|
||||
f.mem = newAddr
|
||||
f.size = newFileSize
|
||||
|
||||
proc close*(f: var MemFile) =
|
||||
## closes the memory mapped file `f`. All changes are written back to the
|
||||
|
||||
Reference in New Issue
Block a user