summaryrefslogtreecommitdiff
path: root/pp_ctl.c
diff options
context:
space:
mode:
authorDaniel Dragan <bulk88@hotmail.com>2015-08-16 04:30:23 -0400
committerZefram <zefram@fysh.org>2017-11-12 02:05:10 +0000
commitd1ac83c4011b4bf51ca3fb070737a97a6c6ac545 (patch)
treedea46ad1fb806ccb24cf176b56ff606f372cc70a /pp_ctl.c
parent69374fe705978962b85217f3eb828a93f836fd8d (diff)
downloadperl-d1ac83c4011b4bf51ca3fb070737a97a6c6ac545.tar.gz
fix do dir returning no $!
do()ing a directory was returning false/empty string in $!, which isn't an error, yet documentation says $! should have the error code in it. Fix this by returning EISDIR for dirs, and EINVAL for block devices. [perl #125774] Remove "errno = 0" and comment added in b2da7ead68, since now there is no scenario where errno is uninitialized, since the dir and block device failure branches now set errno, where previously they didn't.
Diffstat (limited to 'pp_ctl.c')
-rw-r--r--pp_ctl.c25
1 files changed, 17 insertions, 8 deletions
diff --git a/pp_ctl.c b/pp_ctl.c
index a113b48db8..7581b37985 100644
--- a/pp_ctl.c
+++ b/pp_ctl.c
@@ -3562,15 +3562,22 @@ S_check_type_and_open(pTHX_ SV *name)
errno EACCES, so only do a stat to separate a dir from a real EACCES
caused by user perms */
#ifndef WIN32
- /* we use the value of errno later to see how stat() or open() failed.
- * We don't want it set if the stat succeeded but we still failed,
- * such as if the name exists, but is a directory */
- errno = 0;
-
st_rc = PerlLIO_stat(p, &st);
- if (st_rc < 0 || S_ISDIR(st.st_mode) || S_ISBLK(st.st_mode)) {
+ if (st_rc < 0)
return NULL;
+ else {
+ int eno;
+ if(S_ISBLK(st.st_mode)) {
+ eno = EINVAL;
+ goto not_file;
+ }
+ else if(S_ISDIR(st.st_mode)) {
+ eno = EISDIR;
+ not_file:
+ errno = eno;
+ return NULL;
+ }
}
#endif
@@ -3582,8 +3589,10 @@ S_check_type_and_open(pTHX_ SV *name)
int eno;
st_rc = PerlLIO_stat(p, &st);
if (st_rc >= 0) {
- if(S_ISDIR(st.st_mode) || S_ISBLK(st.st_mode))
- eno = 0;
+ if(S_ISDIR(st.st_mode))
+ eno = EISDIR;
+ else if(S_ISBLK(st.st_mode))
+ eno = EINVAL;
else
eno = EACCES;
errno = eno;