* globals.cc: Improve comment on R/O UNICODE_STRINGs.

* mount.h (class fs_info): Add is_mvfs bit.
	* mount.cc (fs_info::update): Recognize MVFS remote filesystem.
	(fillout_mntent): Reorder filesystem checks for speed.  Add
	mvfs, unixfs, and sunwnfs filesystem types.
	* path.h (class path_conv): Add fs_is_mvfs method.
	* path.cc (symlink_worker): On MVFS, always create symlinks as
	Windows shortcuts.  Explain why.
This commit is contained in:
Corinna Vinschen 2009-07-17 09:00:19 +00:00
parent b7735ec72d
commit 0fb0fb8391
6 changed files with 48 additions and 13 deletions

View File

@ -1,3 +1,14 @@
2009-07-17 Corinna Vinschen <corinna@vinschen.de>
* globals.cc: Improve comment on R/O UNICODE_STRINGs.
* mount.h (class fs_info): Add is_mvfs bit.
* mount.cc (fs_info::update): Recognize MVFS remote filesystem.
(fillout_mntent): Reorder filesystem checks for speed. Add
mvfs, unixfs, and sunwnfs filesystem types.
* path.h (class path_conv): Add fs_is_mvfs method.
* path.cc (symlink_worker): On MVFS, always create symlinks as
Windows shortcuts. Explain why.
2009-07-16 Corinna Vinschen <corinna@vinschen.de>
* syscalls.cc (unlink_nt): First remove the R/O DOS attribute with

View File

@ -72,7 +72,13 @@ char NO_COPY almost_null[1];
char *old_title;
/* Heavily-used const UNICODE_STRINGs are defined here once. */
/* Heavily-used const UNICODE_STRINGs are defined here once. The idea is a
speed improvement by not having to initialize a UNICODE_STRING every time
we make a string comparison. The strings are not defined as const,
because the respective NT functions are not taking const arguments
and doing so here results in lots of extra casts for no good reason.
Rather, the strings are placed in the R/O section .rdata, so we get
a SEGV if some code erroneously tries to overwrite these strings. */
#define _ROU(_s) \
{ Length: sizeof (_s) - sizeof (WCHAR), \
MaximumLength: sizeof (_s), \

View File

@ -240,6 +240,10 @@ fs_info::update (PUNICODE_STRING upath, HANDLE in_vol)
&& FS_IS_NETAPP_DATAONTAP)
/* Microsoft NFS needs distinct access methods for metadata. */
&& !is_nfs (RtlEqualUnicodeString (&fsname, &ro_u_nfs, FALSE))
/* MVFS == Rational ClearCase remote filesystem. Has a couple of
drawbacks, like not supporting DOS attributes other than R/O
and stuff like that. */
&& !is_mvfs (RtlEqualUnicodePathPrefix (&fsname, &ro_u_mvfs, FALSE))
/* Known remote file system which can't handle calls to
NtQueryDirectoryFile(FileIdBothDirectoryInformation) */
&& !is_unixfs (RtlEqualUnicodeString (&fsname, &ro_u_unixfs, FALSE)))
@ -1386,22 +1390,28 @@ fillout_mntent (const char *native_path, const char *posix_path, unsigned flags)
RtlAppendUnicodeToString (&unat, L"\\");
mntinfo.update (&unat, NULL);
if (mntinfo.is_samba())
if (mntinfo.is_ntfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "ntfs");
else if (mntinfo.is_fat ())
strcpy (_my_tls.locals.mnt_type, (char *) "vfat");
else if (mntinfo.is_samba())
strcpy (_my_tls.locals.mnt_type, (char *) "smbfs");
else if (mntinfo.is_nfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "nfs");
else if (mntinfo.is_fat ())
strcpy (_my_tls.locals.mnt_type, (char *) "vfat");
else if (mntinfo.is_ntfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "ntfs");
else if (mntinfo.is_netapp ())
strcpy (_my_tls.locals.mnt_type, (char *) "netapp");
else if (mntinfo.is_udf ())
strcpy (_my_tls.locals.mnt_type, (char *) "udf");
else if (mntinfo.is_cdrom ())
strcpy (_my_tls.locals.mnt_type, (char *) "iso9660");
else if (mntinfo.is_netapp ())
strcpy (_my_tls.locals.mnt_type, (char *) "netapp");
else if (mntinfo.is_csc_cache ())
strcpy (_my_tls.locals.mnt_type, (char *) "csc-cache");
else if (mntinfo.is_mvfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "mvfs");
else if (mntinfo.is_unixfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "unixfs");
else if (mntinfo.is_sunwnfs ())
strcpy (_my_tls.locals.mnt_type, (char *) "sunwnfs");
else
strcpy (_my_tls.locals.mnt_type, (char *) "unknown");

