From 4e59dc5b55b7b69788f9e131fd44a23bb9c89b08 Mon Sep 17 00:00:00 2001 From: justcool393 Date: Fri, 25 Nov 2022 07:10:05 -0600 Subject: [PATCH] security: fix DoS on title getter the `timeout` parameter only applies to seconds per *byte* received (and time to first byte), not the entire request this means an attacker could theoretically send a very... slow... stream... of... bytes... and... crash... the... worker... when... the... timeout... is... reached... --- files/routes/posts.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/files/routes/posts.py b/files/routes/posts.py index e145c9002..a6068efbd 100644 --- a/files/routes/posts.py +++ b/files/routes/posts.py @@ -1075,6 +1075,7 @@ extensions = IMAGE_FORMATS + VIDEO_FORMATS + AUDIO_FORMATS @ratelimit_user("3/minute") @auth_required def get_post_title(v): + POST_TITLE_TIMEOUT = 5 url = request.values.get("url") if not url or '\\' in url: abort(400) url = url.strip() @@ -1084,7 +1085,8 @@ def get_post_title(v): if any((checking_url.endswith(f'.{x}') for x in extensions)): abort(400) - try: x = requests.get(url, headers=titleheaders, timeout=5, proxies=proxies) + try: + x = gevent.with_timeout(POST_TITLE_TIMEOUT, requests.get, url, headers=titleheaders, timeout=POST_TITLE_TIMEOUT, proxies=proxies) except: abort(400) content_type = x.headers.get("Content-Type")