Linux v6.1-rc1-4-g6f7630b1b5bc
fortify: Capture __bos() results in const temp var
In lnet_peer_push_event() the memcpy triggers a WARN_ONCE
due to the flexible array at the end of
struct lnet_ping_info contained in struct lnet_ping_buffer
Use unsafe_memcpy() to avoid this false positive warning.
Lustre-change: https://review.whamcloud.com/49801
Lustre-commit:
a3cf8587b6fafdfed16fe0870efddcf6c0746c88
Test-Parameters: trivial
Signed-off-by: Shaun Tancheff <shaun.tancheff@hpe.com>
Change-Id: I4aa8f38678cd1522004d98b58a3f440d8a38589c
Signed-off-by: Stephane Thiell <sthiell@stanford.edu>
Reviewed-on: https://review.whamcloud.com/c/fs/lustre-release/+/50647
Tested-by: jenkins <devops@whamcloud.com>
Tested-by: Maloo <maloo@whamcloud.com>
Reviewed-by: Jian Yu <yujian@whamcloud.com>
Reviewed-by: Oleg Drokin <green@whamcloud.com>
#define INTERVAL_TREE_ROOT RB_ROOT
#endif /* HAVE_INTERVAL_TREE_CACHED */
+#ifndef unsafe_memcpy
+#define unsafe_memcpy(to, from, size, reason) memcpy((to), (from), (size))
+#endif
+
+#define FLEXIBLE_OBJECT \
+ "Struct contains a flexible member, the size of object is checked" \
+ "and can be safely copied in a single memcpy()"
+
#endif /* _LIBCFS_LIBCFS_H_ */
__u32 pi_features;
lnet_pid_t pi_pid;
__u32 pi_nnis;
- struct lnet_ni_status pi_ni[0];
+ struct lnet_ni_status pi_ni[];
} __attribute__((packed));
#define LNET_PING_INFO_SIZE(NNIDS) \
BUILD_BUG_ON((int)offsetof(struct lnet_ping_info, pi_nnis) != 12);
BUILD_BUG_ON((int)sizeof(((struct lnet_ping_info *)0)->pi_nnis) != 4);
BUILD_BUG_ON((int)offsetof(struct lnet_ping_info, pi_ni) != 16);
- BUILD_BUG_ON((int)sizeof(((struct lnet_ping_info *)0)->pi_ni) != 0);
+ BUILD_BUG_ON(offsetof(struct lnet_ping_info, pi_ni) != sizeof(struct lnet_ping_info));
/* Acceptor connection request */
BUILD_BUG_ON(LNET_PROTO_ACCEPTOR_VERSION != 1);
}
/* Success */
- memcpy(&lp->lp_data->pb_info, &pbuf->pb_info,
- LNET_PING_INFO_SIZE(pbuf->pb_info.pi_nnis));
+ unsafe_memcpy(&lp->lp_data->pb_info, &pbuf->pb_info,
+ LNET_PING_INFO_SIZE(pbuf->pb_info.pi_nnis), FLEXIBLE_OBJECT);
lp->lp_state |= LNET_PEER_DATA_PRESENT;
CDEBUG(D_NET, "Received Push %s %u\n",
libcfs_nidstr(&lp->lp_primary_nid),
#define STRINGIFY(a) #a
+#define CHECK_BUILD_TEST(a) \
+ printf(" BUILD_BUG_ON("#a");\n")
+
#define CHECK_DEFINE(a) \
do { \
printf (" BUILD_BUG_ON("#a" != "STRINGIFY(a)");\n"); \
CHECK_VALUE((int)sizeof(((s *)0)->m)); \
} while (0)
+#define CHECK_MEMBER_IS_FLEXIBLE(s, m) \
+do { \
+ CHECK_MEMBER_OFFSET(s, m); \
+ CHECK_BUILD_TEST(offsetof(struct s, m) != sizeof(struct s)); \
+} while (0)
+
#define CHECK_MEMBER(s,m) \
do { \
CHECK_MEMBER_OFFSET(s, m); \
CHECK_MEMBER(struct lnet_ping_info, pi_features);
CHECK_MEMBER(struct lnet_ping_info, pi_pid);
CHECK_MEMBER(struct lnet_ping_info, pi_nnis);
- CHECK_MEMBER(struct lnet_ping_info, pi_ni);
+ CHECK_MEMBER_IS_FLEXIBLE(struct lnet_ping_info, pi_ni);
}
void
CHECK_VALUE((int)sizeof(((s *)0)->m)); \
} while(0)
+#define CHECK_MEMBER_IS_FLEXIBLE(s, m) \
+do { \
+ CHECK_MEMBER_OFFSET(s, m); \
+ CHECK_BUILD_TEST(offsetof(struct s, m) != sizeof(struct s)); \
+} while (0)
+
#define CHECK_MEMBER(s, m) \
do { \
CHECK_MEMBER_OFFSET(s, m); \
CHECK_MEMBER(fiemap, fm_mapped_extents);
CHECK_MEMBER(fiemap, fm_extent_count);
CHECK_MEMBER(fiemap, fm_reserved);
- CHECK_MEMBER(fiemap, fm_extents);
+ CHECK_MEMBER_IS_FLEXIBLE(fiemap, fm_extents);
CHECK_CDEFINE(FIEMAP_FLAG_SYNC);
CHECK_CDEFINE(FIEMAP_FLAG_XATTR);