Welcome to mirror list, hosted at ThFree Co, Russian Federation.

cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
path: root/winsup
diff options
context:
space:
mode:
authorCorinna Vinschen <corinna@vinschen.de>2010-04-26 17:48:04 +0400
committerCorinna Vinschen <corinna@vinschen.de>2010-04-26 17:48:04 +0400
commit002a34fa147303ed79c1cc88fde0ae9e3b1ae4eb (patch)
tree21be9f32e360e4efc57cb662266ddb7b939a1f80 /winsup
parent3134b8ad36723477097ecf80be29b6960b9f0b3c (diff)
* mount.h (fs_info::inited): New inline method.
* path.cc (path_conv::check): Clear filesystem info if following a symlink. Use new fs_info::inited method to check if FS info is already available. (symlink_info::check): Drop fs_update_called. Use fs_info::inited method instead. Streamline test for leading space and trailing dot or space. Add comments.
Diffstat (limited to 'winsup')
-rw-r--r--winsup/cygwin/ChangeLog10
-rw-r--r--winsup/cygwin/mount.h1
-rw-r--r--winsup/cygwin/path.cc53
3 files changed, 40 insertions, 24 deletions
diff --git a/winsup/cygwin/ChangeLog b/winsup/cygwin/ChangeLog
index b2c4ce624..88c062bb2 100644
--- a/winsup/cygwin/ChangeLog
+++ b/winsup/cygwin/ChangeLog
@@ -1,3 +1,13 @@
+2010-04-26 Corinna Vinschen <corinna@vinschen.de>
+
+ * mount.h (fs_info::inited): New inline method.
+ * path.cc (path_conv::check): Clear filesystem info if following a
+ symlink. Use new fs_info::inited method to check if FS info is already
+ available.
+ (symlink_info::check): Drop fs_update_called. Use fs_info::inited
+ method instead. Streamline test for leading space and trailing dot or
+ space. Add comments.
+
2010-04-23 Corinna Vinschen <corinna@vinschen.de>
* path.h (get_nt_native_path): Add third parameter to declaration and
diff --git a/winsup/cygwin/mount.h b/winsup/cygwin/mount.h
index 0138e28a4..7133cc412 100644
--- a/winsup/cygwin/mount.h
+++ b/winsup/cygwin/mount.h
@@ -97,6 +97,7 @@ class fs_info
const char *fsname () const { return fsn[0] ? fsn : "unknown"; }
bool update (PUNICODE_STRING, HANDLE) __attribute__ ((regparm (3)));
+ bool inited () const { return !!status.flags; }
};
/* Mount table entry */
diff --git a/winsup/cygwin/path.cc b/winsup/cygwin/path.cc
index 6b0b1d1c4..63bac3797 100644
--- a/winsup/cygwin/path.cc
+++ b/winsup/cygwin/path.cc
@@ -894,8 +894,10 @@ is_virtual_symlink:
add_ext = true;
goto out;
}
- else
- break;
+ /* Following a symlink we can't trust the collected filesystem
+ information any longer. */
+ fs.clear ();
+ break;
}
else if (sym.error && sym.error != ENOENT)
{
@@ -1026,8 +1028,8 @@ out:
}
}
- /* FS has been checked already for existing files. */
- if (exists () || fs.update (get_nt_native_path (), NULL))
+ /* If FS hasn't been checked already in symlink_info::check, do so now. */
+ if (fs.inited ()|| fs.update (get_nt_native_path (), NULL))
{
/* Incoming DOS paths are treated like DOS paths in native
Windows applications. No ACLs, just default settings. */
@@ -2198,7 +2200,6 @@ symlink_info::check (char *path, const suffix_info *suffixes, unsigned opt,
IO_STATUS_BLOCK io;
FILE_BASIC_INFORMATION fbi;
suffix_scan suffix;
- bool fs_update_called = false;
const ULONG ci_flag = cygwin_shared->obcaseinsensitive
|| (pflags & PATH_NOPOSIX) ? OBJ_CASE_INSENSITIVE : 0;
@@ -2282,7 +2283,7 @@ restart:
if (status == STATUS_OBJECT_NAME_NOT_FOUND)
{
if (ci_flag == 0 && wincap.has_broken_udf ()
- && (!fs_update_called || fs.is_udf ()))
+ && (!fs.inited () || fs.is_udf ()))
{
/* On NT 5.x UDF is broken (at least) in terms of case
sensitivity. When trying to open a file case sensitive,
@@ -2297,8 +2298,8 @@ restart:
attr.Attributes = 0;
if (NT_SUCCESS (status))
{
- if (!fs_update_called)
- fs_update_called = fs.update (&upath, h);
+ if (!fs.inited ())
+ fs.update (&upath, h);
if (!fs.is_udf ())
{
NtClose (h);
@@ -2316,25 +2317,29 @@ restart:
already attach a suffix *and* the above special case for UDF
on XP didn't succeeed. */
if (!restarted && !*ext_here
- && (!fs_update_called || fs.has_dos_filenames_only ()))
+ && (!fs.inited () || fs.has_dos_filenames_only ()))
{
- /* Check for leading space or trailing dot or space in
+ /* Check for trailing dot or space or leading space in
last component. */
- char *pend = ext_here;
- if (pend[-1] == '.' || pend[-1] == ' ')
- --pend;
- char *pbeg = pend;
- while (pbeg[-1] != '\\')
- --pbeg;
- /* If so, call fs.update to check if the filesystem is one of
- the broken ones. */
- if (*pbeg == ' ' || *pend != '\0')
+ char *p = ext_here - 1;
+ if (*p != '.' && *p != ' ')
+ {
+ while (*--p != '\\')
+ ;
+ if (*++p != ' ')
+ p = NULL;
+ }
+ if (p)
{
- if (!fs_update_called)
- fs_update_called = fs.update (&upath, NULL);
+ /* If so, check if file resides on one of the known broken
+ FSes only supporting filenames following DOS rules. */
+ if (!fs.inited ())
+ fs.update (&upath, NULL);
if (fs.has_dos_filenames_only ())
{
- /* If so, try again. */
+ /* If so, try again. Since we now know the FS, the
+ filenames will be tweaked to follow DOS rules via the
+ third parameter in the call to get_nt_native_path. */
restarted = true;
goto restart;
}
@@ -2345,7 +2350,7 @@ restart:
if (NT_SUCCESS (status)
/* Check file system while we're having the file open anyway.
This speeds up path_conv noticably (~10%). */
- && (fs_update_called || (fs_update_called = fs.update (&upath, h)))
+ && (fs.inited () || (fs.update (&upath, h)))
&& NT_SUCCESS (status = fs.has_buggy_basic_info ()
? NtQueryAttributesFile (&attr, &fbi)
: NtQueryInformationFile (h, &io, &fbi, sizeof fbi,
@@ -2415,7 +2420,7 @@ restart:
TRUE, &basename, TRUE);
/* Take the opportunity to check file system while we're
having the handle to the parent dir. */
- fs_update_called = fs.update (&upath, h);
+ fs.update (&upath, h);
NtClose (dir);
if (!NT_SUCCESS (status))
{