View File

@ -37,6 +37,7 @@ class fs_info
unsigned is_csc_cache : 1;
unsigned is_sunwnfs : 1;
unsigned is_unixfs : 1;
unsigned is_mvfs : 1;
};
unsigned long fs_flags;
};
@ -65,6 +66,7 @@ class fs_info
IMPLEMENT_STATUS_FLAG (bool, is_csc_cache)
IMPLEMENT_STATUS_FLAG (bool, is_sunwnfs)
IMPLEMENT_STATUS_FLAG (bool, is_unixfs)
IMPLEMENT_STATUS_FLAG (bool, is_mvfs)
ULONG serial_number () const { return sernum; }
int has_buggy_open () const {return is_sunwnfs ();}

View File

@ -1367,6 +1367,7 @@ symlink_worker (const char *oldpath, const char *newpath, bool use_winsym,
HANDLE fh;
tmp_pathbuf tp;
unsigned check_opt;
bool mk_winsym = use_winsym;
/* POSIX says that empty 'newpath' is invalid input while empty
'oldpath' is valid -- it's symlink resolver job to verify if
@ -1397,7 +1398,11 @@ symlink_worker (const char *oldpath, const char *newpath, bool use_winsym,
check_opt = PC_SYM_NOFOLLOW | PC_POSIX | (isdevice ? PC_NOWARN : 0);
/* We need the normalized full path below. */
win32_newpath.check (newpath, check_opt, stat_suffixes);
if (use_winsym && !win32_newpath.exists ()
/* MVFS doesn't handle the SYSTEM DOS attribute, but it handles the R/O
attribute. Therefore we create symlinks on MVFS always as shortcuts. */
mk_winsym |= win32_newpath.fs_is_mvfs ();
if (mk_winsym && !win32_newpath.exists ()
&& (isdevice || !win32_newpath.fs_is_nfs ()))
{
char *newplnk = tp.c_get ();
@ -1449,7 +1454,7 @@ symlink_worker (const char *oldpath, const char *newpath, bool use_winsym,
goto done;
}
if (use_winsym)
if (mk_winsym)
{
ITEMIDLIST *pidl = NULL;
size_t full_len = 0;
@ -1634,8 +1639,8 @@ symlink_worker (const char *oldpath, const char *newpath, bool use_winsym,
status = NtWriteFile (fh, NULL, NULL, NULL, &io, buf, cp - buf, NULL, NULL);
if (NT_SUCCESS (status) && io.Information == (ULONG) (cp - buf))
{
status = NtSetAttributesFile (fh, use_winsym ? FILE_ATTRIBUTE_READONLY
: FILE_ATTRIBUTE_SYSTEM);
status = NtSetAttributesFile (fh, mk_winsym ? FILE_ATTRIBUTE_READONLY
: FILE_ATTRIBUTE_SYSTEM);
if (!NT_SUCCESS (status))
debug_printf ("Setting attributes failed, status = %p", status);
res = 0;
@ -1653,7 +1658,7 @@ symlink_worker (const char *oldpath, const char *newpath, bool use_winsym,
done:
syscall_printf ("%d = symlink_worker (%s, %s, %d, %d)", res, oldpath,
newpath, use_winsym, isdevice);
newpath, mk_winsym, isdevice);
return res;
}

View File

@ -231,6 +231,7 @@ class path_conv
bool fs_is_nfs () const {return fs.is_nfs ();}
bool fs_is_netapp () const {return fs.is_netapp ();}
bool fs_is_cdrom () const {return fs.is_cdrom ();}
bool fs_is_mvfs () const {return fs.is_mvfs ();}
ULONG fs_serial_number () const {return fs.serial_number ();}
void set_path (const char *p) {strcpy (path, p);}
void fillin (HANDLE h);