From f70b9c84027bd3b1e3b7dc0df4827fafd23ecf9a Mon Sep 17 00:00:00 2001 From: Keith Marshall Date: Thu, 30 Jan 2014 14:22:18 +0000 Subject: [PATCH] Make dirent structure 64-bit deterministic; (cf. issue #2106) --- ChangeLog | 14 ++++++++++++++ include/dirent.h | 38 +++++++++++++++++--------------------- src/libcrt/tchar/dirent.c | 19 ++++++++++++++++--- 3 files changed, 47 insertions(+), 24 deletions(-) diff --git a/ChangeLog b/ChangeLog index d476472..dcf7fca 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,5 +1,19 @@ 2014-01-30 Keith Marshall + Make dirent structure 64-bit deterministic; (cf. issue #2106) + + * include/dirent.h (struct dirent, struct _wdirent): + : Declare as __time64_t. + : Declare as uint64_t; include stdint.h to define it. + + * src/libcrt/tchar/dirent.c (_finddata_t, _wfinddata_t): Define them + explicitly, making them respectively 64-bit clean local aliases for... + (__finddata64_t, __wfinddata64_t): ...these explicit structure types. + (DIRENT_OPEN, DIRENT_UPDATE) : Always assign it, using... + (_tfindfirst64, _tfindnext64): ...these 64-bit clean functions. + +2014-01-30 Keith Marshall + Correct _wfinddata64_t vs. __wfinddata64_t typo. * include/io.h include/wchar.h (_wfinddata64_t): All MSDN data type diff --git a/include/dirent.h b/include/dirent.h index f965d0d..47cc580 100644 --- a/include/dirent.h +++ b/include/dirent.h @@ -27,12 +27,11 @@ #include <_mingw.h> #include +#include #ifndef RC_INVOKED -#ifdef __cplusplus -extern "C" { -#endif +BEGIN_C_DECLS struct dirent { @@ -40,16 +39,16 @@ struct dirent unsigned short d_reclen; /* Always zero. */ unsigned short d_namlen; /* Length of name in d_name. */ - /* The following exactly mimic the layout of _finddata_t ... + /* The following exactly mimic the layout of __finddata64_t ... */ unsigned d_type; /* File attributes */ - time_t d_time_create; - time_t d_time_access; /* always midnight local time */ - time_t d_time_write; - _fsize_t d_size; + __time64_t d_time_create; + __time64_t d_time_access; /* always midnight local time */ + __time64_t d_time_write; + uint64_t d_size; /* - * ...so that we may map a union of _finddata_t at the - * location of d_type (corresponding to _finddata_t.attrib), + * ...so that we may map a union of __finddata64_t at the + * location of d_type (corresponding to __finddata64_t.attrib), * and thus map this directly to the _findfirst/_findnext * returned field. */ @@ -78,16 +77,16 @@ struct _wdirent unsigned short d_reclen; /* Always zero. */ unsigned short d_namlen; /* Length of name in d_name. */ - /* The following exactly mimic the layout of _wfinddata_t ... + /* The following exactly mimic the layout of __wfinddata64_t ... */ unsigned d_type; /* File attributes */ - time_t d_time_create; /* -1 for FAT file systems */ - time_t d_time_access; /* -1 for FAT file systems */ - time_t d_time_write; - _fsize_t d_size; + __time64_t d_time_create; /* -1 for FAT file systems */ + __time64_t d_time_access; /* -1 for FAT file systems */ + __time64_t d_time_write; + uint64_t d_size; /* - * ...so that we may map a union of _wfinddata_t at the - * location of d_type (corresponding to _wfinddata_t.attrib), + * ...so that we may map a union of __wfinddata64_t at the + * location of d_type (corresponding to __wfinddata64_t.attrib), * and thus map this directly to the _wfindfirst/_wfindnext * returned field. */ @@ -107,10 +106,7 @@ void __cdecl __MINGW_NOTHROW _wrewinddir (_WDIR*); long __cdecl __MINGW_NOTHROW _wtelldir (_WDIR*); void __cdecl __MINGW_NOTHROW _wseekdir (_WDIR*, long); - -#ifdef __cplusplus -} -#endif +END_C_DECLS #if defined(_BSD_SOURCE) || defined(_WIN32) /* diff --git a/src/libcrt/tchar/dirent.c b/src/libcrt/tchar/dirent.c index 8d7f162..19b0c2a 100644 --- a/src/libcrt/tchar/dirent.c +++ b/src/libcrt/tchar/dirent.c @@ -21,10 +21,10 @@ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER * DEALINGS IN THE SOFTWARE. */ +#include #include #include #include -#include #include #define WIN32_LEAN_AND_MEAN @@ -35,6 +35,19 @@ #define DIRENT_REJECT( chk, err, rtn ) \ do { if( chk ){ errno = (err); return rtn; }} while(0) +/* MSDN says that _finddata_t is a macro, aliased to either _finddata64i32_t, + * or to _finddata32_t when _USE_32_BIT_TIME_T is defined; (MinGW also adopts + * this convention). We prefer to avoid this _USE_32_BIT_TIME_T insanity; we + * would like our local notion of _finddata_t to represent __finddata64_t. + */ +#undef _finddata_t +#define _finddata_t __finddata64_t + +/* Similarly for _wfinddata_t; we want it to represent __wfinddata64_t. + */ +#undef _wfinddata_t +#define _wfinddata_t __wfinddata64_t + union __dirstream_t { /* Actual (private) declaration for opaque data type "DIR". */ @@ -130,10 +143,10 @@ union __wdirstream_t #define DT_IGNORED (_A_RDONLY | _A_HIDDEN | _A_SYSTEM | _A_ARCH) #define DIRENT_OPEN(D) \ - ((D).dd_handle = _tfindfirst((D).dd_name, &((D).dd_dta))) + ((D).dd_handle = _tfindfirst64((D).dd_name, &((D).dd_dta))) #define DIRENT_UPDATE(D) \ - _tfindnext( (D).dd_handle, &(D).dd_dta ) + _tfindnext64( (D).dd_handle, &(D).dd_dta ) /***** -- 2.11.0