Blame SOURCES/0009-curl-7.76.1-CVE-2021-22947.patch

d889a8
From a1ec463c8207bde97b3575d12e396e999a55a8d0 Mon Sep 17 00:00:00 2001
d889a8
From: Patrick Monnerat <patrick@monnerat.net>
d889a8
Date: Tue, 7 Sep 2021 13:26:42 +0200
d889a8
Subject: [PATCH] ftp,imap,pop3,smtp: reject STARTTLS server response
d889a8
 pipelining
d889a8
d889a8
If a server pipelines future responses within the STARTTLS response, the
d889a8
former are preserved in the pingpong cache across TLS negotiation and
d889a8
used as responses to the encrypted commands.
d889a8
d889a8
This fix detects pipelined STARTTLS responses and rejects them with an
d889a8
error.
d889a8
d889a8
CVE-2021-22947
d889a8
d889a8
Bug: https://curl.se/docs/CVE-2021-22947.html
d889a8
d889a8
Upstream-commit: 8ef147c43646e91fdaad5d0e7b60351f842e5c68
d889a8
Signed-off-by: Kamil Dudka <kdudka@redhat.com>
d889a8
---
d889a8
 lib/ftp.c               |  3 +++
d889a8
 lib/imap.c              |  4 +++
d889a8
 lib/pop3.c              |  4 +++
d889a8
 lib/smtp.c              |  4 +++
d889a8
 tests/data/Makefile.inc |  2 +-
d889a8
 tests/data/test980      | 52 ++++++++++++++++++++++++++++++++++++
d889a8
 tests/data/test981      | 59 +++++++++++++++++++++++++++++++++++++++++
d889a8
 tests/data/test982      | 57 +++++++++++++++++++++++++++++++++++++++
d889a8
 tests/data/test983      | 52 ++++++++++++++++++++++++++++++++++++
d889a8
 9 files changed, 236 insertions(+), 1 deletion(-)
d889a8
 create mode 100644 tests/data/test980
d889a8
 create mode 100644 tests/data/test981
d889a8
 create mode 100644 tests/data/test982
d889a8
 create mode 100644 tests/data/test983
