SSH2: add support for RFC8308

This commit is contained in:
terrafrost 2023-11-21 23:02:42 -06:00
parent 173bb38e67
commit 356ab5f76a

View File

@ -360,6 +360,15 @@ class Net_SSH2
*/ */
var $languages_client_to_server = false; var $languages_client_to_server = false;
/**
* Server Signature Algorithms
*
* @link https://www.rfc-editor.org/rfc/rfc8308.html#section-3.1
* @var array|false
* @access private
*/
var $server_sig_algs = false;
/** /**
* Preferred Algorithms * Preferred Algorithms
* *
@ -1139,6 +1148,7 @@ class Net_SSH2
4 => 'NET_SSH2_MSG_DEBUG', 4 => 'NET_SSH2_MSG_DEBUG',
5 => 'NET_SSH2_MSG_SERVICE_REQUEST', 5 => 'NET_SSH2_MSG_SERVICE_REQUEST',
6 => 'NET_SSH2_MSG_SERVICE_ACCEPT', 6 => 'NET_SSH2_MSG_SERVICE_ACCEPT',
7 => 'NET_SSH2_MSG_EXT_INFO', // RFC 8308
20 => 'NET_SSH2_MSG_KEXINIT', 20 => 'NET_SSH2_MSG_KEXINIT',
21 => 'NET_SSH2_MSG_NEWKEYS', 21 => 'NET_SSH2_MSG_NEWKEYS',
30 => 'NET_SSH2_MSG_KEXDH_INIT', 30 => 'NET_SSH2_MSG_KEXDH_INIT',
@ -1511,6 +1521,8 @@ class Net_SSH2
$preferred['client_to_server']['comp'] : $preferred['client_to_server']['comp'] :
$this->getSupportedCompressionAlgorithms(); $this->getSupportedCompressionAlgorithms();
$kex_algorithms = array_merge($kex_algorithms, array('ext-info-c'));
// some SSH servers have buggy implementations of some of the above algorithms // some SSH servers have buggy implementations of some of the above algorithms
switch (true) { switch (true) {
case $this->server_identifier == 'SSH-2.0-SSHD': case $this->server_identifier == 'SSH-2.0-SSHD':
@ -2418,6 +2430,35 @@ class Net_SSH2
} }
extract(unpack('Ctype', $this->_string_shift($response, 1))); extract(unpack('Ctype', $this->_string_shift($response, 1)));
if ($type == NET_SSH2_MSG_EXT_INFO) {
if (strlen($response) < 4) {
return false;
}
$nr_extensions = unpack('Nlength', $this->_string_shift($response, 4));
for ($i = 0; $i < $nr_extensions['length']; $i++) {
if (strlen($response) < 4) {
return false;
}
$temp = unpack('Nlength', $this->_string_shift($response, 4));
$extension_name = $this->_string_shift($response, $temp['length']);
if ($extension_name == 'server-sig-algs') {
if (strlen($response) < 4) {
return false;
}
$temp = unpack('Nlength', $this->_string_shift($response, 4));
$this->server_sig_algs = explode(',', $this->_string_shift($response, $temp['length']));
}
}
$response = $this->_get_binary_packet();
if ($response === false) {
$this->bitmap = 0;
user_error('Connection closed by server');
return false;
}
extract(unpack('Ctype', $this->_string_shift($response, 1)));
}
if ($type != NET_SSH2_MSG_SERVICE_ACCEPT) { if ($type != NET_SSH2_MSG_SERVICE_ACCEPT) {
user_error('Expected SSH_MSG_SERVICE_ACCEPT'); user_error('Expected SSH_MSG_SERVICE_ACCEPT');
return false; return false;
@ -2788,7 +2829,9 @@ class Net_SSH2
); );
$algos = array('rsa-sha2-256', 'rsa-sha2-512', 'ssh-rsa'); $algos = array('rsa-sha2-256', 'rsa-sha2-512', 'ssh-rsa');
if (isset($this->preferred['hostkey'])) { if ($this->server_sig_algs) {
$algos = array_intersect($this->server_sig_algs, $algos);
} elseif (isset($this->preferred['hostkey'])) {
$algos = array_intersect($this->preferred['hostkey'], $algos); $algos = array_intersect($this->preferred['hostkey'], $algos);
} }
$algo = $this->_array_intersect_first($algos, $this->supported_private_key_algorithms); $algo = $this->_array_intersect_first($algos, $this->supported_private_key_algorithms);