load_and_init_upcase() currently aliases vol->upcase to the global default upcase whenever the shared prefix matches, and then truncates vol->upcase_len to that shorter prefix. The result is correct only by accident: upcase[] accesses in name collation are gated by upcase_len, so the prefix-equality alias produces the same fold output as keeping the volume's own shorter table. Still, prefix equality is not equality: the volume table is logically distinct from the default and should not be replaced by it unless they are byte-for-byte identical. Use memcmp() to compare the complete table in one expression and drop the now-redundant upcase_len rewrite. No user-visible change is expected for compliant volumes whose $UpCase has exactly default_upcase_len entries; shorter volume tables are no longer aliased to the default. Signed-off-by: DaeMyung Kang --- fs/ntfs/super.c | 12 +++--------- 1 file changed, 3 insertions(+), 9 deletions(-) diff --git a/fs/ntfs/super.c b/fs/ntfs/super.c index 14fd244f29fe..971c2822f5e3 100644 --- a/fs/ntfs/super.c +++ b/fs/ntfs/super.c @@ -1323,7 +1323,6 @@ static bool load_and_init_upcase(struct ntfs_volume *vol) u8 *addr; pgoff_t index, max_index; unsigned int size; - int i, max; ntfs_debug("Entering."); /* Read upcase table and setup vol->upcase and vol->upcase_len. */ @@ -1374,16 +1373,11 @@ static bool load_and_init_upcase(struct ntfs_volume *vol) mutex_unlock(&ntfs_lock); return true; } - max = default_upcase_len; - if (max > vol->upcase_len) - max = vol->upcase_len; - for (i = 0; i < max; i++) - if (vol->upcase[i] != default_upcase[i]) - break; - if (i == max) { + if (default_upcase_len == vol->upcase_len && + !memcmp(vol->upcase, default_upcase, + default_upcase_len * sizeof(*default_upcase))) { kvfree(vol->upcase); vol->upcase = default_upcase; - vol->upcase_len = max; ntfs_nr_upcase_users++; mutex_unlock(&ntfs_lock); ntfs_debug("Volume specified $UpCase matches default. Using default."); -- 2.43.0