summaryrefslogtreecommitdiffstats
path: root/Lib/email
diff options
context:
space:
mode:
authorMiss Islington (bot) <31488909+miss-islington@users.noreply.github.com>2019-07-16 18:08:36 (GMT)
committerGitHub <noreply@github.com>2019-07-16 18:08:36 (GMT)
commit6a2aec0ff587032beb8aac8cbebb09e7a52f6694 (patch)
treef1aeaa1333a3a6f3de7deb5fd2810be7de17c1c6 /Lib/email
parent86742d4ce8d6c301104e238699b30f6bdaf9f9cb (diff)
downloadcpython-6a2aec0ff587032beb8aac8cbebb09e7a52f6694.zip
cpython-6a2aec0ff587032beb8aac8cbebb09e7a52f6694.tar.gz
cpython-6a2aec0ff587032beb8aac8cbebb09e7a52f6694.tar.bz2
Fix infinite loop in email folding logic (GH-12732)
As far as I can tell, this infinite loop would be triggered if: 1. The value being folded contains a single word (no spaces) longer than max_line_length 2. The max_line_length is shorter than the encoding's name + 9 characters. bpo-36564: https://bugs.python.org/issue36564 (cherry picked from commit f69d5c61981ea97d251db515c7ff280fcc17182d) Co-authored-by: Paul Ganssle <pganssle@users.noreply.github.com>
Diffstat (limited to 'Lib/email')
-rw-r--r--Lib/email/_header_value_parser.py17
-rw-r--r--Lib/email/parser.py1
2 files changed, 12 insertions, 6 deletions
diff --git a/Lib/email/_header_value_parser.py b/Lib/email/_header_value_parser.py
index d9f592b..6475321 100644
--- a/Lib/email/_header_value_parser.py
+++ b/Lib/email/_header_value_parser.py
@@ -2825,15 +2825,22 @@ def _fold_as_ew(to_encode, lines, maxlen, last_ew, ew_combine_allowed, charset):
trailing_wsp = to_encode[-1]
to_encode = to_encode[:-1]
new_last_ew = len(lines[-1]) if last_ew is None else last_ew
+
+ encode_as = 'utf-8' if charset == 'us-ascii' else charset
+
+ # The RFC2047 chrome takes up 7 characters plus the length
+ # of the charset name.
+ chrome_len = len(encode_as) + 7
+
+ if (chrome_len + 1) >= maxlen:
+ raise errors.HeaderParseError(
+ "max_line_length is too small to fit an encoded word")
+
while to_encode:
remaining_space = maxlen - len(lines[-1])
- # The RFC2047 chrome takes up 7 characters plus the length
- # of the charset name.
- encode_as = 'utf-8' if charset == 'us-ascii' else charset
- text_space = remaining_space - len(encode_as) - 7
+ text_space = remaining_space - chrome_len
if text_space <= 0:
lines.append(' ')
- # XXX We'll get an infinite loop here if maxlen is <= 7
continue
to_encode_word = to_encode[:text_space]
diff --git a/Lib/email/parser.py b/Lib/email/parser.py
index 555b172..7db4da1 100644
--- a/Lib/email/parser.py
+++ b/Lib/email/parser.py
@@ -13,7 +13,6 @@ from email.feedparser import FeedParser, BytesFeedParser
from email._policybase import compat32
-
class Parser:
def __init__(self, _class=None, *, policy=compat32):
"""Parser of RFC 2822 and MIME email messages.