From 1fc52011bbdee6e0b301eaceb6c11fd861f25c4a Mon Sep 17 00:00:00 2001
From: DarkTinia <1106116020@qq.com>
Date: Wed, 18 Jan 2023 04:54:18 -0800
Subject: [PATCH 1/3] repair a ReDoS vulnerability in markdown2.py
---
lib/markdown2.py | 54 ++++++++++++++++++++++++++++++++++++++++++++----
1 file changed, 50 insertions(+), 4 deletions(-)
diff --git a/lib/markdown2.py b/lib/markdown2.py
index 112fa707..a44e92ae 100755
--- a/lib/markdown2.py
+++ b/lib/markdown2.py
@@ -105,6 +105,7 @@
import sys
import re
+import re2
import logging
from hashlib import sha256
import optparse
@@ -2246,17 +2247,62 @@ def _do_tg_spoiler(self, text):
text = self._tg_spoiler_re.sub(r"\1", text)
return text
- _strong_re = re.compile(r"(\*\*|__)(?=\S)(.+?[*_]*)(?<=\S)\1", re.S)
+ #_strong_re = re.compile(r"(\*\*|__)(?=\S)(.+?[*_]*)(?<=\S)\1", re.S)
_em_re = re.compile(r"(\*|_)(?=\S)(.+?)(?<=\S)\1", re.S)
- _code_friendly_strong_re = re.compile(r"\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*", re.S)
+ #_code_friendly_strong_re = re.compile(r"\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*", re.S)
_code_friendly_em_re = re.compile(r"\*(?=\S)(.+?)(?<=\S)\*", re.S)
+
+ def _safe_strong_re_sub(self,text):
+ import re2
+ #(\*\*|__)(?=\S)(.+?[*_]*)(?<=\S)\1
+ _code_friendly_strong_re = re2.compile(r"(?s)(\*\*|__)(.+?[*_]*)(\*\*|__)")
+ m = _code_friendly_strong_re.search(text)
+ tmpText = ""
+ while True:
+ if m == None:
+ tmpText += text
+ return tmpText
+ else:
+ group2Text = m.group(2)
+ # lookaround‘s constraints
+ if re2.match("\S.*", group2Text) and re2.match(".*\S", group2Text) and m.group(1) == m.group(3):
+ tmpText += text[0:m.span()[0]] + "" + group2Text + ""
+ text = text[m.span()[1]:]
+ m = _code_friendly_strong_re.search(text)
+ else:
+ return tmpText + text
+
+ def _safe_code_friendly_strong_re_sub(self,text):
+ # **abc**v**edf **
+ #\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*
+ _code_friendly_strong_re = re2.compile(r"(?s)\*\*(.+?[*_]*)\*\*")
+ m = _code_friendly_strong_re.search(text)
+ tmpText = ""
+ while True:
+ if m == None:
+ tmpText += text
+ return tmpText
+ else:
+ group1Text = m.group(1)
+ # lookaround‘s constraints
+ if re2.match("\S.*",group1Text) and re2.match(".*\S",group1Text):
+ tmpText += text[0:m.span()[0]] + "" + group1Text + ""
+ text = text[m.span()[1]:]
+ m = _code_friendly_strong_re.search(text)
+ else:
+ return tmpText + text
+
+
+
def _do_italics_and_bold(self, text):
# must go first:
if "code-friendly" in self.extras:
- text = self._code_friendly_strong_re.sub(r"\1", text)
+ #text =self._code_friendly_strong_re(r"\1",text)
+ text = self._safe_code_friendly_strong_re_sub(text)
text = self._code_friendly_em_re.sub(r"\1", text)
else:
- text = self._strong_re.sub(r"\2", text)
+ #text = self._strong_re.sub(r"\2", text)
+ text = self._safe_strong_re_sub(text)
text = self._em_re.sub(r"\2", text)
return text
From ea615a9382587da258a657909ff873cbfb7d712f Mon Sep 17 00:00:00 2001
From: DarkTinia <1106116020@qq.com>
Date: Wed, 18 Jan 2023 20:48:02 -0800
Subject: [PATCH 2/3] add an install_requires in setup.py
---
setup.py | 1 +
1 file changed, 1 insertion(+)
diff --git a/setup.py b/setup.py
index e7c43ad3..d9b23c3a 100755
--- a/setup.py
+++ b/setup.py
@@ -56,6 +56,7 @@
},
description="A fast and complete Python implementation of Markdown",
python_requires=">=3.5, <4",
+ install_requires=['pyre2'],
extras_require=extras_require,
classifiers=classifiers.strip().split("\n"),
long_description="""markdown2: A fast and complete Python implementation of Markdown.
From 0eafad6ad784d168eb20238c6aed7a76744ba642 Mon Sep 17 00:00:00 2001
From: Crozzers
Date: Sun, 24 Sep 2023 19:09:14 +0100
Subject: [PATCH 3/3] Remove requirement for third party regex library
---
lib/markdown2.py | 58 +++++-------------------------------------------
setup.py | 1 -
2 files changed, 6 insertions(+), 53 deletions(-)
diff --git a/lib/markdown2.py b/lib/markdown2.py
index a44e92ae..4f1f2f61 100755
--- a/lib/markdown2.py
+++ b/lib/markdown2.py
@@ -105,7 +105,6 @@
import sys
import re
-import re2
import logging
from hashlib import sha256
import optparse
@@ -2241,68 +2240,23 @@ def _do_strike(self, text):
def _do_underline(self, text):
text = self._underline_re.sub(r"\1", text)
return text
-
+
_tg_spoiler_re = re.compile(r"\|\|\s?(.+?)\s?\|\|", re.S)
def _do_tg_spoiler(self, text):
text = self._tg_spoiler_re.sub(r"\1", text)
return text
- #_strong_re = re.compile(r"(\*\*|__)(?=\S)(.+?[*_]*)(?<=\S)\1", re.S)
- _em_re = re.compile(r"(\*|_)(?=\S)(.+?)(?<=\S)\1", re.S)
- #_code_friendly_strong_re = re.compile(r"\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*", re.S)
+ _strong_re = re.compile(r"(\*\*|__)(?=\S)(.*\S)\1", re.S)
+ _em_re = re.compile(r"(\*|_)(?=\S)(.*?\S)\1", re.S)
+ _code_friendly_strong_re = re.compile(r"\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*", re.S)
_code_friendly_em_re = re.compile(r"\*(?=\S)(.+?)(?<=\S)\*", re.S)
-
- def _safe_strong_re_sub(self,text):
- import re2
- #(\*\*|__)(?=\S)(.+?[*_]*)(?<=\S)\1
- _code_friendly_strong_re = re2.compile(r"(?s)(\*\*|__)(.+?[*_]*)(\*\*|__)")
- m = _code_friendly_strong_re.search(text)
- tmpText = ""
- while True:
- if m == None:
- tmpText += text
- return tmpText
- else:
- group2Text = m.group(2)
- # lookaround‘s constraints
- if re2.match("\S.*", group2Text) and re2.match(".*\S", group2Text) and m.group(1) == m.group(3):
- tmpText += text[0:m.span()[0]] + "" + group2Text + ""
- text = text[m.span()[1]:]
- m = _code_friendly_strong_re.search(text)
- else:
- return tmpText + text
-
- def _safe_code_friendly_strong_re_sub(self,text):
- # **abc**v**edf **
- #\*\*(?=\S)(.+?[*_]*)(?<=\S)\*\*
- _code_friendly_strong_re = re2.compile(r"(?s)\*\*(.+?[*_]*)\*\*")
- m = _code_friendly_strong_re.search(text)
- tmpText = ""
- while True:
- if m == None:
- tmpText += text
- return tmpText
- else:
- group1Text = m.group(1)
- # lookaround‘s constraints
- if re2.match("\S.*",group1Text) and re2.match(".*\S",group1Text):
- tmpText += text[0:m.span()[0]] + "" + group1Text + ""
- text = text[m.span()[1]:]
- m = _code_friendly_strong_re.search(text)
- else:
- return tmpText + text
-
-
-
def _do_italics_and_bold(self, text):
# must go first:
if "code-friendly" in self.extras:
- #text =self._code_friendly_strong_re(r"\1",text)
- text = self._safe_code_friendly_strong_re_sub(text)
+ text = self._code_friendly_strong_re.sub(r"\1", text)
text = self._code_friendly_em_re.sub(r"\1", text)
else:
- #text = self._strong_re.sub(r"\2", text)
- text = self._safe_strong_re_sub(text)
+ text = self._strong_re.sub(r"\2", text)
text = self._em_re.sub(r"\2", text)
return text
diff --git a/setup.py b/setup.py
index d9b23c3a..e7c43ad3 100755
--- a/setup.py
+++ b/setup.py
@@ -56,7 +56,6 @@
},
description="A fast and complete Python implementation of Markdown",
python_requires=">=3.5, <4",
- install_requires=['pyre2'],
extras_require=extras_require,
classifiers=classifiers.strip().split("\n"),
long_description="""markdown2: A fast and complete Python implementation of Markdown.