* @version 0.1.0
* @access public
- * @package Net_SSH1
*/
-class Net_SSH1 {
+class Net_SSH1
+{
/**
* The SSH identifier
*
@@ -429,11 +429,35 @@ class Net_SSH1 {
/**
* Current Timeout
*
- * @see Net_SSH2::_get_channel_packet()
+ * @see Net_SSH1::_get_channel_packet()
* @access private
*/
var $curTimeout;
+ /**
+ * Log Boundary
+ *
+ * @see Net_SSH1::_format_log
+ * @access private
+ */
+ var $log_boundary = ':';
+
+ /**
+ * Log Long Width
+ *
+ * @see Net_SSH1::_format_log
+ * @access private
+ */
+ var $log_long_width = 65;
+
+ /**
+ * Log Short Width
+ *
+ * @see Net_SSH1::_format_log
+ * @access private
+ */
+ var $log_short_width = 16;
+
/**
* Default Constructor.
*
@@ -449,16 +473,16 @@ class Net_SSH1 {
function Net_SSH1($host, $port = 22, $timeout = 10, $cipher = NET_SSH1_CIPHER_3DES)
{
if (!class_exists('Math_BigInteger')) {
- require_once('Math/BigInteger.php');
+ include_once 'Math/BigInteger.php';
}
// Include Crypt_Random
// the class_exists() will only be called if the crypt_random_string function hasn't been defined and
// will trigger a call to __autoload() if you're wanting to auto-load classes
- // call function_exists() a second time to stop the require_once from being called outside
+ // call function_exists() a second time to stop the include_once from being called outside
// of the auto loader
if (!function_exists('crypt_random_string') && !class_exists('Crypt_Random') && !function_exists('crypt_random_string')) {
- require_once('Crypt/Random.php');
+ include_once 'Crypt/Random.php';
}
$this->protocol_flags = array(
@@ -603,7 +627,7 @@ class Net_SSH1 {
// break;
case NET_SSH1_CIPHER_DES:
if (!class_exists('Crypt_DES')) {
- require_once('Crypt/DES.php');
+ include_once 'Crypt/DES.php';
}
$this->crypto = new Crypt_DES();
$this->crypto->disablePadding();
@@ -612,7 +636,7 @@ class Net_SSH1 {
break;
case NET_SSH1_CIPHER_3DES:
if (!class_exists('Crypt_TripleDES')) {
- require_once('Crypt/TripleDES.php');
+ include_once 'Crypt/TripleDES.php';
}
$this->crypto = new Crypt_TripleDES(CRYPT_DES_MODE_3CBC);
$this->crypto->disablePadding();
@@ -621,7 +645,7 @@ class Net_SSH1 {
break;
//case NET_SSH1_CIPHER_RC4:
// if (!class_exists('Crypt_RC4')) {
- // require_once('Crypt/RC4.php');
+ // include_once('Crypt/RC4.php');
// }
// $this->crypto = new Crypt_RC4();
// $this->crypto->enableContinuousBuffer();
@@ -1017,7 +1041,7 @@ class Net_SSH1 {
if ($this->curTimeout) {
$read = array($this->fsock);
- $write = $except = NULL;
+ $write = $except = null;
$start = strtok(microtime(), ' ') + strtok(''); // http://php.net/microtime#61838
$sec = floor($this->curTimeout);
@@ -1253,7 +1277,7 @@ class Net_SSH1 {
{
/*
if (!class_exists('Crypt_RSA')) {
- require_once('Crypt/RSA.php');
+ include_once 'Crypt/RSA.php';
}
$rsa = new Crypt_RSA();
@@ -1318,7 +1342,7 @@ class Net_SSH1 {
/**
* Returns a log of the packets that have been sent and received.
*
- * Returns a string if NET_SSH2_LOGGING == NET_SSH2_LOG_COMPLEX, an array if NET_SSH2_LOGGING == NET_SSH2_LOG_SIMPLE and false if !defined('NET_SSH2_LOGGING')
+ * Returns a string if NET_SSH1_LOGGING == NET_SSH1_LOG_COMPLEX, an array if NET_SSH1_LOGGING == NET_SSH1_LOG_SIMPLE and false if !defined('NET_SSH1_LOGGING')
*
* @access public
* @return String or Array
@@ -1351,8 +1375,6 @@ class Net_SSH1 {
*/
function _format_log($message_log, $message_number_log)
{
- static $boundary = ':', $long_width = 65, $short_width = 16;
-
$output = '';
for ($i = 0; $i < count($message_log); $i++) {
$output.= $message_number_log[$i] . "\r\n";
@@ -1362,19 +1384,13 @@ class Net_SSH1 {
if (strlen($current_log)) {
$output.= str_pad(dechex($j), 7, '0', STR_PAD_LEFT) . '0 ';
}
- $fragment = $this->_string_shift($current_log, $short_width);
- $hex = substr(
- preg_replace(
- '#(.)#es',
- '"' . $boundary . '" . str_pad(dechex(ord(substr("\\1", -1))), 2, "0", STR_PAD_LEFT)',
- $fragment),
- strlen($boundary)
- );
+ $fragment = $this->_string_shift($current_log, $this->log_short_width);
+ $hex = substr(preg_replace_callback('#.#s', array($this, '_format_log_helper'), $fragment), strlen($this->log_boundary));
// replace non ASCII printable characters with dots
// http://en.wikipedia.org/wiki/ASCII#ASCII_printable_characters
// also replace < with a . since < messes up the output on web browsers
$raw = preg_replace('#[^\x20-\x7E]|<#', '.', $fragment);
- $output.= str_pad($hex, $long_width - $short_width, ' ') . $raw . "\r\n";
+ $output.= str_pad($hex, $this->log_long_width - $this->log_short_width, ' ') . $raw . "\r\n";
$j++;
} while (strlen($current_log));
$output.= "\r\n";
@@ -1383,6 +1399,20 @@ class Net_SSH1 {
return $output;
}
+ /**
+ * Helper function for _format_log
+ *
+ * For use with preg_replace_callback()
+ *
+ * @param Array $matches
+ * @access private
+ * @return String
+ */
+ function _format_log_helper($matches)
+ {
+ return $this->log_boundary . str_pad(dechex(ord($matches[0])), 2, '0', STR_PAD_LEFT);
+ }
+
/**
* Return the server key public exponent
*
@@ -1496,57 +1526,57 @@ class Net_SSH1 {
*/
function _append_log($protocol_flags, $message)
{
- switch (NET_SSH1_LOGGING) {
- // useful for benchmarks
- case NET_SSH1_LOG_SIMPLE:
- $this->protocol_flags_log[] = $protocol_flags;
- break;
- // the most useful log for SSH1
- case NET_SSH1_LOG_COMPLEX:
- $this->protocol_flags_log[] = $protocol_flags;
- $this->_string_shift($message);
- $this->log_size+= strlen($message);
- $this->message_log[] = $message;
- while ($this->log_size > NET_SSH2_LOG_MAX_SIZE) {
- $this->log_size-= strlen(array_shift($this->message_log));
- array_shift($this->protocol_flags_log);
- }
- break;
- // dump the output out realtime; packets may be interspersed with non packets,
- // passwords won't be filtered out and select other packets may not be correctly
- // identified
- case NET_SSH1_LOG_REALTIME:
- echo "\r\n" . $this->_format_log(array($message), array($protocol_flags)) . "\r\n
\r\n";
- @flush();
- @ob_flush();
+ switch (NET_SSH1_LOGGING) {
+ // useful for benchmarks
+ case NET_SSH1_LOG_SIMPLE:
+ $this->protocol_flags_log[] = $protocol_flags;
+ break;
+ // the most useful log for SSH1
+ case NET_SSH1_LOG_COMPLEX:
+ $this->protocol_flags_log[] = $protocol_flags;
+ $this->_string_shift($message);
+ $this->log_size+= strlen($message);
+ $this->message_log[] = $message;
+ while ($this->log_size > NET_SSH1_LOG_MAX_SIZE) {
+ $this->log_size-= strlen(array_shift($this->message_log));
+ array_shift($this->protocol_flags_log);
+ }
+ break;
+ // dump the output out realtime; packets may be interspersed with non packets,
+ // passwords won't be filtered out and select other packets may not be correctly
+ // identified
+ case NET_SSH1_LOG_REALTIME:
+ echo "\r\n" . $this->_format_log(array($message), array($protocol_flags)) . "\r\n
\r\n";
+ @flush();
+ @ob_flush();
+ break;
+ // basically the same thing as NET_SSH1_LOG_REALTIME with the caveat that NET_SSH1_LOG_REALTIME_FILE
+ // needs to be defined and that the resultant log file will be capped out at NET_SSH1_LOG_MAX_SIZE.
+ // the earliest part of the log file is denoted by the first <<< START >>> and is not going to necessarily
+ // at the beginning of the file
+ case NET_SSH1_LOG_REALTIME_FILE:
+ if (!isset($this->realtime_log_file)) {
+ // PHP doesn't seem to like using constants in fopen()
+ $filename = NET_SSH1_LOG_REALTIME_FILE;
+ $fp = fopen($filename, 'w');
+ $this->realtime_log_file = $fp;
+ }
+ if (!is_resource($this->realtime_log_file)) {
break;
- // basically the same thing as NET_SSH1_LOG_REALTIME with the caveat that NET_SSH1_LOG_REALTIME_FILE
- // needs to be defined and that the resultant log file will be capped out at NET_SSH1_LOG_MAX_SIZE.
- // the earliest part of the log file is denoted by the first <<< START >>> and is not going to necessarily
- // at the beginning of the file
- case NET_SSH1_LOG_REALTIME_FILE:
- if (!isset($this->realtime_log_file)) {
- // PHP doesn't seem to like using constants in fopen()
- $filename = NET_SSH2_LOG_REALTIME_FILE;
- $fp = fopen($filename, 'w');
- $this->realtime_log_file = $fp;
- }
- if (!is_resource($this->realtime_log_file)) {
- break;
- }
- $entry = $this->_format_log(array($message), array($protocol_flags));
- if ($this->realtime_log_wrap) {
- $temp = "<<< START >>>\r\n";
- $entry.= $temp;
- fseek($this->realtime_log_file, ftell($this->realtime_log_file) - strlen($temp));
- }
- $this->realtime_log_size+= strlen($entry);
- if ($this->realtime_log_size > NET_SSH1_LOG_MAX_SIZE) {
- fseek($this->realtime_log_file, 0);
- $this->realtime_log_size = strlen($entry);
- $this->realtime_log_wrap = true;
- }
- fputs($this->realtime_log_file, $entry);
- }
+ }
+ $entry = $this->_format_log(array($message), array($protocol_flags));
+ if ($this->realtime_log_wrap) {
+ $temp = "<<< START >>>\r\n";
+ $entry.= $temp;
+ fseek($this->realtime_log_file, ftell($this->realtime_log_file) - strlen($temp));
+ }
+ $this->realtime_log_size+= strlen($entry);
+ if ($this->realtime_log_size > NET_SSH1_LOG_MAX_SIZE) {
+ fseek($this->realtime_log_file, 0);
+ $this->realtime_log_size = strlen($entry);
+ $this->realtime_log_wrap = true;
+ }
+ fputs($this->realtime_log_file, $entry);
+ }
}
}
diff --git a/apps/files_external/3rdparty/phpseclib/phpseclib/Net/SSH2.php b/apps/files_external/3rdparty/phpseclib/phpseclib/Net/SSH2.php
index dad03697233..2fddb68a9b2 100644
--- a/apps/files_external/3rdparty/phpseclib/phpseclib/Net/SSH2.php
+++ b/apps/files_external/3rdparty/phpseclib/phpseclib/Net/SSH2.php
@@ -1,5 +1,4 @@
- * @copyright MMVII Jim Wigginton
- * @license http://www.opensource.org/licenses/mit-license.html MIT License
- * @link http://phpseclib.sourceforge.net
+ * @category Net
+ * @package Net_SSH2
+ * @author Jim Wigginton
+ * @copyright MMVII Jim Wigginton
+ * @license http://www.opensource.org/licenses/mit-license.html MIT License
+ * @link http://phpseclib.sourceforge.net
*/
/**#@+
@@ -144,19 +143,20 @@ define('NET_SSH2_LOG_MAX_SIZE', 1024 * 1024);
/**
* Pure-PHP implementation of SSHv2.
*
+ * @package Net_SSH2
* @author Jim Wigginton
* @version 0.1.0
* @access public
- * @package Net_SSH2
*/
-class Net_SSH2 {
+class Net_SSH2
+{
/**
* The SSH identifier
*
* @var String
* @access private
*/
- var $identifier = 'SSH-2.0-phpseclib_0.3';
+ var $identifier;
/**
* The Socket Object
@@ -747,6 +747,30 @@ class Net_SSH2 {
*/
var $is_timeout = false;
+ /**
+ * Log Boundary
+ *
+ * @see Net_SSH2::_format_log
+ * @access private
+ */
+ var $log_boundary = ':';
+
+ /**
+ * Log Long Width
+ *
+ * @see Net_SSH2::_format_log
+ * @access private
+ */
+ var $log_long_width = 65;
+
+ /**
+ * Log Short Width
+ *
+ * @see Net_SSH2::_format_log
+ * @access private
+ */
+ var $log_short_width = 16;
+
/**
* Default Constructor.
*
@@ -763,15 +787,15 @@ class Net_SSH2 {
// Include Math_BigInteger
// Used to do Diffie-Hellman key exchange and DSA/RSA signature verification.
if (!class_exists('Math_BigInteger')) {
- require_once('Math/BigInteger.php');
+ include_once 'Math/BigInteger.php';
}
if (!function_exists('crypt_random_string')) {
- require_once('Crypt/Random.php');
+ include_once 'Crypt/Random.php';
}
if (!class_exists('Crypt_Hash')) {
- require_once('Crypt/Hash.php');
+ include_once 'Crypt/Hash.php';
}
$this->last_packet = strtok(microtime(), ' ') + strtok(''); // == microtime(true) in PHP5
@@ -861,7 +885,7 @@ class Net_SSH2 {
}
$read = array($this->fsock);
- $write = $except = NULL;
+ $write = $except = null;
$sec = floor($timeout);
$usec = 1000000 * ($timeout - $sec);
@@ -895,19 +919,7 @@ class Net_SSH2 {
return false;
}
- $ext = array();
- if (extension_loaded('mcrypt')) {
- $ext[] = 'mcrypt';
- }
- if (extension_loaded('gmp')) {
- $ext[] = 'gmp';
- } else if (extension_loaded('bcmath')) {
- $ext[] = 'bcmath';
- }
-
- if (!empty($ext)) {
- $this->identifier.= ' (' . implode(', ', $ext) . ')';
- }
+ $this->identifier = $this->_generate_identifier();
if (defined('NET_SSH2_LOGGING')) {
$this->_append_log('<-', $extra . $temp);
@@ -944,6 +956,36 @@ class Net_SSH2 {
$this->bitmap = NET_SSH2_MASK_CONSTRUCTOR;
}
+ /**
+ * Generates the SSH identifier
+ *
+ * You should overwrite this method in your own class if you want to use another identifier
+ *
+ * @access protected
+ * @return String
+ */
+ function _generate_identifier()
+ {
+ $identifier = 'SSH-2.0-phpseclib_0.3';
+
+ $ext = array();
+ if (extension_loaded('mcrypt')) {
+ $ext[] = 'mcrypt';
+ }
+
+ if (extension_loaded('gmp')) {
+ $ext[] = 'gmp';
+ } elseif (extension_loaded('bcmath')) {
+ $ext[] = 'bcmath';
+ }
+
+ if (!empty($ext)) {
+ $identifier .= ' (' . implode(', ', $ext) . ')';
+ }
+
+ return $identifier;
+ }
+
/**
* Key Exchange
*
@@ -1223,23 +1265,23 @@ class Net_SSH2 {
}
switch ($kex_algorithms[$i]) {
- // see http://tools.ietf.org/html/rfc2409#section-6.2 and
+ // see http://tools.ietf.org/html/rfc2409#section-6.2 and
// http://tools.ietf.org/html/rfc2412, appendex E
case 'diffie-hellman-group1-sha1':
- $prime = 'FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74' .
- '020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F1437' .
- '4FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED' .
+ $prime = 'FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74' .
+ '020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F1437' .
+ '4FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED' .
'EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE65381FFFFFFFFFFFFFFFF';
break;
// see http://tools.ietf.org/html/rfc3526#section-3
case 'diffie-hellman-group14-sha1':
- $prime = 'FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74' .
- '020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F1437' .
- '4FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED' .
- 'EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF05' .
- '98DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB' .
- '9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B' .
- 'E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF695581718' .
+ $prime = 'FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E088A67CC74' .
+ '020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B302B0A6DF25F1437' .
+ '4FE1356D6D51C245E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED' .
+ 'EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3DC2007CB8A163BF05' .
+ '98DA48361C55D39A69163FA8FD24CF5F83655D23DCA3AD961C62F356208552BB' .
+ '9ED529077096966D670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B' .
+ 'E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF695581718' .
'3995497CEA956AE515D2261898FA051015728E5A8AACAA68FFFFFFFFFFFFFFFF';
break;
}
@@ -1260,7 +1302,8 @@ class Net_SSH2 {
-- http://tools.ietf.org/html/rfc4419#section-6.2 */
$one = new Math_BigInteger(1);
$keyLength = min($keyLength, $kexHash->getLength());
- $max = $one->bitwise_leftShift(16 * $keyLength)->subtract($one); // 2 * 8 * $keyLength
+ $max = $one->bitwise_leftShift(16 * $keyLength); // 2 * 8 * $keyLength
+ $max = $max->subtract($one);
$x = $one->random($one, $max);
$e = $g->modPow($x, $prime);
@@ -1353,14 +1396,14 @@ class Net_SSH2 {
switch ($encrypt) {
case '3des-cbc':
if (!class_exists('Crypt_TripleDES')) {
- require_once('Crypt/TripleDES.php');
+ include_once 'Crypt/TripleDES.php';
}
$this->encrypt = new Crypt_TripleDES();
// $this->encrypt_block_size = 64 / 8 == the default
break;
case '3des-ctr':
if (!class_exists('Crypt_TripleDES')) {
- require_once('Crypt/TripleDES.php');
+ include_once 'Crypt/TripleDES.php';
}
$this->encrypt = new Crypt_TripleDES(CRYPT_DES_MODE_CTR);
// $this->encrypt_block_size = 64 / 8 == the default
@@ -1369,7 +1412,7 @@ class Net_SSH2 {
case 'aes192-cbc':
case 'aes128-cbc':
if (!class_exists('Crypt_Rijndael')) {
- require_once('Crypt/Rijndael.php');
+ include_once 'Crypt/Rijndael.php';
}
$this->encrypt = new Crypt_Rijndael();
$this->encrypt_block_size = 16; // eg. 128 / 8
@@ -1378,21 +1421,21 @@ class Net_SSH2 {
case 'aes192-ctr':
case 'aes128-ctr':
if (!class_exists('Crypt_Rijndael')) {
- require_once('Crypt/Rijndael.php');
+ include_once 'Crypt/Rijndael.php';
}
$this->encrypt = new Crypt_Rijndael(CRYPT_RIJNDAEL_MODE_CTR);
$this->encrypt_block_size = 16; // eg. 128 / 8
break;
case 'blowfish-cbc':
if (!class_exists('Crypt_Blowfish')) {
- require_once('Crypt/Blowfish.php');
+ include_once 'Crypt/Blowfish.php';
}
$this->encrypt = new Crypt_Blowfish();
$this->encrypt_block_size = 8;
break;
case 'blowfish-ctr':
if (!class_exists('Crypt_Blowfish')) {
- require_once('Crypt/Blowfish.php');
+ include_once 'Crypt/Blowfish.php';
}
$this->encrypt = new Crypt_Blowfish(CRYPT_BLOWFISH_MODE_CTR);
$this->encrypt_block_size = 8;
@@ -1402,7 +1445,7 @@ class Net_SSH2 {
case 'twofish256-cbc':
case 'twofish-cbc':
if (!class_exists('Crypt_Twofish')) {
- require_once('Crypt/Twofish.php');
+ include_once 'Crypt/Twofish.php';
}
$this->encrypt = new Crypt_Twofish();
$this->encrypt_block_size = 16;
@@ -1411,7 +1454,7 @@ class Net_SSH2 {
case 'twofish192-ctr':
case 'twofish256-ctr':
if (!class_exists('Crypt_Twofish')) {
- require_once('Crypt/Twofish.php');
+ include_once 'Crypt/Twofish.php';
}
$this->encrypt = new Crypt_Twofish(CRYPT_TWOFISH_MODE_CTR);
$this->encrypt_block_size = 16;
@@ -1420,7 +1463,7 @@ class Net_SSH2 {
case 'arcfour128':
case 'arcfour256':
if (!class_exists('Crypt_RC4')) {
- require_once('Crypt/RC4.php');
+ include_once 'Crypt/RC4.php';
}
$this->encrypt = new Crypt_RC4();
break;
@@ -1431,13 +1474,13 @@ class Net_SSH2 {
switch ($decrypt) {
case '3des-cbc':
if (!class_exists('Crypt_TripleDES')) {
- require_once('Crypt/TripleDES.php');
+ include_once 'Crypt/TripleDES.php';
}
$this->decrypt = new Crypt_TripleDES();
break;
case '3des-ctr':
if (!class_exists('Crypt_TripleDES')) {
- require_once('Crypt/TripleDES.php');
+ include_once 'Crypt/TripleDES.php';
}
$this->decrypt = new Crypt_TripleDES(CRYPT_DES_MODE_CTR);
break;
@@ -1445,7 +1488,7 @@ class Net_SSH2 {
case 'aes192-cbc':
case 'aes128-cbc':
if (!class_exists('Crypt_Rijndael')) {
- require_once('Crypt/Rijndael.php');
+ include_once 'Crypt/Rijndael.php';
}
$this->decrypt = new Crypt_Rijndael();
$this->decrypt_block_size = 16;
@@ -1454,21 +1497,21 @@ class Net_SSH2 {
case 'aes192-ctr':
case 'aes128-ctr':
if (!class_exists('Crypt_Rijndael')) {
- require_once('Crypt/Rijndael.php');
+ include_once 'Crypt/Rijndael.php';
}
$this->decrypt = new Crypt_Rijndael(CRYPT_RIJNDAEL_MODE_CTR);
$this->decrypt_block_size = 16;
break;
case 'blowfish-cbc':
if (!class_exists('Crypt_Blowfish')) {
- require_once('Crypt/Blowfish.php');
+ include_once 'Crypt/Blowfish.php';
}
$this->decrypt = new Crypt_Blowfish();
$this->decrypt_block_size = 8;
break;
case 'blowfish-ctr':
if (!class_exists('Crypt_Blowfish')) {
- require_once('Crypt/Blowfish.php');
+ include_once 'Crypt/Blowfish.php';
}
$this->decrypt = new Crypt_Blowfish(CRYPT_BLOWFISH_MODE_CTR);
$this->decrypt_block_size = 8;
@@ -1478,7 +1521,7 @@ class Net_SSH2 {
case 'twofish256-cbc':
case 'twofish-cbc':
if (!class_exists('Crypt_Twofish')) {
- require_once('Crypt/Twofish.php');
+ include_once 'Crypt/Twofish.php';
}
$this->decrypt = new Crypt_Twofish();
$this->decrypt_block_size = 16;
@@ -1487,7 +1530,7 @@ class Net_SSH2 {
case 'twofish192-ctr':
case 'twofish256-ctr':
if (!class_exists('Crypt_Twofish')) {
- require_once('Crypt/Twofish.php');
+ include_once 'Crypt/Twofish.php';
}
$this->decrypt = new Crypt_Twofish(CRYPT_TWOFISH_MODE_CTR);
$this->decrypt_block_size = 16;
@@ -1496,7 +1539,7 @@ class Net_SSH2 {
case 'arcfour128':
case 'arcfour256':
if (!class_exists('Crypt_RC4')) {
- require_once('Crypt/RC4.php');
+ include_once 'Crypt/RC4.php';
}
$this->decrypt = new Crypt_RC4();
break;
@@ -1647,10 +1690,26 @@ class Net_SSH2 {
* @param Mixed $password
* @param Mixed $...
* @return Boolean
- * @see _login_helper
+ * @see _login
* @access public
*/
function login($username)
+ {
+ $args = func_get_args();
+ return call_user_func_array(array(&$this, '_login'), $args);
+ }
+
+ /**
+ * Login Helper
+ *
+ * @param String $username
+ * @param Mixed $password
+ * @param Mixed $...
+ * @return Boolean
+ * @see _login_helper
+ * @access private
+ */
+ function _login($username)
{
$args = array_slice(func_get_args(), 1);
if (empty($args)) {
@@ -1710,8 +1769,13 @@ class Net_SSH2 {
}
// although PHP5's get_class() preserves the case, PHP4's does not
- if (is_object($password) && strtolower(get_class($password)) == 'crypt_rsa') {
- return $this->_privatekey_login($username, $password);
+ if (is_object($password)) {
+ switch (strtolower(get_class($password))) {
+ case 'crypt_rsa':
+ return $this->_privatekey_login($username, $password);
+ case 'system_ssh_agent':
+ return $this->_ssh_agent_login($username, $password);
+ }
}
if (is_array($password)) {
@@ -1757,7 +1821,7 @@ class Net_SSH2 {
// remove the username and password from the logged packet
if (!defined('NET_SSH2_LOGGING')) {
- $logged = NULL;
+ $logged = null;
} else {
$logged = pack('CNa*Na*Na*CNa*',
NET_SSH2_MSG_USERAUTH_REQUEST, strlen('username'), 'username', strlen('ssh-connection'), 'ssh-connection',
@@ -1821,7 +1885,7 @@ class Net_SSH2 {
*/
function _keyboard_interactive_login($username, $password)
{
- $packet = pack('CNa*Na*Na*Na*Na*',
+ $packet = pack('CNa*Na*Na*Na*Na*',
NET_SSH2_MSG_USERAUTH_REQUEST, strlen($username), $username, strlen('ssh-connection'), 'ssh-connection',
strlen('keyboard-interactive'), 'keyboard-interactive', 0, '', 0, ''
);
@@ -1948,6 +2012,26 @@ class Net_SSH2 {
return false;
}
+ /**
+ * Login with an ssh-agent provided key
+ *
+ * @param String $username
+ * @param System_SSH_Agent $agent
+ * @return Boolean
+ * @access private
+ */
+ function _ssh_agent_login($username, $agent)
+ {
+ $keys = $agent->requestIdentities();
+ foreach ($keys as $key) {
+ if ($this->_privatekey_login($username, $key)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
/**
* Login with an RSA private key
*
@@ -2056,7 +2140,7 @@ class Net_SSH2 {
/**
* Get the output from stdError
- *
+ *
* @access public
*/
function getStdError()
@@ -2075,7 +2159,7 @@ class Net_SSH2 {
* @return String
* @access public
*/
- function exec($command, $callback = NULL)
+ function exec($command, $callback = null)
{
$this->curTimeout = $this->timeout;
$this->is_timeout = false;
@@ -2086,7 +2170,7 @@ class Net_SSH2 {
}
// RFC4254 defines the (client) window size as "bytes the other party can send before it must wait for the window to
- // be adjusted". 0x7FFFFFFF is, at 2GB, the max size. technically, it should probably be decremented, but,
+ // be adjusted". 0x7FFFFFFF is, at 2GB, the max size. technically, it should probably be decremented, but,
// honestly, if you're transfering more than 2GB, you probably shouldn't be using phpseclib, anyway.
// see http://tools.ietf.org/html/rfc4254#section-5.2 for more info
$this->window_size_server_to_client[NET_SSH2_CHANNEL_EXEC] = 0x7FFFFFFF;
@@ -2143,7 +2227,7 @@ class Net_SSH2 {
// neither will your script.
// although, in theory, the size of SSH_MSG_CHANNEL_REQUEST could exceed the maximum packet size established by
- // SSH_MSG_CHANNEL_OPEN_CONFIRMATION, RFC4254#section-5.1 states that the "maximum packet size" refers to the
+ // SSH_MSG_CHANNEL_OPEN_CONFIRMATION, RFC4254#section-5.1 states that the "maximum packet size" refers to the
// "maximum size of an individual data packet". ie. SSH_MSG_CHANNEL_DATA. RFC4254#section-5.2 corroborates.
$packet = pack('CNNa*CNa*',
NET_SSH2_MSG_CHANNEL_REQUEST, $this->server_channels[NET_SSH2_CHANNEL_EXEC], strlen('exec'), 'exec', 1, strlen($command), $command);
@@ -2349,7 +2433,6 @@ class Net_SSH2 {
return false;
}
- $channel = $this->in_request_pty_exec ? NET_SSH2_CHANNEL_EXEC : NET_SSH2_CHANNEL_SHELL;
return $this->_send_channel_packet($this->_get_interactive_channel(), $cmd);
}
@@ -2430,8 +2513,7 @@ class Net_SSH2 {
*/
function reset()
{
- $channel = $this->in_request_pty_exec ? NET_SSH2_CHANNEL_EXEC : NET_SSH2_CHANNEL_SHELL;
- $this->_close_channel($channel);
+ $this->_close_channel($this->_get_interactive_channel());
}
/**
@@ -2724,7 +2806,7 @@ class Net_SSH2 {
}
$read = array($this->fsock);
- $write = $except = NULL;
+ $write = $except = null;
$start = strtok(microtime(), ' ') + strtok(''); // http://php.net/microtime#61838
$sec = floor($this->curTimeout);
@@ -2801,7 +2883,7 @@ class Net_SSH2 {
/*
if ($channel == NET_SSH2_CHANNEL_EXEC) {
// SCP requires null packets, such as this, be sent. further, in the case of the ssh.com SSH server
- // this actually seems to make things twice as fast. more to the point, the message right after
+ // this actually seems to make things twice as fast. more to the point, the message right after
// SSH_MSG_CHANNEL_DATA (usually SSH_MSG_IGNORE) won't block for as long as it would have otherwise.
// in OpenSSH it slows things down but only by a couple thousandths of a second.
$this->_send_channel_packet($channel, chr(0));
@@ -2861,12 +2943,9 @@ class Net_SSH2 {
case 'exit-status':
extract(unpack('Cfalse/Nexit_status', $this->_string_shift($response, 5)));
$this->exit_status = $exit_status;
- // "The channel needs to be closed with SSH_MSG_CHANNEL_CLOSE after this message."
- // -- http://tools.ietf.org/html/rfc4254#section-6.10
- $this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_EOF, $this->server_channels[$client_channel]));
- $this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_CLOSE, $this->server_channels[$channel]));
- $this->channel_status[$channel] = NET_SSH2_MSG_CHANNEL_EOF;
+ // "The client MAY ignore these messages."
+ // -- http://tools.ietf.org/html/rfc4254#section-6.10
break;
default:
@@ -2907,7 +2986,7 @@ class Net_SSH2 {
* @return Boolean
* @access private
*/
- function _send_binary_packet($data, $logged = NULL)
+ function _send_binary_packet($data, $logged = null)
{
if (!is_resource($this->fsock) || feof($this->fsock)) {
user_error('Connection closed prematurely');
@@ -2967,70 +3046,70 @@ class Net_SSH2 {
*/
function _append_log($message_number, $message)
{
- // remove the byte identifying the message type from all but the first two messages (ie. the identification strings)
- if (strlen($message_number) > 2) {
- $this->_string_shift($message);
- }
+ // remove the byte identifying the message type from all but the first two messages (ie. the identification strings)
+ if (strlen($message_number) > 2) {
+ $this->_string_shift($message);
+ }
- switch (NET_SSH2_LOGGING) {
- // useful for benchmarks
- case NET_SSH2_LOG_SIMPLE:
- $this->message_number_log[] = $message_number;
- break;
- // the most useful log for SSH2
- case NET_SSH2_LOG_COMPLEX:
- $this->message_number_log[] = $message_number;
- $this->log_size+= strlen($message);
- $this->message_log[] = $message;
- while ($this->log_size > NET_SSH2_LOG_MAX_SIZE) {
- $this->log_size-= strlen(array_shift($this->message_log));
- array_shift($this->message_number_log);
- }
- break;
- // dump the output out realtime; packets may be interspersed with non packets,
- // passwords won't be filtered out and select other packets may not be correctly
- // identified
- case NET_SSH2_LOG_REALTIME:
- switch (PHP_SAPI) {
- case 'cli':
- $start = $stop = "\r\n";
- break;
- default:
- $start = '';
- $stop = '
';
- }
- echo $start . $this->_format_log(array($message), array($message_number)) . $stop;
- @flush();
- @ob_flush();
- break;
- // basically the same thing as NET_SSH2_LOG_REALTIME with the caveat that NET_SSH2_LOG_REALTIME_FILE
- // needs to be defined and that the resultant log file will be capped out at NET_SSH2_LOG_MAX_SIZE.
- // the earliest part of the log file is denoted by the first <<< START >>> and is not going to necessarily
- // at the beginning of the file
- case NET_SSH2_LOG_REALTIME_FILE:
- if (!isset($this->realtime_log_file)) {
- // PHP doesn't seem to like using constants in fopen()
- $filename = NET_SSH2_LOG_REALTIME_FILENAME;
- $fp = fopen($filename, 'w');
- $this->realtime_log_file = $fp;
- }
- if (!is_resource($this->realtime_log_file)) {
+ switch (NET_SSH2_LOGGING) {
+ // useful for benchmarks
+ case NET_SSH2_LOG_SIMPLE:
+ $this->message_number_log[] = $message_number;
+ break;
+ // the most useful log for SSH2
+ case NET_SSH2_LOG_COMPLEX:
+ $this->message_number_log[] = $message_number;
+ $this->log_size+= strlen($message);
+ $this->message_log[] = $message;
+ while ($this->log_size > NET_SSH2_LOG_MAX_SIZE) {
+ $this->log_size-= strlen(array_shift($this->message_log));
+ array_shift($this->message_number_log);
+ }
+ break;
+ // dump the output out realtime; packets may be interspersed with non packets,
+ // passwords won't be filtered out and select other packets may not be correctly
+ // identified
+ case NET_SSH2_LOG_REALTIME:
+ switch (PHP_SAPI) {
+ case 'cli':
+ $start = $stop = "\r\n";
break;
- }
- $entry = $this->_format_log(array($message), array($message_number));
- if ($this->realtime_log_wrap) {
- $temp = "<<< START >>>\r\n";
- $entry.= $temp;
- fseek($this->realtime_log_file, ftell($this->realtime_log_file) - strlen($temp));
- }
- $this->realtime_log_size+= strlen($entry);
- if ($this->realtime_log_size > NET_SSH2_LOG_MAX_SIZE) {
- fseek($this->realtime_log_file, 0);
- $this->realtime_log_size = strlen($entry);
- $this->realtime_log_wrap = true;
- }
- fputs($this->realtime_log_file, $entry);
- }
+ default:
+ $start = '';
+ $stop = '
';
+ }
+ echo $start . $this->_format_log(array($message), array($message_number)) . $stop;
+ @flush();
+ @ob_flush();
+ break;
+ // basically the same thing as NET_SSH2_LOG_REALTIME with the caveat that NET_SSH2_LOG_REALTIME_FILE
+ // needs to be defined and that the resultant log file will be capped out at NET_SSH2_LOG_MAX_SIZE.
+ // the earliest part of the log file is denoted by the first <<< START >>> and is not going to necessarily
+ // at the beginning of the file
+ case NET_SSH2_LOG_REALTIME_FILE:
+ if (!isset($this->realtime_log_file)) {
+ // PHP doesn't seem to like using constants in fopen()
+ $filename = NET_SSH2_LOG_REALTIME_FILENAME;
+ $fp = fopen($filename, 'w');
+ $this->realtime_log_file = $fp;
+ }
+ if (!is_resource($this->realtime_log_file)) {
+ break;
+ }
+ $entry = $this->_format_log(array($message), array($message_number));
+ if ($this->realtime_log_wrap) {
+ $temp = "<<< START >>>\r\n";
+ $entry.= $temp;
+ fseek($this->realtime_log_file, ftell($this->realtime_log_file) - strlen($temp));
+ }
+ $this->realtime_log_size+= strlen($entry);
+ if ($this->realtime_log_size > NET_SSH2_LOG_MAX_SIZE) {
+ fseek($this->realtime_log_file, 0);
+ $this->realtime_log_size = strlen($entry);
+ $this->realtime_log_wrap = true;
+ }
+ fputs($this->realtime_log_file, $entry);
+ }
}
/**
@@ -3103,16 +3182,19 @@ class Net_SSH2 {
* for SCP more than anything.
*
* @param Integer $client_channel
+ * @param Boolean $want_reply
* @return Boolean
* @access private
*/
- function _close_channel($client_channel)
+ function _close_channel($client_channel, $want_reply = false)
{
// see http://tools.ietf.org/html/rfc4254#section-5.3
$this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_EOF, $this->server_channels[$client_channel]));
- $this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_CLOSE, $this->server_channels[$client_channel]));
+ if (!$want_reply) {
+ $this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_CLOSE, $this->server_channels[$client_channel]));
+ }
$this->channel_status[$client_channel] = NET_SSH2_MSG_CHANNEL_CLOSE;
@@ -3120,6 +3202,10 @@ class Net_SSH2 {
while (!is_bool($this->_get_channel_packet($client_channel)));
+ if ($want_reply) {
+ $this->_send_binary_packet(pack('CN', NET_SSH2_MSG_CHANNEL_CLOSE, $this->server_channels[$client_channel]));
+ }
+
if ($this->bitmap & NET_SSH2_MASK_SHELL) {
$this->bitmap&= ~NET_SSH2_MASK_SHELL;
}
@@ -3220,8 +3306,6 @@ class Net_SSH2 {
*/
function _format_log($message_log, $message_number_log)
{
- static $boundary = ':', $long_width = 65, $short_width = 16;
-
$output = '';
for ($i = 0; $i < count($message_log); $i++) {
$output.= $message_number_log[$i] . "\r\n";
@@ -3231,19 +3315,13 @@ class Net_SSH2 {
if (strlen($current_log)) {
$output.= str_pad(dechex($j), 7, '0', STR_PAD_LEFT) . '0 ';
}
- $fragment = $this->_string_shift($current_log, $short_width);
- $hex = substr(
- preg_replace(
- '#(.)#es',
- '"' . $boundary . '" . str_pad(dechex(ord(substr("\\1", -1))), 2, "0", STR_PAD_LEFT)',
- $fragment),
- strlen($boundary)
- );
+ $fragment = $this->_string_shift($current_log, $this->log_short_width);
+ $hex = substr(preg_replace_callback('#.#s', array($this, '_format_log_helper'), $fragment), strlen($this->log_boundary));
// replace non ASCII printable characters with dots
// http://en.wikipedia.org/wiki/ASCII#ASCII_printable_characters
// also replace < with a . since < messes up the output on web browsers
$raw = preg_replace('#[^\x20-\x7E]|<#', '.', $fragment);
- $output.= str_pad($hex, $long_width - $short_width, ' ') . $raw . "\r\n";
+ $output.= str_pad($hex, $this->log_long_width - $this->log_short_width, ' ') . $raw . "\r\n";
$j++;
} while (strlen($current_log));
$output.= "\r\n";
@@ -3252,6 +3330,20 @@ class Net_SSH2 {
return $output;
}
+ /**
+ * Helper function for _format_log
+ *
+ * For use with preg_replace_callback()
+ *
+ * @param Array $matches
+ * @access private
+ * @return String
+ */
+ function _format_log_helper($matches)
+ {
+ return $this->log_boundary . str_pad(dechex(ord($matches[0])), 2, '0', STR_PAD_LEFT);
+ }
+
/**
* Returns all errors
*
@@ -3505,7 +3597,7 @@ class Net_SSH2 {
$signature = $this->_string_shift($signature, $temp['length']);
if (!class_exists('Crypt_RSA')) {
- require_once('Crypt/RSA.php');
+ include_once 'Crypt/RSA.php';
}
$rsa = new Crypt_RSA();
@@ -3572,7 +3664,15 @@ class Net_SSH2 {
*/
function _is_includable($suffix)
{
- foreach (explode(PATH_SEPARATOR, get_include_path()) as $prefix) {
+ // stream_resolve_include_path was introduced in PHP 5.3.2
+ if (function_exists('stream_resolve_include_path')) {
+ return stream_resolve_include_path($suffix) !== false;
+ }
+
+ $paths = PATH_SEPARATOR == ':' ?
+ preg_split('#(?
+ * login('username', $agent)) {
+ * exit('Login Failed');
+ * }
+ *
+ * echo $ssh->exec('pwd');
+ * echo $ssh->exec('ls -la');
+ * ?>
+ *
+ *
+ * LICENSE: Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in
+ * all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+ * THE SOFTWARE.
+ *
+ * @category System
+ * @package System_SSH_Agent
+ * @author Jim Wigginton
+ * @copyright MMXIV Jim Wigginton
+ * @license http://www.opensource.org/licenses/mit-license.html MIT License
+ * @link http://phpseclib.sourceforge.net
+ * @internal See http://api.libssh.org/rfc/PROTOCOL.agent
+ */
+
+/**#@+
+ * Message numbers
+ *
+ * @access private
+ */
+// to request SSH1 keys you have to use SSH_AGENTC_REQUEST_RSA_IDENTITIES (1)
+define('SYSTEM_SSH_AGENTC_REQUEST_IDENTITIES', 11);
+// this is the SSH2 response; the SSH1 response is SSH_AGENT_RSA_IDENTITIES_ANSWER (2).
+define('SYSTEM_SSH_AGENT_IDENTITIES_ANSWER', 12);
+define('SYSTEM_SSH_AGENT_FAILURE', 5);
+// the SSH1 request is SSH_AGENTC_RSA_CHALLENGE (3)
+define('SYSTEM_SSH_AGENTC_SIGN_REQUEST', 13);
+// the SSH1 response is SSH_AGENT_RSA_RESPONSE (4)
+define('SYSTEM_SSH_AGENT_SIGN_RESPONSE', 14);
+/**#@-*/
+
+/**
+ * Pure-PHP ssh-agent client identity object
+ *
+ * Instantiation should only be performed by System_SSH_Agent class.
+ * This could be thought of as implementing an interface that Crypt_RSA
+ * implements. ie. maybe a Net_SSH_Auth_PublicKey interface or something.
+ * The methods in this interface would be getPublicKey, setSignatureMode
+ * and sign since those are the methods phpseclib looks for to perform
+ * public key authentication.
+ *
+ * @package System_SSH_Agent
+ * @author Jim Wigginton
+ * @version 0.1.0
+ * @access internal
+ */
+class System_SSH_Agent_Identity
+{
+ /**
+ * Key Object
+ *
+ * @var Crypt_RSA
+ * @access private
+ * @see System_SSH_Agent_Identity::getPublicKey()
+ */
+ var $key;
+
+ /**
+ * Key Blob
+ *
+ * @var String
+ * @access private
+ * @see System_SSH_Agent_Identity::sign()
+ */
+ var $key_blob;
+
+ /**
+ * Socket Resource
+ *
+ * @var Resource
+ * @access private
+ * @see System_SSH_Agent_Identity::sign()
+ */
+ var $fsock;
+
+ /**
+ * Default Constructor.
+ *
+ * @param Resource $fsock
+ * @return System_SSH_Agent_Identity
+ * @access private
+ */
+ function System_SSH_Agent_Identity($fsock)
+ {
+ $this->fsock = $fsock;
+ }
+
+ /**
+ * Set Public Key
+ *
+ * Called by System_SSH_Agent::requestIdentities()
+ *
+ * @param Crypt_RSA $key
+ * @access private
+ */
+ function setPublicKey($key)
+ {
+ $this->key = $key;
+ $this->key->setPublicKey();
+ }
+
+ /**
+ * Set Public Key
+ *
+ * Called by System_SSH_Agent::requestIdentities(). The key blob could be extracted from $this->key
+ * but this saves a small amount of computation.
+ *
+ * @param String $key_blob
+ * @access private
+ */
+ function setPublicKeyBlob($key_blob)
+ {
+ $this->key_blob = $key_blob;
+ }
+
+ /**
+ * Get Public Key
+ *
+ * Wrapper for $this->key->getPublicKey()
+ *
+ * @param Integer $format optional
+ * @return Mixed
+ * @access public
+ */
+ function getPublicKey($format = null)
+ {
+ return !isset($format) ? $this->key->getPublicKey() : $this->key->getPublicKey($format);
+ }
+
+ /**
+ * Set Signature Mode
+ *
+ * Doesn't do anything as ssh-agent doesn't let you pick and choose the signature mode. ie.
+ * ssh-agent's only supported mode is CRYPT_RSA_SIGNATURE_PKCS1
+ *
+ * @param Integer $mode
+ * @access public
+ */
+ function setSignatureMode($mode)
+ {
+ }
+
+ /**
+ * Create a signature
+ *
+ * See "2.6.2 Protocol 2 private key signature request"
+ *
+ * @param String $message
+ * @return String
+ * @access public
+ */
+ function sign($message)
+ {
+ // the last parameter (currently 0) is for flags and ssh-agent only defines one flag (for ssh-dss): SSH_AGENT_OLD_SIGNATURE
+ $packet = pack('CNa*Na*N', SYSTEM_SSH_AGENTC_SIGN_REQUEST, strlen($this->key_blob), $this->key_blob, strlen($message), $message, 0);
+ $packet = pack('Na*', strlen($packet), $packet);
+ if (strlen($packet) != fputs($this->fsock, $packet)) {
+ user_error('Connection closed during signing');
+ }
+
+ $length = current(unpack('N', fread($this->fsock, 4)));
+ $type = ord(fread($this->fsock, 1));
+ if ($type != SYSTEM_SSH_AGENT_SIGN_RESPONSE) {
+ user_error('Unable to retreive signature');
+ }
+
+ $signature_blob = fread($this->fsock, $length - 1);
+ // the only other signature format defined - ssh-dss - is the same length as ssh-rsa
+ // the + 12 is for the other various SSH added length fields
+ return substr($signature_blob, strlen('ssh-rsa') + 12);
+ }
+}
+
+/**
+ * Pure-PHP ssh-agent client identity factory
+ *
+ * requestIdentities() method pumps out System_SSH_Agent_Identity objects
+ *
+ * @package System_SSH_Agent
+ * @author Jim Wigginton
+ * @version 0.1.0
+ * @access internal
+ */
+class System_SSH_Agent
+{
+ /**
+ * Socket Resource
+ *
+ * @var Resource
+ * @access private
+ */
+ var $fsock;
+
+ /**
+ * Default Constructor
+ *
+ * @return System_SSH_Agent
+ * @access public
+ */
+ function System_SSH_Agent()
+ {
+ switch (true) {
+ case isset($_SERVER['SSH_AUTH_SOCK']):
+ $address = $_SERVER['SSH_AUTH_SOCK'];
+ break;
+ case isset($_ENV['SSH_AUTH_SOCK']):
+ $address = $_ENV['SSH_AUTH_SOCK'];
+ break;
+ default:
+ user_error('SSH_AUTH_SOCK not found');
+ return false;
+ }
+
+ $this->fsock = fsockopen('unix://' . $address, 0, $errno, $errstr);
+ if (!$this->fsock) {
+ user_error("Unable to connect to ssh-agent (Error $errno: $errstr)");
+ }
+ }
+
+ /**
+ * Request Identities
+ *
+ * See "2.5.2 Requesting a list of protocol 2 keys"
+ * Returns an array containing zero or more System_SSH_Agent_Identity objects
+ *
+ * @return Array
+ * @access public
+ */
+ function requestIdentities()
+ {
+ if (!$this->fsock) {
+ return array();
+ }
+
+ $packet = pack('NC', 1, SYSTEM_SSH_AGENTC_REQUEST_IDENTITIES);
+ if (strlen($packet) != fputs($this->fsock, $packet)) {
+ user_error('Connection closed while requesting identities');
+ }
+
+ $length = current(unpack('N', fread($this->fsock, 4)));
+ $type = ord(fread($this->fsock, 1));
+ if ($type != SYSTEM_SSH_AGENT_IDENTITIES_ANSWER) {
+ user_error('Unable to request identities');
+ }
+
+ $identities = array();
+ $keyCount = current(unpack('N', fread($this->fsock, 4)));
+ for ($i = 0; $i < $keyCount; $i++) {
+ $length = current(unpack('N', fread($this->fsock, 4)));
+ $key_blob = fread($this->fsock, $length);
+ $length = current(unpack('N', fread($this->fsock, 4)));
+ $key_comment = fread($this->fsock, $length);
+ $length = current(unpack('N', substr($key_blob, 0, 4)));
+ $key_type = substr($key_blob, 4, $length);
+ switch ($key_type) {
+ case 'ssh-rsa':
+ if (!class_exists('Crypt_RSA')) {
+ include_once 'Crypt/RSA.php';
+ }
+ $key = new Crypt_RSA();
+ $key->loadKey('ssh-rsa ' . base64_encode($key_blob) . ' ' . $key_comment);
+ break;
+ case 'ssh-dss':
+ // not currently supported
+ break;
+ }
+ // resources are passed by reference by default
+ if (isset($key)) {
+ $identity = new System_SSH_Agent_Identity($this->fsock);
+ $identity->setPublicKey($key);
+ $identity->setPublicKeyBlob($key_blob);
+ $identities[] = $identity;
+ unset($key);
+ }
+ }
+
+ return $identities;
+ }
+}
diff --git a/apps/files_external/3rdparty/phpseclib/phpseclib/openssl.cnf b/apps/files_external/3rdparty/phpseclib/phpseclib/openssl.cnf
index 6baa566102c..2b8b52f9f7f 100644
--- a/apps/files_external/3rdparty/phpseclib/phpseclib/openssl.cnf
+++ b/apps/files_external/3rdparty/phpseclib/phpseclib/openssl.cnf
@@ -3,4 +3,4 @@
HOME = .
RANDFILE = $ENV::HOME/.rnd
-[ v3_ca ]
\ No newline at end of file
+[ v3_ca ]