diff --git a/SOURCES/0001-headers-Be-more-robust-against-invalid-input-when-pa.patch b/SOURCES/0001-headers-Be-more-robust-against-invalid-input-when-pa.patch new file mode 100644 index 0000000..daa2730 --- /dev/null +++ b/SOURCES/0001-headers-Be-more-robust-against-invalid-input-when-pa.patch @@ -0,0 +1,121 @@ +From bbeb7d59f98d0073291ca4a7ee9ce1a946842734 Mon Sep 17 00:00:00 2001 +From: Patrick Griffis +Date: Tue, 27 Aug 2024 13:53:26 -0500 +Subject: [PATCH] headers: Be more robust against invalid input when parsing + params + +If you pass invalid input to a function such as soup_header_parse_param_list_strict() +it can cause an overflow if it decodes the input to UTF-8. + +This should never happen with valid UTF-8 input which libsoup's client API +ensures, however it's server API does not currently. +--- + libsoup/soup-headers.c | 46 +++++++++++++++++++++--------------------- + 1 file changed, 23 insertions(+), 23 deletions(-) + +diff --git a/libsoup/soup-headers.c b/libsoup/soup-headers.c +index 271d2a63..8657483f 100644 +--- a/libsoup/soup-headers.c ++++ b/libsoup/soup-headers.c +@@ -650,8 +650,9 @@ soup_header_contains (const char *header, const char *token) + } + + static void +-decode_quoted_string (char *quoted_string) ++decode_quoted_string_inplace (GString *quoted_gstring) + { ++ char *quoted_string = quoted_gstring->str; + char *src, *dst; + + src = quoted_string + 1; +@@ -665,10 +666,11 @@ decode_quoted_string (char *quoted_string) + } + + static gboolean +-decode_rfc5987 (char *encoded_string) ++decode_rfc5987_inplace (GString *encoded_gstring) + { + char *q, *decoded; + gboolean iso_8859_1 = FALSE; ++ const char *encoded_string = encoded_gstring->str; + + q = strchr (encoded_string, '\''); + if (!q) +@@ -697,14 +699,7 @@ decode_rfc5987 (char *encoded_string) + decoded = utf8; + } + +- /* If encoded_string was UTF-8, then each 3-character %-escape +- * will be converted to a single byte, and so decoded is +- * shorter than encoded_string. If encoded_string was +- * iso-8859-1, then each 3-character %-escape will be +- * converted into at most 2 bytes in UTF-8, and so it's still +- * shorter. +- */ +- strcpy (encoded_string, decoded); ++ g_string_assign (encoded_gstring, decoded); + g_free (decoded); + return TRUE; + } +@@ -714,15 +709,17 @@ parse_param_list (const char *header, char delim) + { + GHashTable *params; + GSList *list, *iter; +- char *item, *eq, *name_end, *value; +- gboolean override; + + params = g_hash_table_new_full (soup_str_case_hash, + soup_str_case_equal, +- g_free, NULL); ++ g_free, g_free); + + list = parse_list (header, delim); + for (iter = list; iter; iter = iter->next) { ++ char *item, *eq, *name_end; ++ gboolean override, duplicated; ++ GString *parsed_value = NULL; ++ + item = iter->data; + override = FALSE; + +@@ -737,24 +734,27 @@ parse_param_list (const char *header, char delim) + + *name_end = '\0'; + +- value = (char *)skip_lws (eq + 1); ++ parsed_value = g_string_new ((char *)skip_lws (eq + 1)); + + if (name_end[-1] == '*' && name_end > item + 1) { + name_end[-1] = '\0'; +- if (!decode_rfc5987 (value)) { ++ if (!decode_rfc5987_inplace (parsed_value)) { ++ g_string_free (parsed_value, TRUE); + g_free (item); + continue; + } + override = TRUE; +- } else if (*value == '"') +- decode_quoted_string (value); +- } else +- value = NULL; +- +- if (override || !g_hash_table_lookup (params, item)) +- g_hash_table_replace (params, item, value); +- else ++ } else if (parsed_value->str[0] == '"') ++ decode_quoted_string_inplace (parsed_value); ++ } ++ ++ if (override || !g_hash_table_lookup (params, item)) { ++ g_hash_table_replace (params, item, parsed_value ? g_string_free (parsed_value, FALSE) : NULL); ++ } else { ++ if (parsed_value) ++ g_string_free (parsed_value, TRUE); + g_free (item); ++ } + } + + g_slist_free (list); +-- +2.48.1 + diff --git a/SPECS/libsoup.spec b/SPECS/libsoup.spec index 540880d..4048110 100644 --- a/SPECS/libsoup.spec +++ b/SPECS/libsoup.spec @@ -2,7 +2,7 @@ Name: libsoup Version: 2.62.3 -Release: 6%{?dist} +Release: 7%{?dist} Summary: Soup, an HTTP library implementation License: LGPLv2 @@ -16,6 +16,7 @@ Patch0004: 0004-ntlmv2.patch Patch0005: 0005-WebSockets-do-not-start-the-input-source-when-IO-is-closing.patch Patch0006: 0001-headers-Strictly-don-t-allow-NUL-bytes.patch Patch0007: 0001-websocket-process-the-frame-as-soon-as-we-read-data.patch +Patch0008: 0001-headers-Be-more-robust-against-invalid-input-when-pa.patch BuildRequires: chrpath BuildRequires: glib2-devel >= %{glib2_version} @@ -90,9 +91,13 @@ chrpath --delete $RPM_BUILD_ROOT%{_libdir}/*.so %{_datadir}/vala/vapi/libsoup-2.4.vapi %changelog +* Tue Jan 28 2025 Michael Catanzaro - 2.62.3-7 +- Backport upstream patch for CVE-2024-52531 - buffer overflow via UTF-8 conversion in soup_header_parse_param_list_strict + Resolves: RHEL-76376 + * Tue Nov 12 2024 Tomas Popela - 2.62.3-6 - Backport upstream patch for CVE-2024-52530 - HTTP request smuggling via stripping null bytes from the ends of header names -- Backport upstream patch for CVE-2024-52530 - infinite loop while reading websocket data +- Backport upstream patch for CVE-2024-52532 - infinite loop while reading websocket data - Resolves: RHEL-67076 - Resolves: RHEL-67067