fix CVE-2025-25186
(cherry picked from commit 9d1564fe1e9cd5db7988e1bd4a6a902a930e16b8)
This commit is contained in:
parent
903b11a397
commit
7c15f8745c
123
backport-CVE-2025-25186.patch
Normal file
123
backport-CVE-2025-25186.patch
Normal file
@ -0,0 +1,123 @@
|
|||||||
|
From 0dbb8eb72aa78b7ed0b01533388e69722d16b821 Mon Sep 17 00:00:00 2001
|
||||||
|
From: nick evans <nick@rubinick.dev>
|
||||||
|
Date: Wed, 8 Jan 2025 22:06:47 -0500
|
||||||
|
Subject: [PATCH 3/5] =?UTF-8?q?=F0=9F=94=92=20Prevent=20runaway=20memory?=
|
||||||
|
=?UTF-8?q?=20use=20when=20parsing=20uid-set?=
|
||||||
|
MIME-Version: 1.0
|
||||||
|
Content-Type: text/plain; charset=UTF-8
|
||||||
|
Content-Transfer-Encoding: 8bit
|
||||||
|
|
||||||
|
Reference:https://github.com/ruby/net-imap/commit/0dbb8eb72aa78b7ed0b01533388e69722d16b821
|
||||||
|
Conflict:not change test, the test/net/imap/ directory doesn't exist.
|
||||||
|
|
||||||
|
Problem
|
||||||
|
=========
|
||||||
|
|
||||||
|
The UID sets in UIDPlusData are stored as arrays of UIDs. In common
|
||||||
|
scenarios, copying between one and a few hundred emails at a time, this
|
||||||
|
is barely noticable. But the memory use expands _exponentially_.
|
||||||
|
|
||||||
|
This should not be an issue for _trusted_ servers, and (I assume)
|
||||||
|
compromised servers will be more interested in evading detection and
|
||||||
|
stealing your credentials and your email than in causing client Denial
|
||||||
|
of Service. Nevertheless, this is a very simple DoS attack against
|
||||||
|
clients connecting to untrusted servers (for example, a service that
|
||||||
|
connects to user-specified servers).
|
||||||
|
|
||||||
|
For example, assuming a 64-bit architecture, considering only the data
|
||||||
|
in the two arrays, assuming the arrays' internal capacity is no more
|
||||||
|
than needed, and ignoring the fixed cost of the response structs:
|
||||||
|
* 32 bytes expands to ~160KB (about 5000 times more):
|
||||||
|
`"* OK [COPYUID 1 1:9999 1:9999]\r\n"`
|
||||||
|
* 40 bytes expands to ~1.6GB (about 50 million times more):
|
||||||
|
`"* OK [COPYUID 1 1:99999999 1:99999999]\r\n"`
|
||||||
|
* In the worst scenario (uint32 max), 44 bytes expands to 64GiB in
|
||||||
|
memory, using over 1.5 billion times more to store than to send:
|
||||||
|
`"* OK [COPYUID 1 1:4294967295 1:4294967295]\r\n"`
|
||||||
|
|
||||||
|
Preferred fix
|
||||||
|
===============
|
||||||
|
|
||||||
|
The preferred fix is to store `uid-set` as a SequenceSet, not an array.
|
||||||
|
Unfortunately, this is not fully backwards compatible. For v0.4 and
|
||||||
|
v0.5, use `Config#parser_use_deprecated_uidplus_data` to false to use
|
||||||
|
AppendUIDData and CopyUIDData instead of UIDPlusData. Unless you are
|
||||||
|
_using_ UIDPLUS, this is completely safe. v0.6 will drop UIDPlusData.
|
||||||
|
|
||||||
|
Workaround
|
||||||
|
============
|
||||||
|
|
||||||
|
The simplest _partial_ fix (preserving full backward compatibility) is
|
||||||
|
to raise an error when the number of UIDs goes over some threshold, and
|
||||||
|
continue using arrays inside UIDPlusData.
|
||||||
|
|
||||||
|
For v0.3 (this commit) the maximum count is hard-coded to 10,000. This
|
||||||
|
is high enough that it should almost never be triggered by normal usage,
|
||||||
|
and low enough to be a less extreme problem. For v0.4 and v0.5, the
|
||||||
|
maximum array size is configurable, with a much lower default: 1000 for
|
||||||
|
v0.4 and 100 for v0.5. These are low enough that they are _unlikely_ to
|
||||||
|
cause a problem, but v0.4 and v0.5 can also use the newer AppendUIDData
|
||||||
|
and CopyUIDData classes.
|
||||||
|
|
||||||
|
However, because unhandled responses are stored on the `#responses`
|
||||||
|
hash, this can still be a problem. A malicious server could repeatedly
|
||||||
|
use 160Kb of client memory by sending only 32 bytes in a loop. To fully
|
||||||
|
solve this problem, a response handler must be added to prune excessive
|
||||||
|
APPENDUID/COPYUID responses as they are received.
|
||||||
|
|
||||||
|
Because unhandled responses have always been retained, managing
|
||||||
|
unhandled responses is already documented as necessary for long-lived
|
||||||
|
connections.
|
||||||
|
---
|
||||||
|
.../lib/net/imap/response_parser.rb | 26 ++++++++++++++++---
|
||||||
|
1 file changed, 23 insertions(+), 3 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/.bundle/gems/net-imap-0.3.4/lib/net/imap/response_parser.rb b/.bundle/gems/net-imap-0.3.4/lib/net/imap/response_parser.rb
|
||||||
|
index be1a849..0341356 100644
|
||||||
|
--- a/.bundle/gems/net-imap-0.3.4/lib/net/imap/response_parser.rb
|
||||||
|
+++ b/.bundle/gems/net-imap-0.3.4/lib/net/imap/response_parser.rb
|
||||||
|
@@ -7,6 +7,8 @@ module Net
|
||||||
|
|
||||||
|
# Parses an \IMAP server response.
|
||||||
|
class ResponseParser
|
||||||
|
+ MAX_UID_SET_SIZE = 10_000
|
||||||
|
+
|
||||||
|
# :call-seq: Net::IMAP::ResponseParser.new -> Net::IMAP::ResponseParser
|
||||||
|
def initialize
|
||||||
|
@str = nil
|
||||||
|
@@ -1379,11 +1381,29 @@ module Net
|
||||||
|
case token.symbol
|
||||||
|
when T_NUMBER then [Integer(token.value)]
|
||||||
|
when T_ATOM
|
||||||
|
- token.value.split(",").flat_map {|range|
|
||||||
|
- range = range.split(":").map {|uniqueid| Integer(uniqueid) }
|
||||||
|
- range.size == 1 ? range : Range.new(range.min, range.max).to_a
|
||||||
|
+ entries = uid_set__ranges(token.value)
|
||||||
|
+ if (count = entries.sum(&:count)) > MAX_UID_SET_SIZE
|
||||||
|
+ parse_error("uid-set is too large: %d > 10k", count)
|
||||||
|
+ end
|
||||||
|
+ entries.flat_map(&:to_a)
|
||||||
|
+ end
|
||||||
|
+ end
|
||||||
|
+
|
||||||
|
+ # returns an array of ranges
|
||||||
|
+ def uid_set__ranges(uidset)
|
||||||
|
+ entries = []
|
||||||
|
+ uidset.split(",") do |entry|
|
||||||
|
+ uids = entry.split(":", 2).map {|uid|
|
||||||
|
+ unless uid =~ /\A[1-9][0-9]*\z/
|
||||||
|
+ parse_error("invalid uid-set uid: %p", uid)
|
||||||
|
+ end
|
||||||
|
+ uid = Integer(uid)
|
||||||
|
+ NumValidator.ensure_nz_number(uid)
|
||||||
|
+ uid
|
||||||
|
}
|
||||||
|
+ entries << Range.new(*uids.minmax)
|
||||||
|
end
|
||||||
|
+ entries
|
||||||
|
end
|
||||||
|
|
||||||
|
def nil_atom
|
||||||
|
--
|
||||||
|
2.27.0
|
||||||
|
|
||||||
@ -33,7 +33,7 @@
|
|||||||
|
|
||||||
Name: ruby
|
Name: ruby
|
||||||
Version: %{ruby_version}
|
Version: %{ruby_version}
|
||||||
Release: 147
|
Release: 148
|
||||||
Summary: Object-oriented scripting language interpreter
|
Summary: Object-oriented scripting language interpreter
|
||||||
License: (Ruby or BSD) and Public Domain and MIT and CC0 and zlib and UCD
|
License: (Ruby or BSD) and Public Domain and MIT and CC0 and zlib and UCD
|
||||||
URL: https://www.ruby-lang.org/en/
|
URL: https://www.ruby-lang.org/en/
|
||||||
@ -103,6 +103,7 @@ Patch6026: backport-CVE-2024-39908-CVE-2024-41123-upgrade-lib-rexml-to-3.3.3.pat
|
|||||||
Patch6027: backport-CVE-2024-43398-upgrade-lib-rexml-to-3.3.6.patch
|
Patch6027: backport-CVE-2024-43398-upgrade-lib-rexml-to-3.3.6.patch
|
||||||
Patch6028: backport-CVE-2024-47220.patch
|
Patch6028: backport-CVE-2024-47220.patch
|
||||||
Patch6029: backport-CVE-2024-49761.patch
|
Patch6029: backport-CVE-2024-49761.patch
|
||||||
|
Patch6030: backport-CVE-2025-25186.patch
|
||||||
|
|
||||||
Provides: %{name}-libs = %{version}-%{release}
|
Provides: %{name}-libs = %{version}-%{release}
|
||||||
Obsoletes: %{name}-libs < %{version}-%{release}
|
Obsoletes: %{name}-libs < %{version}-%{release}
|
||||||
@ -888,6 +889,9 @@ make runruby TESTRUN_SCRIPT=%{SOURCE13}
|
|||||||
%{gem_dir}/specifications/matrix-%{matrix_version}.gemspec
|
%{gem_dir}/specifications/matrix-%{matrix_version}.gemspec
|
||||||
|
|
||||||
%changelog
|
%changelog
|
||||||
|
* Sat Feb 22 2025 shixuantong <shixuantong1@huawei.com> - 3.2.2-148
|
||||||
|
- fix CVE-2025-25186
|
||||||
|
|
||||||
* Tue Oct 29 2024 shixuantong <shixuantong1@huawei.com> - 3.2.2-147
|
* Tue Oct 29 2024 shixuantong <shixuantong1@huawei.com> - 3.2.2-147
|
||||||
- fix CVE-2024-49761
|
- fix CVE-2024-49761
|
||||||
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user