diff options
author | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2012-03-26 02:41:04 +0000 |
---|---|---|
committer | nobu <nobu@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2012-03-26 02:41:04 +0000 |
commit | b83ad31c437ca05a3eaa899f4426d2f217212678 (patch) | |
tree | 5ad3fef8627331a420abfd2c21ef0fd2486ee36a /win32 | |
parent | 73a184cc3a4ead8a3242a8f04c4e65fa99026eef (diff) | |
download | ruby-b83ad31c437ca05a3eaa899f4426d2f217212678.tar.gz |
* win32/win32.c (rb_w32_open, rb_w32_wopen): check if the file is a
directory when access denied, to set errno to EISDIR.
git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@35129 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'win32')
-rw-r--r-- | win32/win32.c | 37 |
1 files changed, 33 insertions, 4 deletions
diff --git a/win32/win32.c b/win32/win32.c index b685896755..2657d7403d 100644 --- a/win32/win32.c +++ b/win32/win32.c @@ -5185,6 +5185,28 @@ rb_w32_uopen(const char *file, int oflag, ...) } /* License: Ruby's */ +static int +check_if_dir(const char *file) +{ + struct stati64 st; + if (rb_w32_stati64(file, &st) != 0 || !S_ISDIR(st.st_mode)) + return FALSE; + errno = EISDIR; + return TRUE; +} + +/* License: Ruby's */ +static int +check_if_wdir(const WCHAR *wfile) +{ + struct stati64 st; + if (wstati64(wfile, &st) != 0 || !S_ISDIR(st.st_mode)) + return FALSE; + errno = EISDIR; + return TRUE; +} + +/* License: Ruby's */ int rb_w32_open(const char *file, int oflag, ...) { @@ -5197,8 +5219,11 @@ rb_w32_open(const char *file, int oflag, ...) pmode = va_arg(arg, int); va_end(arg); - if ((oflag & O_TEXT) || !(oflag & O_BINARY)) - return _open(file, oflag, pmode); + if ((oflag & O_TEXT) || !(oflag & O_BINARY)) { + ret = _open(file, oflag, pmode); + if (ret == -1 && errno == EACCES) check_if_dir(file); + return ret; + } if (!(wfile = filecp_to_wstr(file, NULL))) return -1; @@ -5224,7 +5249,9 @@ rb_w32_wopen(const WCHAR *file, int oflag, ...) va_start(arg, oflag); pmode = va_arg(arg, int); va_end(arg); - return _wopen(file, oflag, pmode); + fd = _wopen(file, oflag, pmode); + if (fd == -1 && errno == EACCES) check_if_wdir(file); + return fd; } sec.nLength = sizeof(sec); @@ -5340,7 +5367,9 @@ rb_w32_wopen(const WCHAR *file, int oflag, ...) h = CreateFileW(file, access, FILE_SHARE_READ | FILE_SHARE_WRITE, &sec, create, attr, NULL); if (h == INVALID_HANDLE_VALUE) { - errno = map_errno(GetLastError()); + DWORD e = GetLastError(); + if (e != ERROR_ACCESS_DENIED || !check_if_wdir(file)) + errno = map_errno(e); MTHREAD_ONLY(LeaveCriticalSection(&_pioinfo(fd)->lock)); fd = -1; goto quit; |