From 4384cfdbe11d754d6bfa011432e988dce7dd40ed Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Wed, 15 Sep 2021 13:00:57 +0200 Subject: Use Memory::* API for IoBufferCore::Alloc/FreeBuffer on non-Windows --- zencore/iobuffer.cpp | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 14ba77ea6..222fafa8e 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -21,12 +21,14 @@ namespace zen { void* IoBufferCore::AllocateBuffer(size_t InSize, size_t Alignment) { +#if ZEN_PLATFORM_WINDOWS if (((InSize & 0xffFF) == 0) && (Alignment == 0x10000)) { m_Flags |= kLowLevelAlloc; return VirtualAlloc(nullptr, InSize, MEM_COMMIT, PAGE_READWRITE); } else +#endif // ZEN_PLATFORM_WINDOWS { return Memory::Alloc(InSize, Alignment); } @@ -35,11 +37,13 @@ IoBufferCore::AllocateBuffer(size_t InSize, size_t Alignment) void IoBufferCore::FreeBuffer() { +#if ZEN_PLATFORM_WINDOWS if (m_Flags & kLowLevelAlloc) { VirtualFree(const_cast(m_DataPtr), 0, MEM_DECOMMIT); } else +#endif // ZEN_PLATFORM_WINDOWS { return Memory::Free(const_cast(m_DataPtr)); } -- cgit v1.2.3 From f821b2d421e52e15a15e85f1bfab4b6c05b09191 Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Wed, 15 Sep 2021 15:44:37 +0200 Subject: Incorrect fmt format syntax causing compile errors with GCC --- zencore/iobuffer.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 222fafa8e..e037abb4b 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -223,8 +223,8 @@ IoBufferExtendedCore::Materialize() const if (MappedBase == nullptr) { throw std::system_error( - std::error_code(::GetLastError(), std::system_category()), - "MapViewOfFile failed (offset {#x}, size {#x}) file: '{}'"_format(MapOffset, MapSize, zen::PathFromHandle(m_FileHandle))); + std::error_code(zen::GetLastError(), std::system_category()), + "MapViewOfFile failed (offset {:#x}, size {:#x}) file: '{}'"_format(MapOffset, MapSize, zen::PathFromHandle(m_FileHandle))); } m_MappedPointer = MappedBase; -- cgit v1.2.3 From 1ac503b670f293425c29d5d29a1cfbeb2e5e758d Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 09:57:55 +0200 Subject: Missing include --- zencore/iobuffer.cpp | 1 + 1 file changed, 1 insertion(+) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index e037abb4b..378105e69 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -4,6 +4,7 @@ #include #include +#include #include #include #include -- cgit v1.2.3 From 3f5f5f572f367052f8cb30f5545fbb0a459b25b4 Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 11:36:16 +0200 Subject: Use std::fs::path::value_type instead of wchar_t for path strings --- zencore/iobuffer.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index b591dee89..4a74b9a60 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -320,7 +320,7 @@ IoBufferBuilder::MakeFromFileHandle(void* FileHandle, uint64_t Offset, uint64_t } IoBuffer -IoBufferBuilder::MakeFromFile(const wchar_t* FileName, uint64_t Offset, uint64_t Size) +IoBufferBuilder::MakeFromFile(const path_char_t* FileName, uint64_t Offset, uint64_t Size) { CAtlFile DataFile; @@ -361,7 +361,7 @@ IoBufferBuilder::MakeFromFile(const wchar_t* FileName, uint64_t Offset, uint64_t } IoBuffer -IoBufferBuilder::MakeFromTemporaryFile(const wchar_t* FileName) +IoBufferBuilder::MakeFromTemporaryFile(const path_char_t* FileName) { CAtlFile DataFile; -- cgit v1.2.3 From 42bac2857db915f27095588e7b0a78cd54571ebe Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 13:52:56 +0200 Subject: Implementation of IoBufferExtendedCore() using mmap() --- zencore/iobuffer.cpp | 42 ++++++++++++++++++++++++++++++++++++------ 1 file changed, 36 insertions(+), 6 deletions(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 4a74b9a60..2473e0530 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -12,7 +12,12 @@ #include #include -#include +#if ZEN_PLATFORM_WINDOWS +# include +#else +# include +#endif + #include namespace zen { @@ -156,17 +161,29 @@ IoBufferExtendedCore::~IoBufferExtendedCore() { if (m_MappedPointer) { +#if ZEN_PLATFORM_WINDOWS UnmapViewOfFile(m_MappedPointer); +#else + uint64_t MapSize = ~uint64_t(uintptr_t(m_MmapHandle)); + munmap(m_MappedPointer, MapSize); +#endif } +#if ZEN_PLATFORM_WINDOWS if (m_Flags & kOwnsMmap) { CloseHandle(m_MmapHandle); } +#endif if (m_Flags & kOwnsFile) { +#if ZEN_PLATFORM_WINDOWS BOOL Success = CloseHandle(m_FileHandle); +#else + int Fd = int(uintptr_t(m_FileHandle)); + bool Success = (close(Fd) == 0); +#endif if (!Success) { @@ -196,6 +213,11 @@ IoBufferExtendedCore::Materialize() const if (m_MmapHandle) return; + const uint64_t MapOffset = m_FileOffset & ~0xffffull; + const uint64_t MappedOffsetDisplacement = m_FileOffset - MapOffset; + const uint64_t MapSize = m_DataBytes + MappedOffsetDisplacement; + +#if ZEN_PLATFORM_WINDOWS m_MmapHandle = CreateFileMapping(m_FileHandle, /* lpFileMappingAttributes */ nullptr, /* flProtect */ PAGE_READONLY, @@ -211,20 +233,28 @@ IoBufferExtendedCore::Materialize() const m_Flags |= kOwnsMmap; - const uint64_t MapOffset = m_FileOffset & ~0xffffull; - const uint64_t MappedOffsetDisplacement = m_FileOffset - MapOffset; - const uint64_t MapSize = m_DataBytes + MappedOffsetDisplacement; - void* MappedBase = MapViewOfFile(m_MmapHandle, /* dwDesiredAccess */ FILE_MAP_READ, /* FileOffsetHigh */ uint32_t(MapOffset >> 32), /* FileOffsetLow */ uint32_t(MapOffset & 0xffFFffFFu), /* dwNumberOfBytesToMap */ MapSize); +#else + m_MmapHandle = (void*)uintptr_t(~MapSize); // ~ so it's never null (assuming MapSize >= 0) + m_Flags |= kOwnsMmap; + + void* MappedBase = mmap( + /* addr */ nullptr, + /* length */ MapSize, + /* prot */ PROT_READ, + /* flags */ MAP_SHARED|MAP_NORESERVE, + /* fd */ int(uintptr_t(m_FileHandle)), + /* offset */ MapOffset); +#endif // ZEN_PLATFORM_WINDOWS if (MappedBase == nullptr) { throw std::system_error( - std::error_code(::GetLastError(), std::system_category()), + std::error_code(zen::GetLastError(), std::system_category()), "MapViewOfFile failed (offset {:#x}, size {:#x}) file: '{}'"_format(MapOffset, MapSize, zen::PathFromHandle(m_FileHandle))); } -- cgit v1.2.3 From 306de7d9a2c470613cb7697f2b0beff961fff8b5 Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 13:54:04 +0200 Subject: MakeFromFile() on POSIX --- zencore/iobuffer.cpp | 66 ++++++++++++++++++++++++++++++++++------------------ 1 file changed, 43 insertions(+), 23 deletions(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 2473e0530..16b530955 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -15,6 +15,7 @@ #if ZEN_PLATFORM_WINDOWS # include #else +# include # include #endif @@ -352,42 +353,61 @@ IoBufferBuilder::MakeFromFileHandle(void* FileHandle, uint64_t Offset, uint64_t IoBuffer IoBufferBuilder::MakeFromFile(const path_char_t* FileName, uint64_t Offset, uint64_t Size) { + uint64_t FileSize; + +#if ZEN_PLATFORM_WINDOWS CAtlFile DataFile; HRESULT hRes = DataFile.Create(FileName, GENERIC_READ, FILE_SHARE_READ, OPEN_EXISTING); - if (SUCCEEDED(hRes)) + if (FAILED(hRes)) { - ULONGLONG FileSize; - DataFile.GetSize(FileSize); + return {}; + } - // TODO: should validate that offset is in range + DataFile.GetSize((ULONGLONG&)FileSize); +#else + int Fd = open(FileName, O_RDONLY); + if (Fd < 0) + { + return {}; + } + + static_assert(sizeof(decltype(stat::st_size)) == sizeof(uint64_t), "fstat() doesn't support large files"); + struct stat Stat; + fstat(Fd, &Stat); + FileSize = Stat.st_size; +#endif // ZEN_PLATFORM_WINDOWS + + // TODO: should validate that offset is in range - if (Size == ~0ull) + if (Size == ~0ull) + { + Size = FileSize - Offset; + } + else + { + // Clamp size + if ((Offset + Size) > FileSize) { Size = FileSize - Offset; } - else - { - // Clamp size - if ((Offset + Size) > FileSize) - { - Size = FileSize - Offset; - } - } + } - if (Size) - { - return IoBuffer(IoBuffer::File, DataFile.Detach(), Offset, Size); - } - else - { - // For an empty file, we may as well just return an empty memory IoBuffer - return IoBuffer(IoBuffer::Wrap, "", 0); - } + if (Size) + { +#if ZEN_PLATFORM_WINDOWS + void* Fd = DataFile.Detach(); +#endif + return IoBuffer(IoBuffer::File, (void*)uintptr_t(Fd), Offset, Size); } - return {}; +#if !ZEN_PLATFORM_WINDOWS + close(Fd); +#endif + + // For an empty file, we may as well just return an empty memory IoBuffer + return IoBuffer(IoBuffer::Wrap, "", 0); } IoBuffer -- cgit v1.2.3 From 572d1a61ecb2133f4854dfcfe35406699f763c05 Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 13:56:28 +0200 Subject: MakeFromTemporaryFile() on POSIX --- zencore/iobuffer.cpp | 33 ++++++++++++++++++++++++++------- 1 file changed, 26 insertions(+), 7 deletions(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 16b530955..8e51f0872 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -413,6 +413,10 @@ IoBufferBuilder::MakeFromFile(const path_char_t* FileName, uint64_t Offset, uint IoBuffer IoBufferBuilder::MakeFromTemporaryFile(const path_char_t* FileName) { + uint64_t FileSize; + void* Handle; + +#if ZEN_PLATFORM_WINDOWS CAtlFile DataFile; // We need to open with DELETE since this is used for the case @@ -421,18 +425,33 @@ IoBufferBuilder::MakeFromTemporaryFile(const path_char_t* FileName) HRESULT hRes = DataFile.Create(FileName, GENERIC_READ | DELETE, FILE_SHARE_READ | FILE_SHARE_DELETE, OPEN_EXISTING); - if (SUCCEEDED(hRes)) + if (FAILED(hRes)) { - ULONGLONG FileSize; - DataFile.GetSize(FileSize); + return {}; + } - IoBuffer Iob(IoBuffer::File, DataFile.Detach(), 0, FileSize); - Iob.m_Core->SetIsWholeFile(true); + DataFile.GetSize((ULONGLONG&)FileSize); - return Iob; + Handle = DataFile.Detach(); +#else + int Fd = open(FileName, O_RDONLY); + if (Fd < 0) + { + return {}; } - return {}; + static_assert(sizeof(decltype(stat::st_size)) == sizeof(uint64_t), "fstat() doesn't support large files"); + struct stat Stat; + fstat(Fd, &Stat); + FileSize = Stat.st_size; + + Handle = (void*)uintptr_t(Fd); +#endif // ZEN_PLATFORM_WINDOWS + + IoBuffer Iob(IoBuffer::File, Handle, 0, FileSize); + Iob.m_Core->SetIsWholeFile(true); + + return Iob; } ////////////////////////////////////////////////////////////////////////// -- cgit v1.2.3 From c2b761e19185f8dd608019379f894c68e7408834 Mon Sep 17 00:00:00 2001 From: Martin Ridgers Date: Thu, 16 Sep 2021 13:56:41 +0200 Subject: Removed external linkage from g_MappingLock --- zencore/iobuffer.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'zencore/iobuffer.cpp') diff --git a/zencore/iobuffer.cpp b/zencore/iobuffer.cpp index 8e51f0872..beb969bc7 100644 --- a/zencore/iobuffer.cpp +++ b/zencore/iobuffer.cpp @@ -195,7 +195,7 @@ IoBufferExtendedCore::~IoBufferExtendedCore() m_DataPtr = nullptr; } -RwLock g_MappingLock; +static RwLock g_MappingLock; void IoBufferExtendedCore::Materialize() const -- cgit v1.2.3