[CRT] Update file descriptor handling to match Wine (3/7). CORE-14504

Import Wine commits by Piotr Caban:
* 6c2d4f1092d msvcrt: Use fd critical section in _fstat64.
* 9278190d468 msvcrt: Use fd critical section in _futime64.
This commit is contained in:
Thomas Faber 2018-03-25 16:15:31 +02:00
parent 9eb1eae28c
commit c529e727d7
No known key found for this signature in database
GPG key ID: 076E7C3D44720826
4 changed files with 35 additions and 23 deletions

View file

@ -153,4 +153,13 @@ typedef struct _sig_element
char* _setlocale(int,const char*); char* _setlocale(int,const char*);
NTSYSAPI VOID NTAPI RtlAssert(PVOID FailedAssertion,PVOID FileName,ULONG LineNumber,PCHAR Message); NTSYSAPI VOID NTAPI RtlAssert(PVOID FailedAssertion,PVOID FileName,ULONG LineNumber,PCHAR Message);
/* ioinfo structure size is different in msvcrXX.dll's */
typedef struct {
HANDLE handle;
unsigned char wxflag;
char lookahead[3];
int exflag;
CRITICAL_SECTION crit;
} ioinfo;
#endif /* __WINE_MSVCRT_H */ #endif /* __WINE_MSVCRT_H */

View file