d889a8
d889a8
diff --git a/lib/ftp.c b/lib/ftp.c
d889a8
index 71f998e..e920138 100644
d889a8
--- a/lib/ftp.c
d889a8
+++ b/lib/ftp.c
d889a8
@@ -2740,6 +2740,9 @@ static CURLcode ftp_statemachine(struct Curl_easy *data,
d889a8
     case FTP_AUTH:
d889a8
       /* we have gotten the response to a previous AUTH command */
d889a8
 
d889a8
+      if(pp->cache_size)
d889a8
+        return CURLE_WEIRD_SERVER_REPLY; /* Forbid pipelining in response. */
d889a8
+
d889a8
       /* RFC2228 (page 5) says:
d889a8
        *
d889a8
        * If the server is willing to accept the named security mechanism,
d889a8
diff --git a/lib/imap.c b/lib/imap.c
d889a8
index feb7445..09bc5d6 100644
d889a8
--- a/lib/imap.c
d889a8
+++ b/lib/imap.c
d889a8
@@ -964,6 +964,10 @@ static CURLcode imap_state_starttls_resp(struct Curl_easy *data,
d889a8
 
d889a8
   (void)instate; /* no use for this yet */
d889a8
 
d889a8
+  /* Pipelining in response is forbidden. */
d889a8
+  if(data->conn->proto.imapc.pp.cache_size)
d889a8
+    return CURLE_WEIRD_SERVER_REPLY;
d889a8
+
d889a8
   if(imapcode != IMAP_RESP_OK) {
d889a8
     if(data->set.use_ssl != CURLUSESSL_TRY) {
d889a8
       failf(data, "STARTTLS denied");
d889a8
diff --git a/lib/pop3.c b/lib/pop3.c
d889a8
index 7698d1c..dccfced 100644
d889a8
--- a/lib/pop3.c
d889a8
+++ b/lib/pop3.c
d889a8
@@ -771,6 +771,10 @@ static CURLcode pop3_state_starttls_resp(struct Curl_easy *data,
d889a8
   CURLcode result = CURLE_OK;
d889a8
   (void)instate; /* no use for this yet */
d889a8
 
d889a8
+  /* Pipelining in response is forbidden. */
d889a8
+  if(data->conn->proto.pop3c.pp.cache_size)
d889a8
+    return CURLE_WEIRD_SERVER_REPLY;
d889a8
+
d889a8
   if(pop3code != '+') {
d889a8
     if(data->set.use_ssl != CURLUSESSL_TRY) {
d889a8
       failf(data, "STARTTLS denied");
d889a8
diff --git a/lib/smtp.c b/lib/smtp.c
d889a8
index 1defb25..1f89777 100644
d889a8
--- a/lib/smtp.c
d889a8
+++ b/lib/smtp.c
d889a8
@@ -834,6 +834,10 @@ static CURLcode smtp_state_starttls_resp(struct Curl_easy *data,
d889a8
   CURLcode result = CURLE_OK;
d889a8
   (void)instate; /* no use for this yet */
d889a8
 
d889a8
+  /* Pipelining in response is forbidden. */
d889a8
+  if(data->conn->proto.smtpc.pp.cache_size)
d889a8
+    return CURLE_WEIRD_SERVER_REPLY;
d889a8
+
d889a8
   if(smtpcode != 220) {
d889a8
     if(data->set.use_ssl != CURLUSESSL_TRY) {
d889a8
       failf(data, "STARTTLS denied, code %d", smtpcode);
d889a8
diff --git a/tests/data/Makefile.inc b/tests/data/Makefile.inc
d889a8
index 163ce59..42b0569 100644
d889a8
--- a/tests/data/Makefile.inc
d889a8
+++ b/tests/data/Makefile.inc
d889a8
@@ -117,7 +117,7 @@ test945 test946 test947 test948 test949 test950 test951 test952 test953 \
d889a8
 test954 test955 test956 test957 test958 test959 test960 test961 test962 \
d889a8
 test963 test964 test965 test966 test967 test968 test969 test970 test971 \
d889a8
 \
d889a8
-test984 test985 test986 \
d889a8
+test980 test981 test982 test983 test984 test985 test986 \
d889a8
 \
d889a8
 test1000 test1001 test1002 test1003 test1004 test1005 test1006 test1007 \
d889a8
 test1008 test1009 test1010 test1011 test1012 test1013 test1014 test1015 \
d889a8
diff --git a/tests/data/test980 b/tests/data/test980
d889a8
new file mode 100644
d889a8
index 0000000..97567f8
d889a8
--- /dev/null
d889a8
+++ b/tests/data/test980
d889a8
@@ -0,0 +1,52 @@
d889a8
+<testcase>
d889a8
+<info>
d889a8
+<keywords>
d889a8
+SMTP
d889a8
+STARTTLS
d889a8
+</keywords>
d889a8
+</info>
d889a8
+
d889a8
+#
d889a8
+# Server-side
d889a8
+<reply>
d889a8
+<servercmd>
d889a8
+CAPA STARTTLS
d889a8
+AUTH PLAIN
d889a8
+REPLY STARTTLS 454 currently unavailable\r\n235 Authenticated\r\n250 2.1.0 Sender ok\r\n250 2.1.5 Recipient ok\r\n354 Enter mail\r\n250 2.0.0 Accepted
d889a8
+REPLY AUTH 535 5.7.8 Authentication credentials invalid
d889a8
+</servercmd>
d889a8
+</reply>
d889a8
+
d889a8
+#
d889a8
+# Client-side
d889a8
+<client>
d889a8
+<features>
d889a8
+SSL
d889a8
+</features>
d889a8
+<server>
d889a8
+smtp
d889a8
+</server>
d889a8
+ <name>
d889a8
+SMTP STARTTLS pipelined server response
d889a8
+ </name>
d889a8
+<stdin>
d889a8
+mail body
d889a8
+</stdin>
d889a8
+ <command>
d889a8
+smtp://%HOSTIP:%SMTPPORT/%TESTNUMBER --mail-rcpt recipient@example.com --mail-from sender@example.com -u user:secret --ssl --sasl-ir -T -
d889a8
+</command>
d889a8
+</client>
d889a8
+
d889a8
+#
d889a8
+# Verify data after the test has been "shot"
d889a8
+<verify>
d889a8
+# 8 is CURLE_WEIRD_SERVER_REPLY
d889a8
+<errorcode>
d889a8
+8
d889a8
+</errorcode>
d889a8
+<protocol>
d889a8
+EHLO %TESTNUMBER
d889a8
+STARTTLS
d889a8
+</protocol>
d889a8
+</verify>
d889a8
+</testcase>
d889a8
diff --git a/tests/data/test981 b/tests/data/test981
d889a8
new file mode 100644
d889a8
index 0000000..2b98ce4
d889a8
--- /dev/null
d889a8
+++ b/tests/data/test981
d889a8
@@ -0,0 +1,59 @@
d889a8
+<testcase>
d889a8
+<info>
d889a8
+<keywords>
d889a8
+IMAP
d889a8
+STARTTLS
d889a8
+</keywords>
d889a8
+</info>
d889a8
+
d889a8
+#
d889a8
+# Server-side
d889a8
+<reply>
d889a8
+<servercmd>
d889a8
+CAPA STARTTLS
d889a8
+REPLY STARTTLS A002 BAD currently unavailable\r\nA003 OK Authenticated\r\nA004 OK Accepted
d889a8
+REPLY LOGIN A003 BAD Authentication credentials invalid
d889a8
+</servercmd>
d889a8
+</reply>
d889a8
+
d889a8
+#
d889a8
+# Client-side
d889a8
+<client>
d889a8
+<features>
d889a8
+SSL
d889a8
+</features>
d889a8
+<server>
d889a8
+imap
d889a8
+</server>
d889a8
+ <name>
d889a8
+IMAP STARTTLS pipelined server response
d889a8
+ </name>
d889a8
+ <command>
d889a8
+imap://%HOSTIP:%IMAPPORT/%TESTNUMBER -T log/upload%TESTNUMBER -u user:secret --ssl
d889a8
+</command>
d889a8
+<file name="log/upload%TESTNUMBER">
d889a8
+Date: Mon, 7 Feb 1994 21:52:25 -0800 (PST)
d889a8
+From: Fred Foobar <foobar@example.COM>
d889a8
+Subject: afternoon meeting
d889a8
+To: joe@example.com
d889a8
+Message-Id: <B27397-0100000@example.COM>
d889a8
+MIME-Version: 1.0
d889a8
+Content-Type: TEXT/PLAIN; CHARSET=US-ASCII
d889a8
+
d889a8
+Hello Joe, do you think we can meet at 3:30 tomorrow?
d889a8
+</file>
d889a8
+</client>
d889a8
+
d889a8
+#
d889a8
+# Verify data after the test has been "shot"
d889a8
+<verify>
d889a8
+# 8 is CURLE_WEIRD_SERVER_REPLY
d889a8
+<errorcode>
d889a8
+8
d889a8
+</errorcode>
d889a8
+<protocol>
d889a8
+A001 CAPABILITY
d889a8
+A002 STARTTLS
d889a8
+</protocol>
d889a8
+</verify>
d889a8
+</testcase>
d889a8
diff --git a/tests/data/test982 b/tests/data/test982
d889a8
new file mode 100644
d889a8
index 0000000..9e07cc0
d889a8
--- /dev/null
d889a8
+++ b/tests/data/test982
d889a8
@@ -0,0 +1,57 @@
d889a8
+<testcase>
d889a8
+<info>
d889a8
+<keywords>
d889a8
+POP3
d889a8
+STARTTLS
d889a8
+</keywords>
d889a8
+</info>
d889a8
+
d889a8
+#
d889a8
+# Server-side
d889a8
+<reply>
d889a8
+<servercmd>
d889a8
+CAPA STLS USER
d889a8
+REPLY STLS -ERR currently unavailable\r\n+OK user accepted\r\n+OK authenticated
d889a8
+REPLY PASS -ERR Authentication credentials invalid
d889a8
+</servercmd>
d889a8
+<data nocheck="yes">
d889a8
+From: me@somewhere
d889a8
+To: fake@nowhere
d889a8
+
d889a8
+body
d889a8
+
d889a8
+--
d889a8
+  yours sincerely
d889a8
+</data>
d889a8
+</reply>
d889a8
+
d889a8
+#
d889a8
+# Client-side
d889a8
+<client>
d889a8
+<features>
d889a8
+SSL
d889a8
+</features>
d889a8
+<server>
d889a8
+pop3
d889a8
+</server>
d889a8
+ <name>
d889a8
+POP3 STARTTLS pipelined server response
d889a8
+ </name>
d889a8
+ <command>
d889a8
+pop3://%HOSTIP:%POP3PORT/%TESTNUMBER -u user:secret --ssl
d889a8
+ </command>
d889a8
+</client>
d889a8
+
d889a8
+#
d889a8
+# Verify data after the test has been "shot"
d889a8
+<verify>
d889a8
+# 8 is CURLE_WEIRD_SERVER_REPLY
d889a8
+<errorcode>
d889a8
+8
d889a8
+</errorcode>
d889a8
+<protocol>
d889a8
+CAPA
d889a8
+STLS
d889a8
+</protocol>
d889a8
+</verify>
d889a8
+</testcase>
d889a8
diff --git a/tests/data/test983 b/tests/data/test983
d889a8
new file mode 100644
d889a8
index 0000000..300ec45
d889a8
--- /dev/null
d889a8
+++ b/tests/data/test983
d889a8
@@ -0,0 +1,52 @@
d889a8
+<testcase>
d889a8
+<info>
d889a8
+<keywords>
d889a8
+FTP
d889a8
+STARTTLS
d889a8
+</keywords>
d889a8
+</info>
d889a8
+
d889a8
+#
d889a8
+# Server-side
d889a8
+<reply>
d889a8
+<servercmd>
d889a8
+REPLY AUTH 500 unknown command\r\n500 unknown command\r\n331 give password\r\n230 Authenticated\r\n257 "/"\r\n200 OK\r\n200 OK\r\n200 OK\r\n226 Transfer complete
d889a8
+REPLY PASS 530 Login incorrect
d889a8
+</servercmd>
d889a8
+</reply>
d889a8
+
d889a8
+# Client-side
d889a8
+<client>
d889a8
+<features>
d889a8
+SSL
d889a8
+</features>
d889a8
+<server>
d889a8
+ftp
d889a8
+</server>
d889a8
+ <name>
d889a8
+FTP STARTTLS pipelined server response
d889a8
+ </name>
d889a8
+<file name="log/test%TESTNUMBER.txt">
d889a8
+data
d889a8
+    to
d889a8
+      see
d889a8
+that FTPS
d889a8
+works
d889a8
+  so does it?
d889a8
+</file>
d889a8
+ <command>
d889a8
+--ssl --ftp-ssl-control ftp://%HOSTIP:%FTPPORT/%TESTNUMBER -T log/test%TESTNUMBER.txt -u user:secret -P %CLIENTIP
d889a8
+</command>
d889a8
+</client>
d889a8
+
d889a8
+# Verify data after the test has been "shot"
d889a8
+<verify>
d889a8
+# 8 is CURLE_WEIRD_SERVER_REPLY
d889a8
+<errorcode>
d889a8
+8
d889a8
+</errorcode>
d889a8
+<protocol>
d889a8
+AUTH SSL
d889a8
+</protocol>
d889a8
+</verify>
d889a8
+</testcase>
d889a8
-- 
d889a8
2.31.1
d889a8