Skip to content

Commit

Permalink
Add skip_host_key_verification option
Browse files Browse the repository at this point in the history
Adds _skip_host_key_verification attribute to Transport and
provides a set_skip_host_key_verification method to set or clear
it (default: `False`).

Adds skip_host_key_verification parameter to SSHClient.connect
(default: `False`), which is passed directly to the transport.

Skipping host key verification might be useful in very rare cases
where it is not possible to verify the target's key, for example if
it uses a legacy signature algorithm that is no longer supported by
the client, e.g. in paramiko#2259.
  • Loading branch information
pghmcfc committed Jan 11, 2024
1 parent 43980e7 commit 3e415b1
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 1 deletion.
5 changes: 5 additions & 0 deletions paramiko/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -239,6 +239,7 @@ def connect(
disabled_algorithms=None,
transport_factory=None,
auth_strategy=None,
skip_host_key_verification=False,
):
"""
Connect to an SSH server and authenticate to it. The server's host key
Expand Down Expand Up @@ -318,6 +319,9 @@ def connect(
:param dict disabled_algorithms:
an optional dict passed directly to `.Transport` and its keyword
argument of the same name.
:param bool skip_host_key_verification:
whether or not to skip host key verification (not recommended,
default ``False``)
:param transport_factory:
an optional callable which is handed a subset of the constructor
arguments (primarily those related to the socket, GSS
Expand Down Expand Up @@ -417,6 +421,7 @@ def connect(
disabled_algorithms=disabled_algorithms,
)
t.use_compression(compress=compress)
t.set_skip_host_key_verification(skip_host_key_verification)
t.set_gss_host(
# t.hostname may be None, but GSS-API requires a target name.
# Therefore use hostname as fallback.
Expand Down
26 changes: 25 additions & 1 deletion paramiko/transport.py
Original file line number Diff line number Diff line change
Expand Up @@ -325,6 +325,7 @@ class Transport(threading.Thread, ClosingContextManager):

_modulus_pack = None
_active_check_timeout = 0.1
_skip_host_key_verification = False

def __init__(
self,
Expand Down Expand Up @@ -684,6 +685,27 @@ def set_gss_host(self, gss_host, trust_dns=True, gssapi_requested=True):
# And set attribute for reference later.
self.gss_host = gss_host

def set_skip_host_key_verification(self, skip_host_key_verification):
"""
Skipping host key verification might be useful in very rare cases
where it is not possible to verify the target's key, for example if
it uses a legacy signature algorithm that is no longer supported by
the client.
This option should be avoided if possible because host key
verification protects against issues like MITM attacks and replacement
of a server by a malicious actor that might perhaps use it to log
usernames and passwords with which to access the client system later.
:param bool skip_host_key_verification:
Whether of not to skip host key verification
(Defaults to False.)
:returns: ``None``.
.. versionadded:: 3.5.0
"""
self._skip_host_key_verification = skip_host_key_verification

def start_client(self, event=None, timeout=None):
"""
Negotiate a new SSH2 session as a client. This is the first step after
Expand Down Expand Up @@ -1973,7 +1995,9 @@ def _verify_key(self, host_key, sig):
key = self._key_info[self.host_key_type](Message(host_key))
if key is None:
raise SSHException("Unknown host key type")
if not key.verify_ssh_sig(self.H, Message(sig)):
if not self._skip_host_key_verification and not key.verify_ssh_sig(
self.H, Message(sig)
):
raise SSHException(
"Signature verification ({}) failed.".format(
self.host_key_type
Expand Down

0 comments on commit 3e415b1

Please sign in to comment.