@ -45,6 +45,7 @@
#include <precomp.h> #include <precomp.h>
#include "wine/unicode.h" #include "wine/unicode.h"
#include "internal/wine/msvcrt.h"
#include <sys/utime.h> #include <sys/utime.h>
#include <direct.h> #include <direct.h>
@ -113,15 +114,6 @@ static char utf16_bom[2] = { 0xff, 0xfe };
#define MSVCRT_INTERNAL_BUFSIZ 4096 #define MSVCRT_INTERNAL_BUFSIZ 4096
/* ioinfo structure size is different in msvcrXX.dll's */
typedef struct {
HANDLE handle;
unsigned char wxflag;
char lookahead[3];
int exflag;
CRITICAL_SECTION crit;
} ioinfo;
/********************************************************************* /*********************************************************************
* __pioinfo (MSVCRT.@) * __pioinfo (MSVCRT.@)
* array of pointers to ioinfo arrays [32] * array of pointers to ioinfo arrays [32]
@ -180,7 +172,7 @@ static inline ioinfo* get_ioinfo_nolock(int fd)
return ret + (fd%MSVCRT_FD_BLOCK_SIZE); return ret + (fd%MSVCRT_FD_BLOCK_SIZE);
} }
static inline ioinfo* get_ioinfo(int fd) /*static*/ inline ioinfo* get_ioinfo(int fd)
{ {
ioinfo *ret = get_ioinfo_nolock(fd); ioinfo *ret = get_ioinfo_nolock(fd);
if(ret->exflag & EF_CRIT_INIT) if(ret->exflag & EF_CRIT_INIT)
@ -188,7 +180,7 @@ static inline ioinfo* get_ioinfo(int fd)
return ret; return ret;
} }
static inline void release_ioinfo(ioinfo *info) /*static*/ inline void release_ioinfo(ioinfo *info)
{ {
if(info->exflag & EF_CRIT_INIT) if(info->exflag & EF_CRIT_INIT)
LeaveCriticalSection(&info->crit); LeaveCriticalSection(&info->crit);

View file

@ -1,8 +1,10 @@
#include <precomp.h> #include <precomp.h>
#include <tchar.h> #include <tchar.h>
#include <direct.h> #include <direct.h>
#include <internal/wine/msvcrt.h>
HANDLE fdtoh(int fd); inline ioinfo* get_ioinfo(int fd);
inline void release_ioinfo(ioinfo *info);
#define ALL_S_IREAD (_S_IREAD | (_S_IREAD >> 3) | (_S_IREAD >> 6)) #define ALL_S_IREAD (_S_IREAD | (_S_IREAD >> 3) | (_S_IREAD >> 6))
#define ALL_S_IWRITE (_S_IWRITE | (_S_IWRITE >> 3) | (_S_IWRITE >> 6)) #define ALL_S_IWRITE (_S_IWRITE | (_S_IWRITE >> 3) | (_S_IWRITE >> 6))
@ -97,25 +99,29 @@ int CDECL _tstat64(const _TCHAR *path, struct __stat64 *buf)
int CDECL _fstat64(int fd, struct __stat64* buf) int CDECL _fstat64(int fd, struct __stat64* buf)
{ {
ioinfo *info = get_ioinfo(fd);
DWORD dw; DWORD dw;
DWORD type; DWORD type;
BY_HANDLE_FILE_INFORMATION hfi; BY_HANDLE_FILE_INFORMATION hfi;
HANDLE hand = fdtoh(fd);
TRACE(":fd (%d) stat (%p)\n",fd,buf); TRACE(":fd (%d) stat (%p)\n", fd, buf);
if (hand == INVALID_HANDLE_VALUE) if (info->handle == INVALID_HANDLE_VALUE)
{
release_ioinfo(info);
return -1; return -1;
}
if (!buf) if (!buf)
{ {
WARN(":failed-NULL buf\n"); WARN(":failed-NULL buf\n");
_dosmaperr(ERROR_INVALID_PARAMETER); _dosmaperr(ERROR_INVALID_PARAMETER);
release_ioinfo(info);
return -1; return -1;
} }
memset(&hfi, 0, sizeof(hfi)); memset(&hfi, 0, sizeof(hfi));
memset(buf, 0, sizeof(struct __stat64)); memset(buf, 0, sizeof(struct __stat64));
type = GetFileType(hand); type = GetFileType(info->handle);
if (type == FILE_TYPE_PIPE) if (type == FILE_TYPE_PIPE)
{ {
buf->st_dev = buf->st_rdev = fd; buf->st_dev = buf->st_rdev = fd;
@ -130,10 +136,11 @@ int CDECL _fstat64(int fd, struct __stat64* buf)
} }
else /* FILE_TYPE_DISK etc. */ else /* FILE_TYPE_DISK etc. */
{ {
if (!GetFileInformationByHandle(hand, &hfi)) if (!GetFileInformationByHandle(info->handle, &hfi))
{ {
WARN(":failed-last error (%d)\n",GetLastError()); WARN(":failed-last error (%d)\n",GetLastError());
_dosmaperr(ERROR_INVALID_PARAMETER); _dosmaperr(ERROR_INVALID_PARAMETER);
release_ioinfo(info);
return -1; return -1;
} }
buf->st_mode = _S_IFREG | ALL_S_IREAD; buf->st_mode = _S_IFREG | ALL_S_IREAD;
@ -148,6 +155,7 @@ int CDECL _fstat64(int fd, struct __stat64* buf)
} }
TRACE(":dwFileAttributes = 0x%x, mode set to 0x%x\n",hfi.dwFileAttributes, TRACE(":dwFileAttributes = 0x%x, mode set to 0x%x\n",hfi.dwFileAttributes,
buf->st_mode); buf->st_mode);
release_ioinfo(info);
return 0; return 0;
} }

View file

@ -39,8 +39,10 @@
#include <time.h> #include <time.h>
#include <sys/utime.h> #include <sys/utime.h>
#include "bitsfixup.h" #include "bitsfixup.h"
#include <internal/wine/msvcrt.h>
HANDLE fdtoh(int fd); inline ioinfo* get_ioinfo(int fd);
inline void release_ioinfo(ioinfo *info);
/****************************************************************************** /******************************************************************************
* \name _futime * \name _futime
@ -52,12 +54,12 @@ HANDLE fdtoh(int fd);
int int
_futime(int fd, struct _utimbuf *filetime) _futime(int fd, struct _utimbuf *filetime)
{ {
HANDLE handle; ioinfo *info = get_ioinfo(fd);
FILETIME at, wt; FILETIME at, wt;
handle = fdtoh(fd); if (info->handle == INVALID_HANDLE_VALUE)
if (handle == INVALID_HANDLE_VALUE)
{ {
release_ioinfo(info);
return -1; return -1;
} }
@ -84,11 +86,12 @@ _futime(int fd, struct _utimbuf *filetime)
} }
} }
if (!SetFileTime(handle, NULL, &at, &wt)) if (!SetFileTime(info->handle, NULL, &at, &wt))
{ {
release_ioinfo(info);
_dosmaperr(GetLastError()); _dosmaperr(GetLastError());
return -1 ; return -1 ;
} }
release_ioinfo(info);
return 0; return 0;
} }