diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/pure/memfiles.nim | 28 |
1 files changed, 20 insertions, 8 deletions
diff --git a/lib/pure/memfiles.nim b/lib/pure/memfiles.nim index c6322c7bb..b6154d8de 100644 --- a/lib/pure/memfiles.nim +++ b/lib/pure/memfiles.nim @@ -83,7 +83,8 @@ proc unmapMem*(f: var MemFile, p: pointer, size: int) = proc open*(filename: string, mode: FileMode = fmRead, - mappedSize = -1, offset = 0, newFileSize = -1): MemFile = + mappedSize = -1, offset = 0, newFileSize = -1, + allowRemap = false): MemFile = ## opens a memory mapped file. If this fails, ``EOS`` is raised. ## ## ``newFileSize`` can only be set if the file does not exist and is opened @@ -95,6 +96,9 @@ proc open*(filename: string, mode: FileMode = fmRead, ## ``offset`` must be multiples of the PAGE SIZE of your OS ## (usually 4K or 8K but is unique to your OS) ## + ## ``allowRemap`` only needs to be true if you want to call ``mapMem`` on + ## the resulting MemFile; else file handles are not kept open. + ## ## Example: ## ## .. code-block:: nim @@ -189,11 +193,14 @@ proc open*(filename: string, mode: FileMode = fmRead, else: result.size = fileSize.int result.wasOpened = true + if not allowRemap and result.fHandle != INVALID_HANDLE_VALUE: + if closeHandle(result.fHandle) == 0: + result.fHandle = INVALID_HANDLE_VALUE else: template fail(errCode: OSErrorCode, msg: expr) = rollback() - if result.handle != 0: discard close(result.handle) + if result.handle != -1: discard close(result.handle) raiseOSError(errCode) var flags = if readonly: O_RDONLY else: O_RDWR @@ -236,6 +243,10 @@ proc open*(filename: string, mode: FileMode = fmRead, if result.mem == cast[pointer](MAP_FAILED): fail(osLastError(), "file mapping failed") + if not allowRemap and result.handle != -1: + if close(result.handle) == 0: + result.handle = -1 + proc close*(f: var MemFile) = ## closes the memory mapped file `f`. All changes are written back to the ## file system, if `f` was opened with write access. @@ -244,15 +255,16 @@ proc close*(f: var MemFile) = var lastErr: OSErrorCode when defined(windows): - if f.fHandle != INVALID_HANDLE_VALUE and f.wasOpened: + if f.wasOpened: error = unmapViewOfFile(f.mem) == 0 lastErr = osLastError() error = (closeHandle(f.mapHandle) == 0) or error - error = (closeHandle(f.fHandle) == 0) or error + if f.fHandle != INVALID_HANDLE_VALUE: + error = (closeHandle(f.fHandle) == 0) or error else: - if f.handle != 0: - error = munmap(f.mem, f.size) != 0 - lastErr = osLastError() + error = munmap(f.mem, f.size) != 0 + lastErr = osLastError() + if f.handle != -1: error = (close(f.handle) != 0) or error f.size = 0 @@ -263,7 +275,7 @@ proc close*(f: var MemFile) = f.mapHandle = 0 f.wasOpened = false else: - f.handle = 0 + f.handle = -1 if error: raiseOSError(lastErr) |