Revert "ntdll: Avoid one of the calls to getattrlist() when read_directory_getattrlist() checks the case sensitivity of the file system.".

This was wrong-headed and could never have worked.  The second getattrlist()
call that I was trying to avoid was only necessary when the first fails.  Given
that the first failed, its results can't be used to avoid the second, no matter
what information we requested.

This reverts commit 5514df9d4e.
This commit is contained in:
Ken Thomases 2015-06-11 16:04:04 -05:00 committed by Alexandre Julliard
parent f634faaae3
commit e7fa766378
1 changed files with 22 additions and 40 deletions

View File

@ -983,35 +983,43 @@ static void add_fs_cache( dev_t dev, fsid_t fsid, BOOLEAN case_sensitive )
}
/***********************************************************************
* get_dir_case_sensitivity_attr_by_id
* get_dir_case_sensitivity_attr
*
* Checks if the volume with the specified device and file system IDs
* is case sensitive or not. Uses getattrlist(2).
* Checks if the volume containing the specified directory is case
* sensitive or not. Uses getattrlist(2).
*/
static int get_dir_case_sensitivity_attr_by_id( dev_t dev, fsid_t fsid )
static int get_dir_case_sensitivity_attr( const char *dir )
{
char *mntpoint = NULL;
struct attrlist attr;
struct vol_caps caps;
struct get_fsid get_fsid;
struct fs_cache *entry;
/* First get the FS ID of the volume */
attr.bitmapcount = ATTR_BIT_MAP_COUNT;
attr.reserved = 0;
attr.commonattr = ATTR_CMN_DEVID|ATTR_CMN_FSID;
attr.volattr = attr.dirattr = attr.fileattr = attr.forkattr = 0;
get_fsid.size = 0;
if (getattrlist( dir, &attr, &get_fsid, sizeof(get_fsid), 0 ) != 0 ||
get_fsid.size != sizeof(get_fsid))
return -1;
/* Try to look it up in the cache */
entry = look_up_fs_cache( dev );
if (entry && !memcmp( &entry->fsid, &fsid, sizeof(fsid_t) ))
entry = look_up_fs_cache( get_fsid.dev );
if (entry && !memcmp( &entry->fsid, &get_fsid.fsid, sizeof(fsid_t) ))
/* Cache lookup succeeded */
return entry->case_sensitive;
/* Cache is stale at this point, we have to update it */
mntpoint = get_device_mount_point( dev );
mntpoint = get_device_mount_point( get_fsid.dev );
/* Now look up the case-sensitivity */
attr.bitmapcount = ATTR_BIT_MAP_COUNT;
attr.reserved = attr.commonattr = 0;
attr.commonattr = 0;
attr.volattr = ATTR_VOL_INFO|ATTR_VOL_CAPABILITIES;
attr.dirattr = attr.fileattr = attr.forkattr = 0;
if (getattrlist( mntpoint, &attr, &caps, sizeof(caps), 0 ) < 0)
{
RtlFreeHeap( GetProcessHeap(), 0, mntpoint );
add_fs_cache( dev, fsid, TRUE );
add_fs_cache( get_fsid.dev, get_fsid.fsid, TRUE );
return TRUE;
}
RtlFreeHeap( GetProcessHeap(), 0, mntpoint );
@ -1028,34 +1036,11 @@ static int get_dir_case_sensitivity_attr_by_id( dev_t dev, fsid_t fsid )
else
ret = TRUE;
/* Update the cache */
add_fs_cache( dev, fsid, ret );
add_fs_cache( get_fsid.dev, get_fsid.fsid, ret );
return ret;
}
return FALSE;
}
/***********************************************************************
* get_dir_case_sensitivity_attr
*
* Checks if the volume containing the specified directory is case
* sensitive or not. Uses getattrlist(2).
*/
static int get_dir_case_sensitivity_attr( const char *dir )
{
struct attrlist attr;
struct get_fsid get_fsid;
/* First get the FS ID of the volume */
attr.bitmapcount = ATTR_BIT_MAP_COUNT;
attr.reserved = 0;
attr.commonattr = ATTR_CMN_DEVID|ATTR_CMN_FSID;
attr.volattr = attr.dirattr = attr.fileattr = attr.forkattr = 0;
get_fsid.size = 0;
if (getattrlist( dir, &attr, &get_fsid, sizeof(get_fsid), 0 ) != 0 ||
get_fsid.size != sizeof(get_fsid))
return -1;
return get_dir_case_sensitivity_attr_by_id( get_fsid.dev, get_fsid.fsid );
}
#endif
/***********************************************************************
@ -2163,8 +2148,6 @@ static int read_directory_getattrlist( int fd, IO_STATUS_BLOCK *io, void *buffer
{
u_int32_t length;
struct attrreference name_reference;
dev_t devid;
fsid_t fsid;
fsobj_type_t type;
char name[NAME_MAX * 3 + 1];
} attrlist_buffer;
@ -2196,7 +2179,7 @@ static int read_directory_getattrlist( int fd, IO_STATUS_BLOCK *io, void *buffer
memset( &attrlist, 0, sizeof(attrlist) );
attrlist.bitmapcount = ATTR_BIT_MAP_COUNT;
attrlist.commonattr = ATTR_CMN_NAME | ATTR_CMN_DEVID | ATTR_CMN_FSID | ATTR_CMN_OBJTYPE;
attrlist.commonattr = ATTR_CMN_NAME | ATTR_CMN_OBJTYPE;
ret = getattrlist( unix_name, &attrlist, &attrlist_buffer, sizeof(attrlist_buffer), FSOPT_NOFOLLOW );
/* If unix_name named a symlink, the above may have succeeded even if the symlink is broken.
Check that with another call without FSOPT_NOFOLLOW. We don't ask for any attributes. */
@ -2216,8 +2199,7 @@ static int read_directory_getattrlist( int fd, IO_STATUS_BLOCK *io, void *buffer
}
else io->u.Status = STATUS_NO_MORE_FILES;
}
else if ((errno == ENOENT || errno == ENOTDIR) &&
!get_dir_case_sensitivity_attr_by_id( attrlist_buffer.devid, attrlist_buffer.fsid ))
else if ((errno == ENOENT || errno == ENOTDIR) && !get_dir_case_sensitivity("."))
{
io->u.Status = STATUS_NO_MORE_FILES;
ret = 0;