mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [PATCH] ntfs3: replace the extend_data member with a union data structure
@ 2026-10-13 12:38 Rong Zhang
  0 siblings, 0 replies; only message in thread
From: Rong Zhang @ 2026-10-13 12:38 UTC (permalink / raw)
  To: almaz.alexandrovich; +Cc: ntfs3, linux-kernel, Rong Zhang

Replace the extend_data member of struct NTFS_DUP_INFO with a union data
structure.

This patch makes the code more robust.

Fixes: 8df35e16a92c ("fs/ntfs3: fix symlinks cannot be handled correctly")
Signed-off-by: Rong Zhang <ulin0208@gmail.com>
---
 fs/ntfs3/dir.c     |  4 +++-
 fs/ntfs3/frecord.c |  6 +++---
 fs/ntfs3/inode.c   |  6 +++---
 fs/ntfs3/ntfs.h    | 10 +++++++++-
 fs/ntfs3/ntfs_fs.h |  2 +-
 fs/ntfs3/xattr.c   |  6 +++---
 6 files changed, 22 insertions(+), 12 deletions(-)

diff --git a/fs/ntfs3/dir.c b/fs/ntfs3/dir.c
index eb9152e9fa22..42222a82ca0f 100644
--- a/fs/ntfs3/dir.c
+++ b/fs/ntfs3/dir.c
@@ -377,7 +377,9 @@ static inline bool ntfs_dir_emit(struct ntfs_sb_info *sbi,
 	 * It does additional locks/reads just to get the type of name.
 	 * Should we use additional mount option to enable branch below?
 	 */
-	if (fname->dup.extend_data && ino != ni->mi.rno) {
+	if (((fname->dup.fa & FILE_ATTRIBUTE_REPARSE_POINT) ||
+	     fname->dup.ea.ea_size) &&
+	     ino != ni->mi.rno) {
 		struct inode *inode = ntfs_iget5(sbi->sb, &e->ref, NULL);
 		if (!IS_ERR_OR_NULL(inode)) {
 			dt_type = fs_umode_to_dtype(inode->i_mode);
diff --git a/fs/ntfs3/frecord.c b/fs/ntfs3/frecord.c
index bead01a953f3..066fe6aefcc4 100644
--- a/fs/ntfs3/frecord.c
+++ b/fs/ntfs3/frecord.c
@@ -3090,7 +3090,7 @@ static bool ni_update_parent(struct ntfs_inode *ni, struct NTFS_DUP_INFO *dup,
 		}
 	}
 
-	dup->extend_data = 0;
+	dup->rp.reparse = 0;
 
 	if (dup->fa & FILE_ATTRIBUTE_REPARSE_POINT) {
 		attr = ni_find_attr(ni, NULL, NULL, ATTR_REPARSE, NULL, 0, NULL,
@@ -3103,7 +3103,7 @@ static bool ni_update_parent(struct ntfs_inode *ni, struct NTFS_DUP_INFO *dup,
 					      sizeof(struct REPARSE_POINT));
 			/* If ATTR_REPARSE exists 'rp' can't be NULL. */
 			if (rp)
-				dup->extend_data = rp->ReparseTag;
+				dup->rp.reparse = rp->ReparseTag;
 		}
 	} else if (ni->ni_flags & NI_FLAG_EA) {
 		attr = ni_find_attr(ni, attr, &le, ATTR_EA_INFO, NULL, 0, NULL,
@@ -3114,7 +3114,7 @@ static bool ni_update_parent(struct ntfs_inode *ni, struct NTFS_DUP_INFO *dup,
 			info = resident_data_ex(attr, sizeof(struct EA_INFO));
 			/* If ATTR_EA_INFO exists 'info' can't be NULL. */
 			if (info)
-				dup->extend_data = info->size;
+				dup->ea.ea_size = info->size_pack;
 		}
 	}
 
diff --git a/fs/ntfs3/inode.c b/fs/ntfs3/inode.c
index 4ac26c80bd34..329650c87593 100644
--- a/fs/ntfs3/inode.c
+++ b/fs/ntfs3/inode.c
@@ -1594,7 +1594,7 @@ int ntfs_create_inode(struct mnt_idmap *idmap, struct inode *dir,
 		fname->dup.a_time = std5->cr_time;
 	fname->dup.alloc_size = fname->dup.data_size = 0;
 	fname->dup.fa = std5->fa;
-	fname->dup.extend_data = S_ISLNK(mode) ? IO_REPARSE_TAG_SYMLINK : 0;
+	fname->dup.rp.reparse =	S_ISLNK(mode) ? IO_REPARSE_TAG_SYMLINK : 0;
 
 	dsize = le16_to_cpu(new_de->key_size);
 	asize = ALIGN(SIZEOF_RESIDENT + dsize, 8);
@@ -1837,7 +1837,7 @@ int ntfs_create_inode(struct mnt_idmap *idmap, struct inode *dir,
 		 * The packed size of extended attribute is stored in direntry too.
 		 * 'fname' here points to inside new_de.
 		 */
-		err = ntfs_save_wsl_perm(inode, &fname->dup.extend_data);
+		err = ntfs_save_wsl_perm(inode, &fname->dup.ea.ea_size);
 		if (err)
 			goto out6;
 
@@ -1853,7 +1853,7 @@ int ntfs_create_inode(struct mnt_idmap *idmap, struct inode *dir,
 
 			fn = resident_data_ex(attr, SIZEOF_ATTRIBUTE_FILENAME);
 			if (fn)
-				fn->dup.extend_data = fname->dup.extend_data;
+				fn->dup.ea.ea_size = fname->dup.ea.ea_size;
 		}
 	}
 
diff --git a/fs/ntfs3/ntfs.h b/fs/ntfs3/ntfs.h
index 4589b16329c9..bcef7ae02065 100644
--- a/fs/ntfs3/ntfs.h
+++ b/fs/ntfs3/ntfs.h
@@ -566,7 +566,15 @@ struct NTFS_DUP_INFO {
 	__le64 alloc_size;	// 0x20: Data attribute allocated size, multiple of cluster size.
 	__le64 data_size;	// 0x28: Data attribute size <= Dataalloc_size.
 	enum FILE_ATTRIBUTE fa;	// 0x30: Standard DOS attributes & more.
-	__le32 extend_data;	// 0x34: Extended data.
+	union {
+		struct {
+			__le16 ea_size; // 0x34: Packed EAs.
+			__le16 reserved;
+		} ea;
+		struct {
+			__le32 reparse; // 0x34: Used by Reparse.
+		} rp;
+	};
 
 }; // 0x38
 
diff --git a/fs/ntfs3/ntfs_fs.h b/fs/ntfs3/ntfs_fs.h
index 5811d89d67b3..aa8be7b2379b 100644
--- a/fs/ntfs3/ntfs_fs.h
+++ b/fs/ntfs3/ntfs_fs.h
@@ -978,7 +978,7 @@ int ntfs_acl_chmod(struct mnt_idmap *idmap, struct dentry *dentry);
 ssize_t ntfs_listxattr(struct dentry *dentry, char *buffer, size_t size);
 extern const struct xattr_handler *const ntfs_xattr_handlers[];
 
-int ntfs_save_wsl_perm(struct inode *inode, __le32 *ea_size);
+int ntfs_save_wsl_perm(struct inode *inode, __le16 *ea_size);
 void ntfs_get_wsl_perm(struct inode *inode);
 
 /* globals from lznt.c */
diff --git a/fs/ntfs3/xattr.c b/fs/ntfs3/xattr.c
index 594ef6860b93..46d83427f66c 100644
--- a/fs/ntfs3/xattr.c
+++ b/fs/ntfs3/xattr.c
@@ -316,7 +316,7 @@ static int ntfs_get_ea(struct inode *inode, const char *name, size_t name_len,
 static noinline int ntfs_set_ea(struct inode *inode, const char *name,
 				size_t name_len, const void *value,
 				size_t val_size, int flags, bool locked,
-				__le32 *ea_size)
+				__le16 *ea_size)
 {
 	struct ntfs_inode *ni = ntfs_i(inode);
 	struct ntfs_sb_info *sbi = ni->mi.sbi;
@@ -525,7 +525,7 @@ static noinline int ntfs_set_ea(struct inode *inode, const char *name,
 	if (ea_info.size_pack != size_pack)
 		ni->ni_flags |= NI_FLAG_UPDATE_PARENT;
 	if (ea_size)
-		*ea_size = ea_info.size;
+		*ea_size = ea_info.size_pack;
 	mark_inode_dirty(&ni->vfs_inode);
 
 out:
@@ -987,7 +987,7 @@ static noinline int ntfs_setxattr(const struct xattr_handler *handler,
  *
  * save uid/gid/mode in xattr
  */
-int ntfs_save_wsl_perm(struct inode *inode, __le32 *ea_size)
+int ntfs_save_wsl_perm(struct inode *inode, __le16 *ea_size)
 {
 	int err;
 	__le32 value;
-- 
2.56.0


^ permalink raw reply	[flat|nested] only message in thread

only message in thread, other threads:[~2026-10-13 12:38 UTC | newest]

Thread overview: (only message) (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-10-13 12:38 [PATCH] ntfs3: replace the extend_data member with a union data structure Rong Zhang

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®