summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorCorinna Vinschen <corinna@vinschen.de>2019-01-06 20:13:52 +0100
committerCorinna Vinschen <corinna@vinschen.de>2019-01-06 20:30:14 +0100
commitba12614f79347e6d67af79b7369869890aa5c741 (patch)
tree4bbc6a7f512d41d2811b38fb4a12f49d3475b10b
parentc1023ee353705671aa9a8e4e1179022277add2aa (diff)
downloadcygnal-ba12614f79347e6d67af79b7369869890aa5c741.tar.gz
cygnal-ba12614f79347e6d67af79b7369869890aa5c741.tar.bz2
cygnal-ba12614f79347e6d67af79b7369869890aa5c741.zip
Cygwin: path_conv: add PATH_RESOLVE_PROCFD path_types flag
path_conv now sets the PATH_RESOLVE_PROCFD flag in path_flags if the PC_SYM_NOFOLLOW_PROCFD pathconv_arg flag has been set on input *and* the file is actually a proc fd symlink. Add matching path_conv::follow_fd_symlink method for checking and use it in open(2). Signed-off-by: Corinna Vinschen <corinna@vinschen.de>
-rw-r--r--winsup/cygwin/path.cc5
-rw-r--r--winsup/cygwin/path.h2
-rw-r--r--winsup/cygwin/syscalls.cc8
3 files changed, 10 insertions, 5 deletions
diff --git a/winsup/cygwin/path.cc b/winsup/cygwin/path.cc
index 0a68671fb..158f1e5fb 100644
--- a/winsup/cygwin/path.cc
+++ b/winsup/cygwin/path.cc
@@ -850,7 +850,10 @@ path_conv::check (const char *src, unsigned opt,
case virt_fdsymlink:
/* Allow open/linkat to do the right thing. */
if (opt & PC_SYM_NOFOLLOW_PROCFD)
- opt &= ~PC_SYM_FOLLOW;
+ {
+ opt &= ~PC_SYM_FOLLOW;
+ sym.path_flags |= PATH_RESOLVE_PROCFD;
+ }
/*FALLTHRU*/
case virt_symlink:
goto is_virtual_symlink;
diff --git a/winsup/cygwin/path.h b/winsup/cygwin/path.h
index 69da8fd93..af10321c5 100644
--- a/winsup/cygwin/path.h
+++ b/winsup/cygwin/path.h
@@ -69,6 +69,7 @@ enum path_types
PATH_REP = _BIT ( 3),
PATH_SYMLINK = _BIT ( 4),
PATH_SOCKET = _BIT ( 5),
+ PATH_RESOLVE_PROCFD = _BIT ( 6),
PATH_DONT_USE = _BIT (31) /* conversion to signed happens. */
};
@@ -192,6 +193,7 @@ class path_conv
int iscygexec () const {return mount_flags & MOUNT_CYGWIN_EXEC;}
int isopen () const {return path_flags & PATH_OPEN;}
int isctty_capable () const {return path_flags & PATH_CTTY;}
+ int follow_fd_symlink () const {return path_flags & PATH_RESOLVE_PROCFD;}
void set_cygexec (bool isset)
{
if (isset)
diff --git a/winsup/cygwin/syscalls.cc b/winsup/cygwin/syscalls.cc
index 9f43512b2..60f66a63b 100644
--- a/winsup/cygwin/syscalls.cc
+++ b/winsup/cygwin/syscalls.cc
@@ -1398,13 +1398,13 @@ open (const char *unix_path, int flags, ...)
if (fd < 0)
__leave; /* errno already set */
+ int opt = PC_OPEN | PC_SYM_NOFOLLOW_PROCFD;
+ opt |= (flags & (O_NOFOLLOW | O_EXCL)) ? PC_SYM_NOFOLLOW
+ : PC_SYM_FOLLOW;
/* This is a temporary kludge until all utilities can catch up
with a change in behavior that implements linux functionality:
opening a tty should not automatically cause it to become the
controlling tty for the process. */
- int opt = PC_OPEN | PC_SYM_NOFOLLOW_PROCFD;
- opt |= (flags & (O_NOFOLLOW | O_EXCL)) ? PC_SYM_NOFOLLOW
- : PC_SYM_FOLLOW;
if (!(flags & O_NOCTTY) && fd > 2 && myself->ctty != -2)
{
flags |= O_NOCTTY;
@@ -1472,7 +1472,7 @@ open (const char *unix_path, int flags, ...)
fh = fh_file;
}
- if (fh->dev () == FH_PROCESSFD)
+ if (fh->dev () == FH_PROCESSFD && fh->pc.follow_fd_symlink ())
{
/* Reopen file by descriptor */
fh_file = fh->fd_reopen (flags);