From a9a6d4486e22a73dd114883b6069848c807f8bb8 Mon Sep 17 00:00:00 2001
From: Kfir Hadas <sharkykh@gmail.com>
Date: Sun, 21 May 2017 10:48:54 +0300
Subject: [PATCH] Generate self-signed certificates using 'sha256' digest
 (#3777)

* Update certgen.py (default to sha256, md5 is unsecure)

Update to https://github.com/pyca/pyopenssl/blob/d52975cef3a36e18552aeb23de7c06aa73d76454/examples/certgen.py

* Update self-signed certificate generator

sickbeard.helpers.create_https_certificates
---
 lib/README.md        |  1 +
 lib/certgen.py       | 28 +++++++++++++++-------------
 sickbeard/helpers.py | 13 ++++++++-----
 3 files changed, 24 insertions(+), 18 deletions(-)

diff --git a/lib/README.md b/lib/README.md
index 95500808d..bc9b1392e 100644
--- a/lib/README.md
+++ b/lib/README.md
@@ -18,6 +18,7 @@ Packages List
 =========
 ```
 beautifulsoup4==4.5.3
+# certgen.py==d52975c # source: https://github.com/pyca/pyopenssl/blob/d52975cef3a36e18552aeb23de7c06aa73d76454/examples/certgen.py
 html5lib==0.999999999
   - six [required: Any, installed: 1.10.0]
   - webencodings [required: Any, installed: 0.5.1]
diff --git a/lib/certgen.py b/lib/certgen.py
index 1b941161b..7b70e98b8 100644
--- a/lib/certgen.py
+++ b/lib/certgen.py
@@ -1,21 +1,18 @@
 # -*- coding: latin-1 -*-
 #
-# Copyright (C) Martin Sj�gren and AB Strakt 2001, All rights reserved
-# Copyright (C) Jean-Paul Calderone 2008, All rights reserved
-# This file is licenced under the GNU LESSER GENERAL PUBLIC LICENSE Version 2.1 or later (aka LGPL v2.1)
-# Please see LGPL2.1.txt for more information
+# Copyright (C) AB Strakt
+# Copyright (C) Jean-Paul Calderone
+# See LICENSE for details.
+
 """
 Certificate generation module.
 """
 
 from OpenSSL import crypto
-import time
 
 TYPE_RSA = crypto.TYPE_RSA
 TYPE_DSA = crypto.TYPE_DSA
 
-serial = int(time.time())
-
 
 def createKeyPair(type, bits):
     """
@@ -29,12 +26,13 @@ def createKeyPair(type, bits):
     pkey.generate_key(type, bits)
     return pkey
 
-def createCertRequest(pkey, digest="md5", **name):
+
+def createCertRequest(pkey, digest="sha256", **name):
     """
     Create a certificate request.
 
     Arguments: pkey   - The key to associate with the request
-               digest - Digestion method to use for signing, default is md5
+               digest - Digestion method to use for signing, default is sha256
                **name - The name of the subject of the request, possible
                         arguments are:
                           C     - Country name
@@ -49,18 +47,20 @@ def createCertRequest(pkey, digest="md5", **name):
     req = crypto.X509Req()
     subj = req.get_subject()
 
-    for (key,value) in name.items():
+    for key, value in name.items():
         setattr(subj, key, value)
 
     req.set_pubkey(pkey)
     req.sign(pkey, digest)
     return req
 
-def createCertificate(req, (issuerCert, issuerKey), serial, (notBefore, notAfter), digest="md5"):
+
+def createCertificate(req, issuerCertKey, serial, validityPeriod,
+                      digest="sha256"):
     """
     Generate a certificate given a certificate request.
 
-    Arguments: req        - Certificate reqeust to use
+    Arguments: req        - Certificate request to use
                issuerCert - The certificate of the issuer
                issuerKey  - The private key of the issuer
                serial     - Serial number for the certificate
@@ -68,9 +68,11 @@ def createCertificate(req, (issuerCert, issuerKey), serial, (notBefore, notAfter
                             starts being valid
                notAfter   - Timestamp (relative to now) when the certificate
                             stops being valid
-               digest     - Digest method to use for signing, default is md5
+               digest     - Digest method to use for signing, default is sha256
     Returns:   The signed certificate in an X509 object
     """
+    issuerCert, issuerKey = issuerCertKey
+    notBefore, notAfter = validityPeriod
     cert = crypto.X509()
     cert.set_serial_number(serial)
     cert.gmtime_adj_notBefore(notBefore)
diff --git a/sickbeard/helpers.py b/sickbeard/helpers.py
index eca4b4ad0..b8d9d48f6 100644
--- a/sickbeard/helpers.py
+++ b/sickbeard/helpers.py
@@ -839,22 +839,25 @@ def create_https_certificates(ssl_cert, ssl_key):
     # assert isinstance(ssl_cert, unicode)
 
     try:
-        from OpenSSL import crypto  # noinspection PyUnresolvedReferences
-        from certgen import createKeyPair, createCertRequest, createCertificate, TYPE_RSA, \
-            serial  # @UnresolvedImport
+        # noinspection PyUnresolvedReferences
+        from OpenSSL import crypto
+        from certgen import createKeyPair, createCertRequest, createCertificate, TYPE_RSA
     except Exception:
         logger.log("pyopenssl module missing, please install for https access", logger.WARNING)
         return False
 
+    import time
+    serial = int(time.time())
+    validity_period = (0, 60 * 60 * 24 * 365 * 10)  # ten years
     # Create the CA Certificate
     cakey = createKeyPair(TYPE_RSA, 4096)
     careq = createCertRequest(cakey, CN='Certificate Authority')
-    cacert = createCertificate(careq, (careq, cakey), serial, (0, 60 * 60 * 24 * 365 * 10))  # ten years
+    cacert = createCertificate(careq, (careq, cakey), serial, validity_period, 'sha256')
 
     cname = 'SickRage'
     pkey = createKeyPair(TYPE_RSA, 4096)
     req = createCertRequest(pkey, CN=cname)
-    cert = createCertificate(req, (cacert, cakey), serial, (0, 60 * 60 * 24 * 365 * 10))  # ten years
+    cert = createCertificate(req, (cacert, cakey), serial, validity_period, 'sha256')
 
     # Save the key and certificate to disk
     try:
-- 
GitLab