On Sun, 13 Apr 2025, Pali Rohár wrote:

All 64-bit CRT import libraries already provides _fstat64i32, _stat64i32
and _wstat64i32 function symbols. These symbols are either directly
exported from 64-bit CRT DLL library or def file contains alias to other
ABI compatible symbols (_fstat, _stat and _wstat).

Also all these functions _fstat64i32, _stat64i32 and _wstat64i32 are
provided by msvcr80+ and UCRT, so ensure that mingw-w64 does not provide
any replacement for msvcr80+ import libraries. And ensure that libmingwex.a
library does not provide duplication of these symbols.

For 32-bit pre-msvcr80 CRT import libraries provides mingw-w64 emulation
via _fstat64, _stat64 and _wstat64, which just truncates 64-bit st_size
(returned by _*stat64 function) to 32-bit st_size (which is ABI of
_*stat64i32). Do not use any _mingw_no_trailing_slash workaround as for all
these functions with underscore prefix, it is expected that behavior is
same as for other stat functions with underscore prefix.

These _fstat64i32, _stat64i32 and _wstat64i32 functions in msvcr80+ and
UCRT DLL libraries do not touch output struct stat buffer on error. So do
same thing in mingw-w64 emulation and remove memset(stat, 0, sizeof(stat))
call in failure path.

And add missing __MINGW_IMP_SYMBOL import symbols into mingw-w64 emulation
code for these functions as msvcr80+ import libraries already have them.
---
mingw-w64-crt/Makefile.am         | 10 +++-
mingw-w64-crt/stdio/_fstat64i32.c | 27 +++++++---
mingw-w64-crt/stdio/_stat64i32.c  | 88 +++++++------------------------
mingw-w64-crt/stdio/_wstat64i32.c | 88 +++++++------------------------
4 files changed, 66 insertions(+), 147 deletions(-)

diff --git a/mingw-w64-crt/stdio/_fstat64i32.c 
b/mingw-w64-crt/stdio/_fstat64i32.c
index 7e71f2e80005..cc72b3814ba9 100644
--- a/mingw-w64-crt/stdio/_fstat64i32.c
+++ b/mingw-w64-crt/stdio/_fstat64i32.c
@@ -1,14 +1,27 @@
+/**
+ * This file has no copyright assigned and is placed in the Public Domain.
+ * This file is part of the mingw-w64 runtime package.
+ * No warranty is given; refer to the file DISCLAIMER.PD within this package.
+ */
+
#define __CRT__NO_INLINE
#include <sys/stat.h>

+/* When the file size does not fit into the st_size field:
+ *           crtdll-msvcr90   msvcr100   msvcr110+
+ * st_size      truncate         0           0
+ * errno       no change     no change   EOVERFLOW
+ * returns         0            -1          -1
+ *
+ * This file is used only for pre-msvcr80 builds,
+ * So use the pre-msvcr80 behavior - truncate without error.
+ */
int __cdecl _fstat64i32(int _FileDes,struct _stat64i32 *_Stat)
{
  struct _stat64 st;
  int ret=_fstat64(_FileDes,&st);
-  if (ret == -1) {
-    *_Stat = (struct _stat64i32){0};
-    return -1;
-  }
+  if (ret != 0)
+    return ret;
  _Stat->st_dev=st.st_dev;
  _Stat->st_ino=st.st_ino;
  _Stat->st_mode=st.st_mode;
@@ -16,10 +29,10 @@ int __cdecl _fstat64i32(int _FileDes,struct _stat64i32 
*_Stat)
  _Stat->st_uid=st.st_uid;
  _Stat->st_gid=st.st_gid;
  _Stat->st_rdev=st.st_rdev;
-  _Stat->st_size=(_off_t) st.st_size; /* 32bit size */
+  _Stat->st_size=(_off_t) st.st_size; /* truncate 64-bit st_size to 32-bit */
  _Stat->st_atime=st.st_atime;
  _Stat->st_mtime=st.st_mtime;
  _Stat->st_ctime=st.st_ctime;
-  return ret;
+  return 0;
}
-
+int (__cdecl *__MINGW_IMP_SYMBOL(_fstat64i32))(int, struct _stat64i32 *) = 
_fstat64i32;

This function, and _stat64i32 and _wstat64i32, don't seem to be declared with dllimport/_CRTIMP in headers, so the __MINGW_IMP_SYMBOL isn't technically required here.

// Martin

_______________________________________________
Mingw-w64-public mailing list
Mingw-w64-public@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/mingw-w64-public

Reply via email to