Adding a support for SNI (Issue #1256)

This commit is contained in:
Miroslav Stampar 2015-06-01 10:45:16 +02:00
parent 341d2a6028
commit ec87d8ebda
2 changed files with 40 additions and 16 deletions

View File

@ -1836,6 +1836,7 @@ def _setKnowledgeBaseAttributes(flushAll=True):
kb.safeReq = AttribDict() kb.safeReq = AttribDict()
kb.singleLogFlags = set() kb.singleLogFlags = set()
kb.reduceTests = None kb.reduceTests = None
kb.tlsSNI = None
kb.stickyDBMS = False kb.stickyDBMS = False
kb.stickyLevel = None kb.stickyLevel = None
kb.storeCrawlingChoice = None kb.storeCrawlingChoice = None

View File

@ -7,8 +7,10 @@ See the file 'doc/COPYING' for copying permission
import httplib import httplib
import socket import socket
import sys
import urllib2 import urllib2
from lib.core.data import kb
from lib.core.data import logger from lib.core.data import logger
from lib.core.exception import SqlmapConnectionException from lib.core.exception import SqlmapConnectionException
@ -19,7 +21,7 @@ try:
except ImportError: except ImportError:
pass pass
_protocols = filter(None, (getattr(ssl, _, None) for _ in ("PROTOCOL_SSLv3", "PROTOCOL_TLSv1", "PROTOCOL_SSLv23", "PROTOCOL_SSLv2"))) _protocols = filter(None, (getattr(ssl, _, None) for _ in ("PROTOCOL_TLSv1_2", "PROTOCOL_TLSv1_1", "PROTOCOL_TLSv1", "PROTOCOL_SSLv3", "PROTOCOL_SSLv23", "PROTOCOL_SSLv2")))
class HTTPSConnection(httplib.HTTPSConnection): class HTTPSConnection(httplib.HTTPSConnection):
""" """
@ -41,21 +43,42 @@ class HTTPSConnection(httplib.HTTPSConnection):
success = False success = False
for protocol in _protocols: if not kb.tlsSNI:
try: for protocol in _protocols:
sock = create_sock() try:
_ = ssl.wrap_socket(sock, self.key_file, self.cert_file, ssl_version=protocol) sock = create_sock()
if _: _ = ssl.wrap_socket(sock, self.key_file, self.cert_file, ssl_version=protocol)
success = True if _:
self.sock = _ success = True
_protocols.remove(protocol) self.sock = _
_protocols.insert(0, protocol) _protocols.remove(protocol)
break _protocols.insert(0, protocol)
else: break
sock.close() else:
except (ssl.SSLError, socket.error, httplib.BadStatusLine), errMsg: sock.close()
self._tunnel_host = None except (ssl.SSLError, socket.error, httplib.BadStatusLine), errMsg:
logger.debug("SSL connection error occurred ('%s')" % errMsg) self._tunnel_host = None
logger.debug("SSL connection error occurred ('%s')" % errMsg)
# Reference(s): https://docs.python.org/2/library/ssl.html#ssl.SSLContext
# https://www.mnot.net/blog/2014/12/27/python_2_and_tls_sni
if not success and hasattr(ssl, "SSLContext"):
for protocol in filter(lambda _: _ >= ssl.PROTOCOL_TLSv1, _protocols):
try:
sock = create_sock()
context = ssl.SSLContext(protocol)
_ = context.wrap_socket(sock, do_handshake_on_connect=False, server_hostname=self.host)
if _:
kb.tlsSNI = success = True
self.sock = _
_protocols.remove(protocol)
_protocols.insert(0, protocol)
break
else:
sock.close()
except (ssl.SSLError, socket.error, httplib.BadStatusLine), errMsg:
self._tunnel_host = None
logger.debug("SSL connection error occurred ('%s')" % errMsg)
if not success: if not success:
raise SqlmapConnectionException("can't establish SSL connection") raise SqlmapConnectionException("can't establish SSL connection")