diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog index 7225d1520..fee9fd9d3 100644 --- a/winsup/cygwin/ChangeLog +++ b/winsup/cygwin/ChangeLog @@ -1,3 +1,9 @@ +2005-05-29 Corinna Vinschen + + * path.cc (path_conv::check): Move component to function scope. Set + PATH_RO only on *real* FH_NETDRIVEs or on non-FH_NETDRIVE virtual + paths. Allow non-retrievable shares to be handled as files. + 2005-05-29 Eric Blake * include/limits.h (LLONG_MIN, LLONG_MAX, ULLONG_MAX): Always define. diff --git a/winsup/cygwin/path.cc b/winsup/cygwin/path.cc index dcf0871c1..2f9c450cb 100644 --- a/winsup/cygwin/path.cc +++ b/winsup/cygwin/path.cc @@ -550,6 +550,7 @@ path_conv::check (const char *src, unsigned opt, memset (&dev, 0, sizeof (dev)); fs.clear (); normalized_path = NULL; + int component = 0; // Number of translated components if (!(opt & PC_NULLEMPTY)) error = 0; @@ -582,7 +583,7 @@ path_conv::check (const char *src, unsigned opt, Also: be careful to preserve the errno returned from symlink.check as the caller may need it. */ /* FIXME: Do we have to worry about multiple \'s here? */ - int component = 0; // Number of translated components + component = 0; // Number of translated components sym.contents[0] = '\0'; int symlen = 0; @@ -671,7 +672,8 @@ path_conv::check (const char *src, unsigned opt, fileattr = INVALID_FILE_ATTRIBUTES; goto virtual_component_retry; } - path_flags |= PATH_RO; + if (component == 0 || dev.devn != FH_NETDRIVE) + path_flags |= PATH_RO; goto out; } /* devn should not be a device. If it is, then stop parsing now. */ @@ -886,8 +888,20 @@ out: } else if (isvirtual_dev (dev.devn) && fileattr == INVALID_FILE_ATTRIBUTES) { - error = dev.devn == FH_NETDRIVE ? ENOSHARE : ENOENT; - return; + if (dev.devn == FH_NETDRIVE && component) + { + /* This case indicates a non-existant resp. a non-retrievable + share. This happens for instance if the share is a printer. + In this case the path must not be treated like a FH_NETDRIVE, + but like a FH_FS instead, so the usual open call for files + is used on it. */ + dev.parse (FH_FS); + } + else + { + error = dev.devn == FH_NETDRIVE ? ENOSHARE : ENOENT; + return; + } } else if (!need_directory || error) /* nothing to do */;