git: 10f2a38769c7 - main - netlink: fix OOB write when creating attribute bitmask.
- Go to: [ bottom of page ] [ top of archives ] [ this month ]
Date: Sat, 21 Jan 2023 18:06:30 UTC
The branch main has been updated by melifaro:
URL: https://cgit.FreeBSD.org/src/commit/?id=10f2a38769c7b2fa210a3ea077d3185448479013
commit 10f2a38769c7b2fa210a3ea077d3185448479013
Author: Alexander V. Chernikov <melifaro@FreeBSD.org>
AuthorDate: 2023-01-21 18:03:47 +0000
Commit: Alexander V. Chernikov <melifaro@FreeBSD.org>
CommitDate: 2023-01-21 18:03:47 +0000
netlink: fix OOB write when creating attribute bitmask.
Fix wrong arithmetics by moving to the standard bitset(9) functions.
Reported by: markj, KASAN
---
sys/netlink/netlink_message_parser.c | 16 +++++++++++++---
sys/netlink/netlink_message_parser.h | 16 ++++++----------
2 files changed, 19 insertions(+), 13 deletions(-)
diff --git a/sys/netlink/netlink_message_parser.c b/sys/netlink/netlink_message_parser.c
index 451d9d497491..dc0c38712613 100644
--- a/sys/netlink/netlink_message_parser.c
+++ b/sys/netlink/netlink_message_parser.c
@@ -152,17 +152,27 @@ nl_get_attrs_bmask_raw(struct nlattr *nla_head, int len, struct nlattr_bmask *bm
{
struct nlattr *nla = NULL;
- bzero(bm->mask, sizeof(bm->mask));
+ BIT_ZERO(NL_ATTR_BMASK_SIZE, bm);
NLA_FOREACH(nla, nla_head, len) {
if (nla->nla_len < sizeof(struct nlattr))
return;
int nla_type = nla->nla_type & NLA_TYPE_MASK;
- if (nla_type <= sizeof(bm->mask) * 8)
- bm->mask[nla_type / 8] |= 1 << (nla_type % 8);
+ if (nla_type < NL_ATTR_BMASK_SIZE)
+ BIT_SET(NL_ATTR_BMASK_SIZE, nla_type, bm);
+ else
+ NL_LOG(LOG_DEBUG2, "Skipping type %d in the mask: too short",
+ nla_type);
}
}
+bool
+nl_has_attr(const struct nlattr_bmask *bm, unsigned int nla_type)
+{
+ MPASS(nla_type < NL_ATTR_BMASK_SIZE);
+
+ return (BIT_ISSET(NL_ATTR_BMASK_SIZE, nla_type, bm));
+}
int
nlattr_get_flag(struct nlattr *nla, struct nl_pstate *npt, const void *arg, void *target)
diff --git a/sys/netlink/netlink_message_parser.h b/sys/netlink/netlink_message_parser.h
index 3f64c1967f09..94f0ca5260d7 100644
--- a/sys/netlink/netlink_message_parser.h
+++ b/sys/netlink/netlink_message_parser.h
@@ -29,6 +29,9 @@
#define _NETLINK_NETLINK_MESSAGE_PARSER_H_
#ifdef _KERNEL
+
+#include <sys/bitset.h>
+
/*
* It is not meant to be included directly
*/
@@ -152,18 +155,11 @@ static const struct nlhdr_parser _name = { \
.np_size = NL_ARRAY_LEN(_np), \
}
-struct nlattr_bmask {
- uint64_t mask[2];
-};
-
-static inline bool
-nl_has_attr(const struct nlattr_bmask *bm, unsigned int attr_type)
-{
- MPASS(attr_type < sizeof(bm->mask) * 8);
+#define NL_ATTR_BMASK_SIZE 128
+BITSET_DEFINE(nlattr_bmask, NL_ATTR_BMASK_SIZE);
- return ((bm->mask[attr_type / 8] & (1 << (attr_type % 8))));
-}
void nl_get_attrs_bmask_raw(struct nlattr *nla_head, int len, struct nlattr_bmask *bm);
+bool nl_has_attr(const struct nlattr_bmask *bm, unsigned int nla_type);
int nl_parse_attrs_raw(struct nlattr *nla_head, int len, const struct nlattr_parser *ps,
int pslen, struct nl_pstate *npt, void *target);