File avahi-CVE-2024-52616.patch of Package avahi.36694
From f8710bdc8b29ee1176fe3bfaeabebbda1b7a79f7 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Petr=20Men=C5=A1=C3=ADk?= <pemensik@redhat.com>
Date: Mon, 11 Nov 2024 00:56:09 +0100
Subject: [PATCH] Properly randomize query id of DNS packets
---
avahi-core/wide-area.c | 36 ++++++++++++++++++++++++++++--------
configure.ac | 3 ++-
2 files changed, 30 insertions(+), 9 deletions(-)
diff --git a/avahi-core/wide-area.c b/avahi-core/wide-area.c
index 971f5e7..00a1505 100644
--- a/avahi-core/wide-area.c
+++ b/avahi-core/wide-area.c
@@ -40,6 +40,13 @@
#include "addr-util.h"
#include "rr-util.h"
+#ifdef HAVE_SYS_RANDOM_H
+#include <sys/random.h>
+#endif
+#ifndef HAVE_GETRANDOM
+# define getrandom(d, len, flags) (-1)
+#endif
+
#define CACHE_ENTRIES_MAX 500
typedef struct AvahiWideAreaCacheEntry AvahiWideAreaCacheEntry;
@@ -84,8 +91,6 @@
int fd_ipv4, fd_ipv6;
AvahiWatch *watch_ipv4, *watch_ipv6;
- uint16_t next_id;
-
/* Cache */
AVAHI_LLIST_HEAD(AvahiWideAreaCacheEntry, cache);
AvahiHashmap *cache_by_key;
@@ -201,6 +206,25 @@
avahi_time_event_update(e, avahi_elapse_time(&tv, 1000, 0));
}
+static uint16_t get_random_uint16(void) {
+ uint16_t next_id;
+
+ if (getrandom(&next_id, sizeof(next_id), 0) == -1)
+ next_id = (uint16_t) rand();
+ return next_id;
+}
+
+static uint16_t avahi_wide_area_next_id(AvahiWideAreaLookupEngine *e) {
+ uint16_t next_id;
+
+ next_id = get_random_uint16();
+ while (find_lookup(e, next_id)) {
+ /* This ID is already used, get new. */
+ next_id = get_random_uint16();
+ }
+ return next_id;
+}
+
AvahiWideAreaLookup *avahi_wide_area_lookup_new(
AvahiWideAreaLookupEngine *e,
AvahiKey *key,
@@ -227,11 +251,7 @@
/* If more than 65K wide area quries are issued simultaneously,
* this will break. This should be limited by some higher level */
- for (;; e->next_id++)
- if (!find_lookup(e, e->next_id))
- break; /* This ID is not yet used. */
-
- l->id = e->next_id++;
+ l->id = avahi_wide_area_next_id(e);
/* We keep the packet around in case we need to repeat our query */
l->packet = avahi_dns_packet_new(0);
@@ -603,7 +623,6 @@
e->watch_ipv6 = s->poll_api->watch_new(e->server->poll_api, e->fd_ipv6, AVAHI_WATCH_IN, socket_event, e);
e->n_dns_servers = e->current_dns_server = 0;
- e->next_id = (uint16_t) rand();
/* Initialize cache */
AVAHI_LLIST_HEAD_INIT(AvahiWideAreaCacheEntry, e->cache);
diff --git a/configure.ac b/configure.ac
index a3211b8..31bce3d 100644
--- a/configure.ac
+++ b/configure.ac
@@ -366,7 +366,8 @@
# whether libc's malloc does too. (Same for realloc.)
#AC_FUNC_MALLOC
#AC_FUNC_REALLOC
-AC_CHECK_FUNCS([gethostname memchr memmove memset mkdir select socket strchr strcspn strdup strerror strrchr strspn strstr uname setresuid setreuid setresgid setregid strcasecmp gettimeofday putenv strncasecmp strlcpy gethostbyname seteuid setegid setproctitle getprogname])
+AC_CHECK_FUNCS([gethostname memchr memmove memset mkdir select socket strchr strcspn strdup strerror strrchr strspn strstr uname setresuid setreuid setresgid setregid strcasecmp gettimeofday putenv strncasecmp strlcpy gethostbyname seteuid setegid setproctitle getprogname getrandom])
+AC_CHECK_HEADERS([sys/random.h])
AC_FUNC_CHOWN
AC_FUNC_STAT