From 149baf116b243098ee6d13a0bd0d5e5e425a36f7 Mon Sep 17 00:00:00 2001 From: Ralph Sennhauser Date: Sun, 14 Jun 2026 19:49:19 +0200 Subject: [PATCH] Replace all use of POSIX truncate Use `` instead of `truncate` and remove `truncate` portability wrapper. Add a helper function `StatusFromSystemError` to convert error_code to `Status`. Signed-off-by: Ralph Sennhauser --- source/lib/file/io/io.h | 13 +++++++++---- source/lib/status.cpp | 12 +++++++++++- source/lib/status.h | 8 +++++++- source/lib/sysdep/filesystem.h | 12 ------------ source/lib/sysdep/os/unix/ufilesystem.cpp | 5 ----- source/lib/sysdep/os/win/wposix/waio.h | 4 ++-- source/lib/sysdep/os/win/wposix/wfilesystem.cpp | 15 --------------- 7 files changed, 29 insertions(+), 40 deletions(-) diff --git a/source/lib/file/io/io.h b/source/lib/file/io/io.h index 2371b3ad4f..903be5b7d3 100644 --- a/source/lib/file/io/io.h +++ b/source/lib/file/io/io.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2025 Wildfire Games. +/* Copyright (C) 2026 Wildfire Games. * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -38,7 +38,7 @@ #include "lib/posix/posix_aio.h" // LIO_READ, LIO_WRITE #include "lib/posix/posix_types.h" #include "lib/status.h" -#include "lib/sysdep/filesystem.h" // wtruncate +#include "lib/sysdep/filesystem.h" #include "lib/sysdep/os.h" #include "lib/sysdep/rtl.h" #include "lib/types.h" @@ -47,7 +47,9 @@ #include #include #include +#include #include +#include namespace ERR { @@ -332,9 +334,12 @@ static inline Status Store(const OsPath& pathname, const void* data, size_t size RETURN_STATUS_IF_ERR(io::Run(op, p, completedHook, issueHook)); - file.Close(); // (required by wtruncate) + file.Close(); // (required by resize_file) - RETURN_STATUS_IF_ERR(wtruncate(pathname, size)); + std::error_code ec{}; + std::filesystem::resize_file(pathname.string(), size, ec); + if (ec) + return StatusFromSystemError(ec); return INFO::OK; } diff --git a/source/lib/status.cpp b/source/lib/status.cpp index 049ba153cf..95bb44d469 100644 --- a/source/lib/status.cpp +++ b/source/lib/status.cpp @@ -1,4 +1,4 @@ -/* Copyright (C) 2025 Wildfire Games. +/* Copyright (C) 2026 Wildfire Games. * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -100,6 +100,16 @@ int ErrnoFromStatus(Status status) return EPERM; } +Status StatusFromSystemError(std::error_code& ec) +{ + if (!ec) + return INFO::OK; + std::error_condition cond = ec.default_error_condition(); + if (cond.category() != std::generic_category()) + return ERR::FAIL; + const StatusDefinition* def = DefinitionFromErrno(cond.value()); + return def ? def->status : ERR::FAIL; +} Status StatusFromErrno() { diff --git a/source/lib/status.h b/source/lib/status.h index 251e01c93e..7b389cd41c 100644 --- a/source/lib/status.h +++ b/source/lib/status.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2025 Wildfire Games. +/* Copyright (C) 2026 Wildfire Games. * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -165,6 +165,7 @@ To summarize: +/-1SHHCC (S=subsystem, HH=header, CC=code number) #include "lib/types.h" #include +#include // an integral type allows defining error codes in separate headers, // but is not as type-safe as an enum. use Lint's 'strong type' checking @@ -246,6 +247,11 @@ extern int ErrnoFromStatus(Status status); **/ extern Status StatusFromErrno(); +/** + * @return Status equivalent of error_code, or ERR::FAIL if there's no equivalent. + */ +extern Status StatusFromSystemError(std::error_code& ec); + // note: other conversion routines (e.g. to/from Win32) are implemented in // the corresponding modules to keep this header portable. diff --git a/source/lib/sysdep/filesystem.h b/source/lib/sysdep/filesystem.h index fdca713f0d..f3518c53fa 100644 --- a/source/lib/sysdep/filesystem.h +++ b/source/lib/sysdep/filesystem.h @@ -56,18 +56,6 @@ extern int wopen(const OsPath& pathname, int oflag, mode_t mode); extern int wclose(int fd); -// -// unistd.h -// - -// waio requires offsets and sizes to be multiples of the sector size. -// to allow arbitrarily sized files, we truncate them after I/O. -// however, ftruncate cannot be used since it is also subject to the -// sector-alignment requirement. instead, the file must be closed and -// this function called. -int wtruncate(const OsPath& pathname, off_t length); - - // // stdlib.h // diff --git a/source/lib/sysdep/os/unix/ufilesystem.cpp b/source/lib/sysdep/os/unix/ufilesystem.cpp index 4095735e41..1ca2f2e14c 100644 --- a/source/lib/sysdep/os/unix/ufilesystem.cpp +++ b/source/lib/sysdep/os/unix/ufilesystem.cpp @@ -93,11 +93,6 @@ int wclose(int fd) return close(fd); } -int wtruncate(const OsPath& pathname, off_t length) -{ - return truncate(OsString(pathname).c_str(), length); -} - int wrename(const OsPath& pathnameOld, const OsPath& pathnameNew) { return rename(OsString(pathnameOld).c_str(), OsString(pathnameNew).c_str()); diff --git a/source/lib/sysdep/os/win/wposix/waio.h b/source/lib/sysdep/os/win/wposix/waio.h index 0efb24f53e..cc78d35a25 100644 --- a/source/lib/sysdep/os/win/wposix/waio.h +++ b/source/lib/sysdep/os/win/wposix/waio.h @@ -1,4 +1,4 @@ -/* Copyright (C) 2025 Wildfire Games. +/* Copyright (C) 2026 Wildfire Games. * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the @@ -130,7 +130,7 @@ extern Status waio_close(int fd); // @param size is rounded up to a multiple of maxSectorSize (required by // SetEndOfFile; this could be avoided by using the undocumented // NtSetInformationFile or SetFileInformationByHandle on Vista and later). -// use wtruncate after I/O is complete to chop off the excess padding. +// use truncate after I/O is complete to chop off the excess padding. // // NB: writes that extend a file (i.e. ALL WRITES when creating new files) // are synchronous, which prevents overlapping I/O and other work. diff --git a/source/lib/sysdep/os/win/wposix/wfilesystem.cpp b/source/lib/sysdep/os/win/wposix/wfilesystem.cpp index 8aff89ad46..26de25d38a 100644 --- a/source/lib/sysdep/os/win/wposix/wfilesystem.cpp +++ b/source/lib/sysdep/os/win/wposix/wfilesystem.cpp @@ -131,21 +131,6 @@ int wclose(int fd) } - -int wtruncate(const OsPath& pathname, off_t length) -{ - // (re-open the file to avoid the FILE_FLAG_NO_BUFFERING - // sector-alignment restriction) - HANDLE hFile = CreateFileW(OsString(pathname).c_str(), GENERIC_WRITE, 0, 0, OPEN_EXISTING, 0, 0); - ENSURE(hFile != INVALID_HANDLE_VALUE); - LARGE_INTEGER ofs; ofs.QuadPart = length; - WARN_IF_FALSE(SetFilePointerEx(hFile, ofs, 0, FILE_BEGIN)); - WARN_IF_FALSE(SetEndOfFile(hFile)); - WARN_IF_FALSE(CloseHandle(hFile)); - return 0; -} - - OsPath wrealpath(const OsPath& pathname) { wchar_t resolved[PATH_MAX];