From 853e132a41e6ee4ef7bac589823b30fafb228db0 Mon Sep 17 00:00:00 2001 From: Eric Mei Date: Mon, 8 Feb 2010 16:57:43 -0700 Subject: [PATCH] b=21278 fix linkea definition and unaligned access. link_ea_entry->lee_reclen should be defined as unsigned char instead of char which might get sign expansion during conversion. fix unaligned memory access to link_ea_entry->lee_parent_fid. i=nathan i=rahul --- lustre/include/lustre/lustre_idl.h | 5 ++--- lustre/mdd/mdd_dir.c | 11 +++++++---- lustre/ptlrpc/wiretest.c | 8 ++++---- lustre/utils/wiretest.c | 8 ++++---- 4 files changed, 17 insertions(+), 15 deletions(-) diff --git a/lustre/include/lustre/lustre_idl.h b/lustre/include/lustre/lustre_idl.h index 453d018..9e0f9e7 100644 --- a/lustre/include/lustre/lustre_idl.h +++ b/lustre/include/lustre/lustre_idl.h @@ -2594,10 +2594,9 @@ struct link_ea_header { * Stored in this crazy struct for maximum packing and endian-neutrality */ struct link_ea_entry { - struct lu_fid lee_parent_fid; /** __u16 stored big-endian, unaligned */ - char lee_reclen[2]; - __u16 lee_padding; + unsigned char lee_reclen[2]; + unsigned char lee_parent_fid[sizeof(struct lu_fid)]; char lee_name[0]; }__attribute__((packed)); diff --git a/lustre/mdd/mdd_dir.c b/lustre/mdd/mdd_dir.c index 6045cf3..d0307f2 100644 --- a/lustre/mdd/mdd_dir.c +++ b/lustre/mdd/mdd_dir.c @@ -2313,10 +2313,12 @@ struct lu_buf *mdd_links_get(const struct lu_env *env, static int mdd_lee_pack(struct link_ea_entry *lee, const struct lu_name *lname, const struct lu_fid *pfid) { - int reclen; + struct lu_fid tmpfid; + int reclen; - fid_cpu_to_be(&lee->lee_parent_fid, pfid); - strncpy(lee->lee_name, lname->ln_name, lname->ln_namelen); + fid_cpu_to_be(&tmpfid, pfid); + memcpy(&lee->lee_parent_fid, &tmpfid, sizeof(tmpfid)); + memcpy(lee->lee_name, lname->ln_name, lname->ln_namelen); reclen = sizeof(struct link_ea_entry) + lname->ln_namelen; lee->lee_reclen[0] = (reclen >> 8) & 0xff; @@ -2328,7 +2330,8 @@ void mdd_lee_unpack(const struct link_ea_entry *lee, int *reclen, struct lu_name *lname, struct lu_fid *pfid) { *reclen = (lee->lee_reclen[0] << 8) | lee->lee_reclen[1]; - fid_be_to_cpu(pfid, &lee->lee_parent_fid); + memcpy(pfid, &lee->lee_parent_fid, sizeof(*pfid)); + fid_be_to_cpu(pfid, pfid); lname->ln_name = lee->lee_name; lname->ln_namelen = *reclen - sizeof(struct link_ea_entry); } diff --git a/lustre/ptlrpc/wiretest.c b/lustre/ptlrpc/wiretest.c index 286b4e6..d186f71 100644 --- a/lustre/ptlrpc/wiretest.c +++ b/lustre/ptlrpc/wiretest.c @@ -2669,17 +2669,17 @@ void lustre_assert_wire_constants(void) (long long)(int)sizeof(((struct link_ea_header *)0)->padding2)); /* Checks for struct link_ea_entry */ - LASSERTF((int)sizeof(struct link_ea_entry) == 20, " found %lld\n", + LASSERTF((int)sizeof(struct link_ea_entry) == 18, " found %lld\n", (long long)(int)sizeof(struct link_ea_entry)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_reclen) == 16, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_reclen) == 0, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_reclen)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_reclen) == 2, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_reclen)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_parent_fid) == 0, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_parent_fid) == 2, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_parent_fid)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_parent_fid) == 16, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_parent_fid)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_name) == 20, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_name) == 18, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_name)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_name) == 0, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_name)); diff --git a/lustre/utils/wiretest.c b/lustre/utils/wiretest.c index 8644e27..ada400e 100644 --- a/lustre/utils/wiretest.c +++ b/lustre/utils/wiretest.c @@ -2666,17 +2666,17 @@ void lustre_assert_wire_constants(void) (long long)(int)sizeof(((struct link_ea_header *)0)->padding2)); /* Checks for struct link_ea_entry */ - LASSERTF((int)sizeof(struct link_ea_entry) == 20, " found %lld\n", + LASSERTF((int)sizeof(struct link_ea_entry) == 18, " found %lld\n", (long long)(int)sizeof(struct link_ea_entry)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_reclen) == 16, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_reclen) == 0, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_reclen)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_reclen) == 2, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_reclen)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_parent_fid) == 0, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_parent_fid) == 2, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_parent_fid)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_parent_fid) == 16, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_parent_fid)); - LASSERTF((int)offsetof(struct link_ea_entry, lee_name) == 20, " found %lld\n", + LASSERTF((int)offsetof(struct link_ea_entry, lee_name) == 18, " found %lld\n", (long long)(int)offsetof(struct link_ea_entry, lee_name)); LASSERTF((int)sizeof(((struct link_ea_entry *)0)->lee_name) == 0, " found %lld\n", (long long)(int)sizeof(((struct link_ea_entry *)0)->lee_name)); -- 1.8.3.1