Skip to content

Commit

Permalink
Merge pull request #1928 from ValdikSS/crypt-obf
Browse files Browse the repository at this point in the history
Less obvious fake TLS certificate generation
  • Loading branch information
HelloZeroNet authored Mar 27, 2019
2 parents 9117339 + f66cfc9 commit 91b2f6a
Show file tree
Hide file tree
Showing 2 changed files with 104 additions and 26 deletions.
109 changes: 99 additions & 10 deletions src/Crypt/CryptConnection.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@
import os
import ssl
import hashlib
import random

from Config import config
from util import SslPatch
Expand All @@ -11,6 +12,7 @@

class CryptConnectionManager:
def __init__(self):
# TODO: UGLY UGLY UGLY
# OpenSSL params
if sys.platform.startswith("win"):
self.openssl_bin = "src\\lib\\opensslVerify\\openssl.exe"
Expand All @@ -19,6 +21,11 @@ def __init__(self):
self.openssl_env = {"OPENSSL_CONF": "src/lib/opensslVerify/openssl.cnf"}

self.crypt_supported = [] # Supported cryptos
self.cacert_pem = config.data_dir+"/cacert-rsa.pem"
self.cakey_pem = config.data_dir+"/cakey-rsa.pem"
self.cert_pem = config.data_dir+"/cert-rsa.pem"
self.cert_csr = config.data_dir+"/cert-rsa.csr"
self.key_pem = config.data_dir+"/key-rsa.pem"

# Select crypt that supported by both sides
# Return: Name of the crypto
Expand All @@ -36,8 +43,8 @@ def wrapSocket(self, sock, crypt, server=False, cert_pin=None):
ciphers += "!aNULL:!eNULL:!EXPORT:!DSS:!DES:!RC4:!3DES:!MD5:!PSK"
if server:
sock_wrapped = ssl.wrap_socket(
sock, server_side=server, keyfile='%s/key-rsa.pem' % config.data_dir,
certfile='%s/cert-rsa.pem' % config.data_dir, ciphers=ciphers)
sock, server_side=server, keyfile=self.key_pem,
certfile=self.cert_pem, ciphers=ciphers)
else:
sock_wrapped = ssl.wrap_socket(sock, ciphers=ciphers)
if cert_pin:
Expand All @@ -50,7 +57,7 @@ def wrapSocket(self, sock, crypt, server=False, cert_pin=None):
def removeCerts(self):
if config.keep_ssl_cert:
return False
for file_name in ["cert-rsa.pem", "key-rsa.pem"]:
for file_name in ["cert-rsa.pem", "key-rsa.pem", "cacert-rsa.pem", "cakey-rsa.pem", "cert-rsa.csr"]:
file_path = "%s/%s" % (config.data_dir, file_name)
if os.path.isfile(file_path):
os.unlink(file_path)
Expand All @@ -66,25 +73,107 @@ def loadCerts(self):
# Try to create RSA server cert + sign for connection encryption
# Return: True on success
def createSslRsaCert(self):
if os.path.isfile("%s/cert-rsa.pem" % config.data_dir) and os.path.isfile("%s/key-rsa.pem" % config.data_dir):
casubjects = [
"/C=US/O=Amazon/OU=Server CA 1B/CN=Amazon",
"/C=US/O=Let's Encrypt/CN=Let's Encrypt Authority X3",
"/C=US/O=DigiCert Inc/OU=www.digicert.com/CN = DigiCert SHA2 High Assurance Server CA",
"/C=GB/ST=Greater Manchester/L=Salford/O=COMODO CA Limited/CN = COMODO RSA Domain Validation Secure Server CA"
]
fakedomains = [
"yahoo.com",
"amazon.com",
"live.com",
"microsoft.com",
"mail.ru",
"csdn.net",
"bing.com",
"amazon.co.jp",
"office.com",
"imdb.com",
"msn.com",
"samsung.com",
"huawei.com",
"ztedevices.com",
"godaddy.com",
"w3.org",
"gravatar.com",
"creativecommons.org",
"hatena.ne.jp",
"adobe.com",
"opera.com",
"apache.org",
"rambler.ru",
"one.com",
"nationalgeographic.com",
"networksolutions.com",
"php.net",
"python.org",
"phoca.cz",
"debian.org",
"ubuntu.com",
"nazwa.pl",
"symantec.com"
]
self.openssl_env['CN'] = random.choice(fakedomains)

if os.path.isfile(self.cert_pem) and os.path.isfile(self.key_pem):
return True # Files already exits

import subprocess
cmd = "%s req -x509 -newkey rsa:2048 -sha256 -batch -keyout %s -out %s -nodes -config %s" % helper.shellquote(
# Generate CAcert and CAkey
cmd = "%s req -new -newkey rsa:2048 -days 3650 -nodes -x509 -subj %s -keyout %s -out %s -batch -config %s" % helper.shellquote(
self.openssl_bin,
config.data_dir+"/key-rsa.pem",
config.data_dir+"/cert-rsa.pem",
self.openssl_env["OPENSSL_CONF"]
random.choice(casubjects),
self.cakey_pem,
self.cacert_pem,
self.openssl_env["OPENSSL_CONF"],
)
proc = subprocess.Popen(
cmd.encode(sys.getfilesystemencoding()),
shell=True, stderr=subprocess.STDOUT, stdout=subprocess.PIPE, env=self.openssl_env
)
back = proc.stdout.read().strip()
proc.wait()
logging.debug("Generating RSA cert and key PEM files...%s" % back)
logging.debug("Generating RSA CAcert and CAkey PEM files...%s" % back)

if os.path.isfile("%s/cert-rsa.pem" % config.data_dir) and os.path.isfile("%s/key-rsa.pem" % config.data_dir):
if not (os.path.isfile(self.cacert_pem) and os.path.isfile(self.cakey_pem)):
logging.error("RSA ECC SSL CAcert generation failed, CAcert or CAkey files not exist.")
return False

# Generate certificate key and signing request
cmd = "%s req -new -newkey rsa:2048 -keyout %s -out %s -subj %s -sha256 -nodes -batch -config %s" % helper.shellquote(
self.openssl_bin,
self.key_pem,
self.cert_csr,
"/CN="+self.openssl_env['CN'],
self.openssl_env["OPENSSL_CONF"],
)
proc = subprocess.Popen(
cmd.encode(sys.getfilesystemencoding()),
shell=True, stderr=subprocess.STDOUT, stdout=subprocess.PIPE, env=self.openssl_env
)
back = proc.stdout.read().strip()
proc.wait()
logging.debug("Generating certificate key and signing request...%s" % back)

# Sign request and generate certificate
cmd = "%s x509 -req -in %s -CA %s -CAkey %s -CAcreateserial -out %s -days 730 -sha256 -extensions x509_ext -extfile %s" % helper.shellquote(
self.openssl_bin,
self.cert_csr,
self.cacert_pem,
self.cakey_pem,
self.cert_pem,
self.openssl_env["OPENSSL_CONF"],
)
proc = subprocess.Popen(
cmd.encode(sys.getfilesystemencoding()),
shell=True, stderr=subprocess.STDOUT, stdout=subprocess.PIPE, env=self.openssl_env
)
back = proc.stdout.read().strip()
proc.wait()
logging.debug("Generating RSA cert...%s" % back)

if os.path.isfile(self.cert_pem) and os.path.isfile(self.key_pem):
return True
else:
logging.error("RSA ECC SSL cert generation failed, cert or key files not exist.")
Expand Down
21 changes: 5 additions & 16 deletions src/lib/opensslVerify/openssl.cnf
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
[ req ]
prompt = no
prompt = yes
default_bits = 2048
default_keyfile = server-key.pem
distinguished_name = subject
Expand Down Expand Up @@ -32,8 +32,8 @@ authorityKeyIdentifier = keyid,issuer

basicConstraints = CA:FALSE
keyUsage = digitalSignature, keyEncipherment
extendedKeyUsage = clientAuth, serverAuth
subjectAltName = @alternate_names
nsComment = "OpenSSL Generated Certificate"

# RFC 5280, Section 4.2.1.12 makes EKU optional
# CA/Browser Baseline Requirements, Appendix (B)(3)(G) makes me confused
Expand All @@ -46,25 +46,14 @@ subjectKeyIdentifier = hash

basicConstraints = CA:FALSE
keyUsage = digitalSignature, keyEncipherment
extendedKeyUsage = clientAuth, serverAuth
subjectAltName = @alternate_names
nsComment = "OpenSSL Generated Certificate"

# RFC 5280, Section 4.2.1.12 makes EKU optional
# CA/Browser Baseline Requirements, Appendix (B)(3)(G) makes me confused
# extendedKeyUsage = serverAuth, clientAuth

[ alternate_names ]

DNS.1 = example.com
DNS.2 = www.example.com
DNS.3 = mail.example.com
DNS.4 = ftp.example.com

# Add these if you need them. But usually you don't want them or
# need them in production. You may need them for development.
# DNS.5 = localhost
# DNS.6 = localhost.localdomain
# DNS.7 = 127.0.0.1

# IPv6 localhost
# DNS.8 = ::1
DNS.1 = $ENV::CN
DNS.2 = www.$ENV::CN

0 comments on commit 91b2f6a

Please sign in to comment.