Merge branch 'develop' of git@github.com:LDAPAccountManager/lam.git into develop

This commit is contained in:
Roland Gruber 2017-09-24 09:49:02 +02:00
commit d521f60f66
63 changed files with 33816 additions and 34310 deletions

1
.gitignore vendored
View File

@ -1,3 +1,4 @@
/.settings/
/.buildpath
/.project
/.Readme.md.html

View File

@ -3,9 +3,16 @@ LDAP Account Manager
LDAP Account Manager (LAM) is a webfrontend for managing entries (e.g. users, groups, DHCP settings) stored in an LDAP directory. LAM was designed to make LDAP management as easy as possible for the user. It abstracts from the technical details of LDAP and allows persons without technical background to manage LDAP entries. If needed, power users may still directly edit LDAP entries via the integrated LDAP browser.
![LAM](https://www.ldap-account-manager.org/lamcms/sites/default/files/styles/slideshow/public/userList.png)
![LAM](https://www.ldap-account-manager.org/lamcms/sites/default/files/styles/slideshow/public/user_0.png)
# Download
You can get the newest version at https://www.ldap-account-manager.org/.
# Documentation
Please see the [documentation area](https://www.ldap-account-manager.org/lamcms/documentation).
# Source code
There are two modules. Usually, you only need the files inside "lam".

View File

@ -1,3 +1,7 @@
December 2017
- PHP 5.6 and Internet Explorer 11 or later required
19.09.2017 6.1
- Automatically trim input fields to avoid trailing/leading spaces
- LAM Pro:
@ -8,11 +12,13 @@
-> Password modify page reports error on password change when posixAccount is present for users
-> Nginx configuration files did not include "fastcgi_param SCRIPT_FILENAME $request_filename;" (193)
20.07.2017 6.0.1
- Fixed bugs:
-> Configuration file fills up with empty values
-> Tool visibility settings
26.06.2017 6.0
- Support multiple configurations for same account type
- PHP 7.1 compatibility

View File

@ -15,7 +15,7 @@ LAM - Readme
https://www.ldap-account-manager.org/
Copyright (C) 2003 - 2016 Roland Gruber <post@rolandgruber.de>
Copyright (C) 2003 - 2017 Roland Gruber <post@rolandgruber.de>
Installation and documentation:
Please see the LAM manual in docs/manual/index.html.

View File

@ -1,4 +1,4 @@
This software is copyright (c) 2003 - 2016 by Roland Gruber
This software is copyright (c) 2003 - 2017 by Roland Gruber
If you purchased a copy of LDAP Account Manager Pro then the following
files are licensed under the conditions which you accepted at purchase

View File

@ -15,7 +15,7 @@
<itemizedlist>
<listitem>
<para>Apache/Nginx webserver (SSL recommended) with PHP module (PHP
(&gt;= 5.4.0) with ldap, gettext, xml, openssl and optional
(&gt;= 5.6.0) with ldap, gettext, xml, openssl and optional
OpenSSL)</para>
</listitem>
@ -44,7 +44,7 @@
</listitem>
<listitem>
<para>Internet Explorer 9 <emphasis role="bold">(compatibility
<para>Internet Explorer 11 <emphasis role="bold">(compatibility
mode turned off)</emphasis></para>
</listitem>

View File

@ -63,7 +63,7 @@
<itemizedlist>
<listitem>
<para>PHP (&gt;= 5.4.0)</para>
<para>PHP (&gt;= 5.6.0)</para>
</listitem>
<listitem>
@ -85,7 +85,7 @@
</listitem>
<listitem>
<para>Internet Explorer 9<emphasis role="bold"> (compatibility mode
<para>Internet Explorer 11<emphasis role="bold"> (compatibility mode
turned off)</emphasis></para>
</listitem>

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available/possible, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* NOTE: Since AES.php is (for compatibility and phpseclib-historical reasons) virtually
* just a wrapper to Rijndael.php you may consider using Rijndael.php instead of
@ -16,16 +16,16 @@
* it'll be null-padded to 192-bits and 192 bits will be the key length until {@link self::setKey() setKey()}
* is called, again, at which point, it'll be recalculated.
*
* Since Crypt_AES extends Crypt_Rijndael, some functions are available to be called that, in the context of AES, don't
* Since \phpseclib\Crypt\AES extends \phpseclib\Crypt\Rijndael, some functions are available to be called that, in the context of AES, don't
* make a whole lot of sense. {@link self::setBlockLength() setBlockLength()}, for instance. Calling that function,
* however possible, won't do anything (AES has a fixed block length whereas Rijndael has a variable one).
*
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/AES.php';
* include 'vendor/autoload.php';
*
* $aes = new Crypt_AES();
* $aes = new \phpseclib\Crypt\AES();
*
* $aes->setKey('abcdefghijklmnop');
*
@ -39,102 +39,31 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_AES
* @package AES
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2008 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Rijndael
*/
if (!class_exists('Crypt_Rijndael')) {
include_once 'Rijndael.php';
}
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_AES_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_AES_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_AES_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_AES_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_AES_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of AES.
*
* @package Crypt_AES
* @package AES
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_AES extends Crypt_Rijndael
class AES extends Rijndael
{
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'AES';
/**
* Dummy function
*
* Since Crypt_AES extends Crypt_Rijndael, this function is, technically, available, but it doesn't do anything.
* Since \phpseclib\Crypt\AES extends \phpseclib\Crypt\Rijndael, this function is, technically, available, but it doesn't do anything.
*
* @see Crypt_Rijndael::setBlockLength()
* @see \phpseclib\Crypt\Rijndael::setBlockLength()
* @access public
* @param int $length
*/
@ -149,7 +78,7 @@ class Crypt_AES extends Crypt_Rijndael
* Valid key lengths are 128, 192, and 256. If the length is less than 128, it will be rounded up to
* 128. If the length is greater than 128 and invalid, it will be rounded down to the closest valid amount.
*
* @see Crypt_Rijndael:setKeyLength()
* @see \phpseclib\Crypt\Rijndael:setKeyLength()
* @access public
* @param int $length
*/
@ -170,7 +99,7 @@ class Crypt_AES extends Crypt_Rijndael
*
* Rijndael supports five different key lengths, AES only supports three.
*
* @see Crypt_Rijndael:setKey()
* @see \phpseclib\Crypt\Rijndael:setKey()
* @see setKeyLength()
* @access public
* @param string $key

File diff suppressed because it is too large Load Diff

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* Useful resources are as follows:
*
@ -14,9 +14,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/Blowfish.php';
* include 'vendor/autoload.php';
*
* $blowfish = new Crypt_Blowfish();
* $blowfish = new \phpseclib\Crypt\Blowfish();
*
* $blowfish->setKey('12345678901234567890123456789012');
*
@ -26,26 +26,8 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_Blowfish
* @package Blowfish
* @author Jim Wigginton <terrafrost@php.net>
* @author Hans-Juergen Petrich <petrich@tronic-media.com>
* @copyright 2007 Jim Wigginton
@ -53,86 +35,31 @@
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_BLOWFISH_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_BLOWFISH_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_BLOWFISH_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_BLOWFISH_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_BLOWFISH_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of Blowfish.
*
* @package Crypt_Blowfish
* @package Blowfish
* @author Jim Wigginton <terrafrost@php.net>
* @author Hans-Juergen Petrich <petrich@tronic-media.com>
* @access public
*/
class Crypt_Blowfish extends Crypt_Base
class Blowfish extends Base
{
/**
* Block Length of the cipher
*
* @see Crypt_Base::block_size
* @see \phpseclib\Crypt\Base::block_size
* @var int
* @access private
*/
var $block_size = 8;
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'BLOWFISH';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -141,7 +68,7 @@ class Crypt_Blowfish extends Crypt_Base
/**
* Optimizing value while CFB-encrypting
*
* @see Crypt_Base::cfb_init_len
* @see \phpseclib\Crypt\Base::cfb_init_len
* @var int
* @access private
*/
@ -346,7 +273,7 @@ class Crypt_Blowfish extends Crypt_Base
/**
* The Key Length (in bytes)
*
* @see Crypt_Base::setKeyLength()
* @see \phpseclib\Crypt\Base::setKeyLength()
* @var int
* @access private
* @internal The max value is 256 / 8 = 32, the min value is 128 / 8 = 16. Exists in conjunction with $Nk
@ -380,17 +307,20 @@ class Crypt_Blowfish extends Crypt_Base
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::isValidEngine()
* @see \phpseclib\Crypt\Base::isValidEngine()
* @param int $engine
* @access public
* @return bool
*/
function isValidEngine($engine)
{
if ($engine == CRYPT_ENGINE_OPENSSL) {
if ($this->key_length != 16) {
if ($engine == self::ENGINE_OPENSSL) {
if (version_compare(PHP_VERSION, '5.3.7') < 0 && $this->key_length != 16) {
return false;
}
if ($this->key_length < 16) {
return false;
}
$this->cipher_name_openssl_ecb = 'bf-ecb';
@ -403,7 +333,7 @@ class Crypt_Blowfish extends Crypt_Base
/**
* Setup the key (expansion)
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -530,15 +460,15 @@ class Crypt_Blowfish extends Crypt_Base
/**
* Setup the performance-optimized function for de/encrypt()
*
* @see Crypt_Base::_setupInlineCrypt()
* @see \phpseclib\Crypt\Base::_setupInlineCrypt()
* @access private
*/
function _setupInlineCrypt()
{
$lambda_functions =& Crypt_Blowfish::_getLambdaFunctions();
$lambda_functions =& self::_getLambdaFunctions();
// We create max. 10 hi-optimized code for memory reason. Means: For each $key one ultra fast inline-crypt function.
// (Currently, for Crypt_Blowfish, one generated $lambda_function cost on php5.5@32bit ~100kb unfreeable mem and ~180kb on php5.5@64bit)
// (Currently, for Blowfish, one generated $lambda_function cost on php5.5@32bit ~100kb unfreeable mem and ~180kb on php5.5@64bit)
// After that, we'll still create very fast optimized code but not the hi-ultimative code, for each $mode one.
$gen_hi_opt_code = (bool)(count($lambda_functions) < 10);

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* Useful resources are as follows:
*
@ -16,9 +16,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/DES.php';
* include 'vendor/autoload.php';
*
* $des = new Crypt_DES();
* $des = new \phpseclib\Crypt\DES();
*
* $des->setKey('abcdefgh');
*
@ -32,108 +32,44 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_DES
* @package DES
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access private
* @see self::_setupKey()
* @see self::_processBlock()
*/
/**
* Contains $keys[CRYPT_DES_ENCRYPT]
*/
define('CRYPT_DES_ENCRYPT', 0);
/**
* Contains $keys[CRYPT_DES_DECRYPT]
*/
define('CRYPT_DES_DECRYPT', 1);
/**#@-*/
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_DES_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_DES_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_DES_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_DES_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_DES_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of DES.
*
* @package Crypt_DES
* @package DES
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_DES extends Crypt_Base
class DES extends Base
{
/**#@+
* @access private
* @see \phpseclib\Crypt\DES::_setupKey()
* @see \phpseclib\Crypt\DES::_processBlock()
*/
/**
* Contains $keys[self::ENCRYPT]
*/
const ENCRYPT = 0;
/**
* Contains $keys[self::DECRYPT]
*/
const DECRYPT = 1;
/**#@-*/
/**
* Block Length of the cipher
*
* @see Crypt_Base::block_size
* @see \phpseclib\Crypt\Base::block_size
* @var int
* @access private
*/
@ -142,25 +78,16 @@ class Crypt_DES extends Crypt_Base
/**
* Key Length (in bytes)
*
* @see Crypt_Base::setKeyLength()
* @see \phpseclib\Crypt\Base::setKeyLength()
* @var int
* @access private
*/
var $key_length = 8;
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'DES';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -169,22 +96,22 @@ class Crypt_DES extends Crypt_Base
/**
* The OpenSSL names of the cipher / modes
*
* @see Crypt_Base::openssl_mode_names
* @see \phpseclib\Crypt\Base::openssl_mode_names
* @var array
* @access private
*/
var $openssl_mode_names = array(
CRYPT_MODE_ECB => 'des-ecb',
CRYPT_MODE_CBC => 'des-cbc',
CRYPT_MODE_CFB => 'des-cfb',
CRYPT_MODE_OFB => 'des-ofb'
// CRYPT_MODE_CTR is undefined for DES
self::MODE_ECB => 'des-ecb',
self::MODE_CBC => 'des-cbc',
self::MODE_CFB => 'des-cfb',
self::MODE_OFB => 'des-ofb'
// self::MODE_CTR is undefined for DES
);
/**
* Optimizing value while CFB-encrypting
*
* @see Crypt_Base::cfb_init_len
* @see \phpseclib\Crypt\Base::cfb_init_len
* @var int
* @access private
*/
@ -193,7 +120,7 @@ class Crypt_DES extends Crypt_Base
/**
* Switch for DES/3DES encryption
*
* Used only if $engine == CRYPT_DES_MODE_INTERNAL
* Used only if $engine == self::ENGINE_INTERNAL
*
* @see self::_setupKey()
* @see self::_processBlock()
@ -654,9 +581,9 @@ class Crypt_DES extends Crypt_Base
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::isValidEngine()
* @see \phpseclib\Crypt\Base::isValidEngine()
* @param int $engine
* @access public
* @return bool
@ -664,7 +591,7 @@ class Crypt_DES extends Crypt_Base
function isValidEngine($engine)
{
if ($this->key_length_max == 8) {
if ($engine == CRYPT_ENGINE_OPENSSL) {
if ($engine == self::ENGINE_OPENSSL) {
$this->cipher_name_openssl_ecb = 'des-ecb';
$this->cipher_name_openssl = 'des-' . $this->_openssl_translate_mode();
}
@ -684,7 +611,7 @@ class Crypt_DES extends Crypt_Base
*
* If the key is not explicitly set, it'll be assumed to be all zero's.
*
* @see Crypt_Base::setKey()
* @see \phpseclib\Crypt\Base::setKey()
* @access public
* @param string $key
*/
@ -703,8 +630,8 @@ class Crypt_DES extends Crypt_Base
/**
* Encrypts a block
*
* @see Crypt_Base::_encryptBlock()
* @see Crypt_Base::encrypt()
* @see \phpseclib\Crypt\Base::_encryptBlock()
* @see \phpseclib\Crypt\Base::encrypt()
* @see self::encrypt()
* @access private
* @param string $in
@ -712,14 +639,14 @@ class Crypt_DES extends Crypt_Base
*/
function _encryptBlock($in)
{
return $this->_processBlock($in, CRYPT_DES_ENCRYPT);
return $this->_processBlock($in, self::ENCRYPT);
}
/**
* Decrypts a block
*
* @see Crypt_Base::_decryptBlock()
* @see Crypt_Base::decrypt()
* @see \phpseclib\Crypt\Base::_decryptBlock()
* @see \phpseclib\Crypt\Base::decrypt()
* @see self::decrypt()
* @access private
* @param string $in
@ -727,13 +654,13 @@ class Crypt_DES extends Crypt_Base
*/
function _decryptBlock($in)
{
return $this->_processBlock($in, CRYPT_DES_DECRYPT);
return $this->_processBlock($in, self::DECRYPT);
}
/**
* Encrypts or decrypts a 64-bit block
*
* $mode should be either CRYPT_DES_ENCRYPT or CRYPT_DES_DECRYPT. See
* $mode should be either self::ENCRYPT or self::DECRYPT. See
* {@link http://en.wikipedia.org/wiki/Image:Feistel.png Feistel.png} to get a general
* idea of what this function does.
*
@ -822,7 +749,7 @@ class Crypt_DES extends Crypt_Base
/**
* Creates the key schedule
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -1303,8 +1230,8 @@ class Crypt_DES extends Crypt_Base
$d = (($key['d'] >> 4) & 0x0FFFFFF0) | ($key['c'] & 0x0F);
$keys[$des_round] = array(
CRYPT_DES_ENCRYPT => array(),
CRYPT_DES_DECRYPT => array_fill(0, 32, 0)
self::ENCRYPT => array(),
self::DECRYPT => array_fill(0, 32, 0)
);
for ($i = 0, $ki = 31; $i < 16; ++$i, $ki-= 2) {
$c <<= $shifts[$i];
@ -1323,33 +1250,33 @@ class Crypt_DES extends Crypt_Base
(($dp >> 16) & 0x0000FF00) | (($dp >> 8) & 0x000000FF);
$val2 = (($cp << 8) & 0xFF000000) | (($cp << 16) & 0x00FF0000) |
(($dp >> 8) & 0x0000FF00) | ( $dp & 0x000000FF);
$keys[$des_round][CRYPT_DES_ENCRYPT][ ] = $val1;
$keys[$des_round][CRYPT_DES_DECRYPT][$ki - 1] = $val1;
$keys[$des_round][CRYPT_DES_ENCRYPT][ ] = $val2;
$keys[$des_round][CRYPT_DES_DECRYPT][$ki ] = $val2;
$keys[$des_round][self::ENCRYPT][ ] = $val1;
$keys[$des_round][self::DECRYPT][$ki - 1] = $val1;
$keys[$des_round][self::ENCRYPT][ ] = $val2;
$keys[$des_round][self::DECRYPT][$ki ] = $val2;
}
}
switch ($this->des_rounds) {
case 3: // 3DES keys
$this->keys = array(
CRYPT_DES_ENCRYPT => array_merge(
$keys[0][CRYPT_DES_ENCRYPT],
$keys[1][CRYPT_DES_DECRYPT],
$keys[2][CRYPT_DES_ENCRYPT]
self::ENCRYPT => array_merge(
$keys[0][self::ENCRYPT],
$keys[1][self::DECRYPT],
$keys[2][self::ENCRYPT]
),
CRYPT_DES_DECRYPT => array_merge(
$keys[2][CRYPT_DES_DECRYPT],
$keys[1][CRYPT_DES_ENCRYPT],
$keys[0][CRYPT_DES_DECRYPT]
self::DECRYPT => array_merge(
$keys[2][self::DECRYPT],
$keys[1][self::ENCRYPT],
$keys[0][self::DECRYPT]
)
);
break;
// case 1: // DES keys
default:
$this->keys = array(
CRYPT_DES_ENCRYPT => $keys[0][CRYPT_DES_ENCRYPT],
CRYPT_DES_DECRYPT => $keys[0][CRYPT_DES_DECRYPT]
self::ENCRYPT => $keys[0][self::ENCRYPT],
self::DECRYPT => $keys[0][self::DECRYPT]
);
}
}
@ -1357,12 +1284,12 @@ class Crypt_DES extends Crypt_Base
/**
* Setup the performance-optimized function for de/encrypt()
*
* @see Crypt_Base::_setupInlineCrypt()
* @see \phpseclib\Crypt\Base::_setupInlineCrypt()
* @access private
*/
function _setupInlineCrypt()
{
$lambda_functions =& Crypt_DES::_getLambdaFunctions();
$lambda_functions =& self::_getLambdaFunctions();
// Engine configuration for:
// - DES ($des_rounds == 1) or
@ -1370,12 +1297,12 @@ class Crypt_DES extends Crypt_Base
$des_rounds = $this->des_rounds;
// We create max. 10 hi-optimized code for memory reason. Means: For each $key one ultra fast inline-crypt function.
// (Currently, for Crypt_DES, one generated $lambda_function cost on php5.5@32bit ~135kb unfreeable mem and ~230kb on php5.5@64bit)
// (Currently, for Crypt_TripleDES, one generated $lambda_function cost on php5.5@32bit ~240kb unfreeable mem and ~340kb on php5.5@64bit)
// (Currently, for DES, one generated $lambda_function cost on php5.5@32bit ~135kb unfreeable mem and ~230kb on php5.5@64bit)
// (Currently, for TripleDES, one generated $lambda_function cost on php5.5@32bit ~240kb unfreeable mem and ~340kb on php5.5@64bit)
// After that, we'll still create very fast optimized code but not the hi-ultimative code, for each $mode one
$gen_hi_opt_code = (bool)( count($lambda_functions) < 10 );
// Generation of a uniqe hash for our generated code
// Generation of a unique hash for our generated code
$code_hash = "Crypt_DES, $des_rounds, {$this->mode}";
if ($gen_hi_opt_code) {
// For hi-optimized code, we create for each combination of
@ -1413,8 +1340,8 @@ class Crypt_DES extends Crypt_Base
// No futher initialisation of the $keys schedule is necessary.
// That is the extra performance boost.
$k = array(
CRYPT_DES_ENCRYPT => $this->keys[CRYPT_DES_ENCRYPT],
CRYPT_DES_DECRYPT => $this->keys[CRYPT_DES_DECRYPT]
self::ENCRYPT => $this->keys[self::ENCRYPT],
self::DECRYPT => $this->keys[self::DECRYPT]
);
$init_encrypt = '';
$init_decrypt = '';
@ -1423,21 +1350,21 @@ class Crypt_DES extends Crypt_Base
// In generic optimized code mode, we have to use, as the best compromise [currently],
// our key schedule as $ke/$kd arrays. (with hardcoded indexes...)
$k = array(
CRYPT_DES_ENCRYPT => array(),
CRYPT_DES_DECRYPT => array()
self::ENCRYPT => array(),
self::DECRYPT => array()
);
for ($i = 0, $c = count($this->keys[CRYPT_DES_ENCRYPT]); $i < $c; ++$i) {
$k[CRYPT_DES_ENCRYPT][$i] = '$ke[' . $i . ']';
$k[CRYPT_DES_DECRYPT][$i] = '$kd[' . $i . ']';
for ($i = 0, $c = count($this->keys[self::ENCRYPT]); $i < $c; ++$i) {
$k[self::ENCRYPT][$i] = '$ke[' . $i . ']';
$k[self::DECRYPT][$i] = '$kd[' . $i . ']';
}
$init_encrypt = '$ke = $self->keys[CRYPT_DES_ENCRYPT];';
$init_decrypt = '$kd = $self->keys[CRYPT_DES_DECRYPT];';
$init_encrypt = '$ke = $self->keys[self::ENCRYPT];';
$init_decrypt = '$kd = $self->keys[self::DECRYPT];';
break;
}
// Creating code for en- and decryption.
$crypt_block = array();
foreach (array(CRYPT_DES_ENCRYPT, CRYPT_DES_DECRYPT) as $c) {
foreach (array(self::ENCRYPT, self::DECRYPT) as $c) {
/* Do the initial IP permutation. */
$crypt_block[$c] = '
$in = unpack("N*", $in);
@ -1504,8 +1431,8 @@ class Crypt_DES extends Crypt_Base
'init_crypt' => $init_crypt,
'init_encrypt' => $init_encrypt,
'init_decrypt' => $init_decrypt,
'encrypt_block' => $crypt_block[CRYPT_DES_ENCRYPT],
'decrypt_block' => $crypt_block[CRYPT_DES_DECRYPT]
'encrypt_block' => $crypt_block[self::ENCRYPT],
'decrypt_block' => $crypt_block[self::DECRYPT]
)
);
}

View File

@ -10,7 +10,7 @@
* If {@link self::setKey() setKey()} is called, {@link self::hash() hash()} will return the HMAC as opposed to
* the hash. If no valid algorithm is provided, sha1 will be used.
*
* PHP versions 4 and 5
* PHP version 5
*
* {@internal The variable names are the same as those in
* {@link http://tools.ietf.org/html/rfc2104#section-2 RFC2104}.}}
@ -18,9 +18,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/Hash.php';
* include 'vendor/autoload.php';
*
* $hash = new Crypt_Hash('sha1');
* $hash = new \phpseclib\Crypt\Hash('sha1');
*
* $hash->setKey('abcdefg');
*
@ -28,59 +28,45 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_Hash
* @package Hash
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**#@+
* @access private
* @see self::Crypt_Hash()
*/
/**
* Toggles the internal implementation
*/
define('CRYPT_HASH_MODE_INTERNAL', 1);
/**
* Toggles the mhash() implementation, which has been deprecated on PHP 5.3.0+.
*/
define('CRYPT_HASH_MODE_MHASH', 2);
/**
* Toggles the hash() implementation, which works on PHP 5.1.2+.
*/
define('CRYPT_HASH_MODE_HASH', 3);
/**#@-*/
namespace phpseclib\Crypt;
use phpseclib\Math\BigInteger;
/**
* Pure-PHP implementations of keyed-hash message authentication codes (HMACs) and various cryptographic hashing functions.
*
* @package Crypt_Hash
* @package Hash
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_Hash
class Hash
{
/**#@+
* @access private
* @see \phpseclib\Crypt\Hash::__construct()
*/
/**
* Toggles the internal implementation
*/
const MODE_INTERNAL = 1;
/**
* Toggles the mhash() implementation, which has been deprecated on PHP 5.3.0+.
*/
const MODE_MHASH = 2;
/**
* Toggles the hash() implementation, which works on PHP 5.1.2+.
*/
const MODE_HASH = 3;
/**#@-*/
/**
* Hash Parameter
*
@ -148,21 +134,21 @@ class Crypt_Hash
* Default Constructor.
*
* @param string $hash
* @return Crypt_Hash
* @return \phpseclib\Crypt\Hash
* @access public
*/
function Crypt_Hash($hash = 'sha1')
function __construct($hash = 'sha1')
{
if (!defined('CRYPT_HASH_MODE')) {
switch (true) {
case extension_loaded('hash'):
define('CRYPT_HASH_MODE', CRYPT_HASH_MODE_HASH);
define('CRYPT_HASH_MODE', self::MODE_HASH);
break;
case extension_loaded('mhash'):
define('CRYPT_HASH_MODE', CRYPT_HASH_MODE_MHASH);
define('CRYPT_HASH_MODE', self::MODE_MHASH);
break;
default:
define('CRYPT_HASH_MODE', CRYPT_HASH_MODE_INTERNAL);
define('CRYPT_HASH_MODE', self::MODE_INTERNAL);
}
}
@ -231,19 +217,19 @@ class Crypt_Hash
switch ($hash) {
case 'md2':
$mode = CRYPT_HASH_MODE == CRYPT_HASH_MODE_HASH && in_array('md2', hash_algos()) ?
CRYPT_HASH_MODE_HASH : CRYPT_HASH_MODE_INTERNAL;
$mode = CRYPT_HASH_MODE == self::MODE_HASH && in_array('md2', hash_algos()) ?
self::MODE_HASH : self::MODE_INTERNAL;
break;
case 'sha384':
case 'sha512':
$mode = CRYPT_HASH_MODE == CRYPT_HASH_MODE_MHASH ? CRYPT_HASH_MODE_INTERNAL : CRYPT_HASH_MODE;
$mode = CRYPT_HASH_MODE == self::MODE_MHASH ? self::MODE_INTERNAL : CRYPT_HASH_MODE;
break;
default:
$mode = CRYPT_HASH_MODE;
}
switch ($mode) {
case CRYPT_HASH_MODE_MHASH:
case self::MODE_MHASH:
switch ($hash) {
case 'md5':
$this->hash = MHASH_MD5;
@ -256,7 +242,7 @@ class Crypt_Hash
$this->hash = MHASH_SHA1;
}
return;
case CRYPT_HASH_MODE_HASH:
case self::MODE_HASH:
switch ($hash) {
case 'md5':
$this->hash = 'md5';
@ -311,17 +297,17 @@ class Crypt_Hash
*/
function hash($text)
{
$mode = is_array($this->hash) ? CRYPT_HASH_MODE_INTERNAL : CRYPT_HASH_MODE;
$mode = is_array($this->hash) ? self::MODE_INTERNAL : CRYPT_HASH_MODE;
if (!empty($this->key) || is_string($this->key)) {
switch ($mode) {
case CRYPT_HASH_MODE_MHASH:
case self::MODE_MHASH:
$output = mhash($this->hash, $text, $this->key);
break;
case CRYPT_HASH_MODE_HASH:
case self::MODE_HASH:
$output = hash_hmac($this->hash, $text, $this->key, true);
break;
case CRYPT_HASH_MODE_INTERNAL:
case self::MODE_INTERNAL:
/* "Applications that use keys longer than B bytes will first hash the key using H and then use the
resultant L byte string as the actual key to HMAC."
@ -338,13 +324,13 @@ class Crypt_Hash
}
} else {
switch ($mode) {
case CRYPT_HASH_MODE_MHASH:
case self::MODE_MHASH:
$output = mhash($this->hash, $text);
break;
case CRYPT_HASH_MODE_HASH:
case self::MODE_HASH:
$output = hash($this->hash, $text, true);
break;
case CRYPT_HASH_MODE_INTERNAL:
case self::MODE_INTERNAL:
$output = call_user_func($this->hash, $text);
}
}
@ -520,7 +506,6 @@ class Crypt_Hash
$this->_rightShift( $w[$i - 2], 10);
// @codingStandardsIgnoreEnd
$w[$i] = $this->_add($w[$i - 16], $s0, $w[$i - 7], $s1);
}
// Initialize hash value for this chunk
@ -578,10 +563,6 @@ class Crypt_Hash
*/
function _sha512($m)
{
if (!class_exists('Math_BigInteger')) {
include_once 'Math/BigInteger.php';
}
static $init384, $init512, $k;
if (!isset($k)) {
@ -596,9 +577,9 @@ class Crypt_Hash
);
for ($i = 0; $i < 8; $i++) {
$init384[$i] = new Math_BigInteger($init384[$i], 16);
$init384[$i] = new BigInteger($init384[$i], 16);
$init384[$i]->setPrecision(64);
$init512[$i] = new Math_BigInteger($init512[$i], 16);
$init512[$i] = new BigInteger($init512[$i], 16);
$init512[$i]->setPrecision(64);
}
@ -628,7 +609,7 @@ class Crypt_Hash
);
for ($i = 0; $i < 80; $i++) {
$k[$i] = new Math_BigInteger($k[$i], 16);
$k[$i] = new BigInteger($k[$i], 16);
}
}
@ -647,7 +628,7 @@ class Crypt_Hash
foreach ($chunks as $chunk) {
$w = array();
for ($i = 0; $i < 16; $i++) {
$temp = new Math_BigInteger($this->_string_shift($chunk, 8), 256);
$temp = new BigInteger($this->_string_shift($chunk, 8), 256);
$temp->setPrecision(64);
$w[] = $temp;
}
@ -743,7 +724,7 @@ class Crypt_Hash
}
// Produce the final hash value (big-endian)
// (Crypt_Hash::hash() trims the output for hashes but not for HMACs. as such, we trim the output here)
// (\phpseclib\Crypt\Hash::hash() trims the output for hashes but not for HMACs. as such, we trim the output here)
$temp = $hash[0]->toBytes() . $hash[1]->toBytes() . $hash[2]->toBytes() . $hash[3]->toBytes() .
$hash[4]->toBytes() . $hash[5]->toBytes();
if ($this->l != 48) {
@ -801,7 +782,7 @@ class Crypt_Hash
* Add
*
* _sha256() adds multiple unsigned 32-bit integers. Since PHP doesn't support unsigned integers and since the
* possibility of overflow exists, care has to be taken. Math_BigInteger() could be used but this should be faster.
* possibility of overflow exists, care has to be taken. BigInteger could be used but this should be faster.
*
* @param int $...
* @return int

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* Useful resources are as follows:
*
@ -14,9 +14,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/RC2.php';
* include 'vendor/autoload.php';
*
* $rc2 = new Crypt_RC2();
* $rc2 = new \phpseclib\Crypt\RC2();
*
* $rc2->setKey('abcdefgh');
*
@ -26,91 +26,27 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_RC2
* @package RC2
* @author Patrick Monnerat <pm@datasphere.ch>
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_RC2_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_RC2_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_RC2_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_RC2_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_RC2_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of RC2.
*
* @package Crypt_RC2
* @package RC2
* @access public
*/
class Crypt_RC2 extends Crypt_Base
class RC2 extends Base
{
/**
* Block Length of the cipher
*
* @see Crypt_Base::block_size
* @see \phpseclib\Crypt\Base::block_size
* @var int
* @access private
*/
@ -119,7 +55,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* The Key
*
* @see Crypt_Base::key
* @see \phpseclib\Crypt\Base::key
* @see self::setKey()
* @var string
* @access private
@ -129,7 +65,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* The Original (unpadded) Key
*
* @see Crypt_Base::key
* @see \phpseclib\Crypt\Base::key
* @see self::setKey()
* @see self::encrypt()
* @see self::decrypt()
@ -141,7 +77,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* Don't truncate / null pad key
*
* @see Crypt_Base::_clearBuffers()
* @see \phpseclib\Crypt\Base::_clearBuffers()
* @var bool
* @access private
*/
@ -150,25 +86,16 @@ class Crypt_RC2 extends Crypt_Base
/**
* Key Length (in bytes)
*
* @see Crypt_RC2::setKeyLength()
* @see \phpseclib\Crypt\RC2::setKeyLength()
* @var int
* @access private
*/
var $key_length = 16; // = 128 bits
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'RC2';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -177,7 +104,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* Optimizing value while CFB-encrypting
*
* @see Crypt_Base::cfb_init_len
* @see \phpseclib\Crypt\Base::cfb_init_len
* @var int
* @access private
*/
@ -332,40 +259,12 @@ class Crypt_RC2 extends Crypt_Base
0x70, 0x02, 0xC2, 0x1E, 0xB8, 0x0A, 0xFC, 0xE6
);
/**
* Default Constructor.
*
* Determines whether or not the mcrypt extension should be used.
*
* $mode could be:
*
* - CRYPT_RC2_MODE_ECB
*
* - CRYPT_RC2_MODE_CBC
*
* - CRYPT_RC2_MODE_CTR
*
* - CRYPT_RC2_MODE_CFB
*
* - CRYPT_RC2_MODE_OFB
*
* If not explicitly set, CRYPT_RC2_MODE_CBC will be used.
*
* @see Crypt_Base::Crypt_Base()
* @param int $mode
* @access public
*/
function Crypt_RC2($mode = CRYPT_RC2_MODE_CBC)
{
parent::Crypt_Base($mode);
}
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::Crypt_Base()
* @see \phpseclib\Crypt\Base::__construct()
* @param int $engine
* @access public
* @return bool
@ -373,7 +272,7 @@ class Crypt_RC2 extends Crypt_Base
function isValidEngine($engine)
{
switch ($engine) {
case CRYPT_ENGINE_OPENSSL:
case self::ENGINE_OPENSSL:
if ($this->current_key_length != 128 || strlen($this->orig_key) < 16) {
return false;
}
@ -389,7 +288,7 @@ class Crypt_RC2 extends Crypt_Base
*
* Valid key lengths are 8 to 1024.
* Calling this function after setting the key has no effect until the next
* Crypt_RC2::setKey() call.
* \phpseclib\Crypt\RC2::setKey() call.
*
* @access public
* @param int $length in bits
@ -430,7 +329,7 @@ class Crypt_RC2 extends Crypt_Base
* If the key is not explicitly set, it'll be assumed to be a single
* null byte.
*
* @see Crypt_Base::setKey()
* @see \phpseclib\Crypt\Base::setKey()
* @access public
* @param string $key
* @param int $t1 optional Effective key length in bits.
@ -481,7 +380,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* Encrypts a message.
*
* Mostly a wrapper for Crypt_Base::encrypt, with some additional OpenSSL handling code
* Mostly a wrapper for \phpseclib\Crypt\Base::encrypt, with some additional OpenSSL handling code
*
* @see self::decrypt()
* @access public
@ -490,7 +389,7 @@ class Crypt_RC2 extends Crypt_Base
*/
function encrypt($plaintext)
{
if ($this->engine == CRYPT_ENGINE_OPENSSL) {
if ($this->engine == self::ENGINE_OPENSSL) {
$temp = $this->key;
$this->key = $this->orig_key;
$result = parent::encrypt($plaintext);
@ -504,7 +403,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* Decrypts a message.
*
* Mostly a wrapper for Crypt_Base::decrypt, with some additional OpenSSL handling code
* Mostly a wrapper for \phpseclib\Crypt\Base::decrypt, with some additional OpenSSL handling code
*
* @see self::encrypt()
* @access public
@ -513,7 +412,7 @@ class Crypt_RC2 extends Crypt_Base
*/
function decrypt($ciphertext)
{
if ($this->engine == CRYPT_ENGINE_OPENSSL) {
if ($this->engine == self::ENGINE_OPENSSL) {
$temp = $this->key;
$this->key = $this->orig_key;
$result = parent::decrypt($ciphertext);
@ -527,8 +426,8 @@ class Crypt_RC2 extends Crypt_Base
/**
* Encrypts a block
*
* @see Crypt_Base::_encryptBlock()
* @see Crypt_Base::encrypt()
* @see \phpseclib\Crypt\Base::_encryptBlock()
* @see \phpseclib\Crypt\Base::encrypt()
* @access private
* @param string $in
* @return string
@ -572,8 +471,8 @@ class Crypt_RC2 extends Crypt_Base
/**
* Decrypts a block
*
* @see Crypt_Base::_decryptBlock()
* @see Crypt_Base::decrypt()
* @see \phpseclib\Crypt\Base::_decryptBlock()
* @see \phpseclib\Crypt\Base::decrypt()
* @access private
* @param string $in
* @return string
@ -615,9 +514,9 @@ class Crypt_RC2 extends Crypt_Base
}
/**
* Setup the CRYPT_ENGINE_MCRYPT $engine
* Setup the \phpseclib\Crypt\Base::ENGINE_MCRYPT $engine
*
* @see Crypt_Base::_setupMcrypt()
* @see \phpseclib\Crypt\Base::_setupMcrypt()
* @access private
*/
function _setupMcrypt()
@ -632,7 +531,7 @@ class Crypt_RC2 extends Crypt_Base
/**
* Creates the key schedule
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -641,7 +540,7 @@ class Crypt_RC2 extends Crypt_Base
$this->setKey('');
}
// Key has already been expanded in Crypt_RC2::setKey():
// Key has already been expanded in \phpseclib\Crypt\RC2::setKey():
// Only the first value must be altered.
$l = unpack('Ca/Cb/v*', $this->key);
array_unshift($l, $this->pitable[$l['a']] | ($l['b'] << 8));
@ -653,12 +552,12 @@ class Crypt_RC2 extends Crypt_Base
/**
* Setup the performance-optimized function for de/encrypt()
*
* @see Crypt_Base::_setupInlineCrypt()
* @see \phpseclib\Crypt\Base::_setupInlineCrypt()
* @access private
*/
function _setupInlineCrypt()
{
$lambda_functions = &Crypt_RC2::_getLambdaFunctions();
$lambda_functions =& self::_getLambdaFunctions();
// The first 10 generated $lambda_functions will use the $keys hardcoded as integers
// for the mixing rounds, for better inline crypt performance [~20% faster].
@ -666,7 +565,7 @@ class Crypt_RC2 extends Crypt_Base
// (Currently, for Crypt_RC2, one generated $lambda_function cost on php5.5@32bit ~60kb unfreeable mem and ~100kb on php5.5@64bit)
$gen_hi_opt_code = (bool)(count($lambda_functions) < 10);
// Generation of a uniqe hash for our generated code
// Generation of a unique hash for our generated code
$code_hash = "Crypt_RC2, {$this->mode}";
if ($gen_hi_opt_code) {
$code_hash = str_pad($code_hash, 32) . $this->_hashInlineCryptFunction($this->key);

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* Useful resources are as follows:
*
@ -18,9 +18,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/RC4.php';
* include 'vendor/autoload.php';
*
* $rc4 = new Crypt_RC4();
* $rc4 = new \phpseclib\Crypt\RC4();
*
* $rc4->setKey('abcdefgh');
*
@ -34,65 +34,40 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_RC4
* @package RC4
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access private
* @see self::_crypt()
*/
define('CRYPT_RC4_ENCRYPT', 0);
define('CRYPT_RC4_DECRYPT', 1);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of RC4.
*
* @package Crypt_RC4
* @package RC4
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_RC4 extends Crypt_Base
class RC4 extends Base
{
/**#@+
* @access private
* @see \phpseclib\Crypt\RC4::_crypt()
*/
const ENCRYPT = 0;
const DECRYPT = 1;
/**#@-*/
/**
* Block Length of the cipher
*
* RC4 is a stream cipher
* so we the block_size to 0
*
* @see Crypt_Base::block_size
* @see \phpseclib\Crypt\Base::block_size
* @var int
* @access private
*/
@ -101,25 +76,16 @@ class Crypt_RC4 extends Crypt_Base
/**
* Key Length (in bytes)
*
* @see Crypt_RC4::setKeyLength()
* @see \phpseclib\Crypt\RC4::setKeyLength()
* @var int
* @access private
*/
var $key_length = 128; // = 1024 bits
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'RC4';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -128,7 +94,7 @@ class Crypt_RC4 extends Crypt_Base
/**
* Holds whether performance-optimized $inline_crypt() can/should be used.
*
* @see Crypt_Base::inline_crypt
* @see \phpseclib\Crypt\Base::inline_crypt
* @var mixed
* @access private
*/
@ -157,29 +123,31 @@ class Crypt_RC4 extends Crypt_Base
*
* Determines whether or not the mcrypt extension should be used.
*
* @see Crypt_Base::Crypt_Base()
* @return Crypt_RC4
* @see \phpseclib\Crypt\Base::__construct()
* @return \phpseclib\Crypt\RC4
* @access public
*/
function Crypt_RC4()
function __construct()
{
parent::Crypt_Base(CRYPT_MODE_STREAM);
parent::__construct(Base::MODE_STREAM);
}
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::Crypt_Base()
* @see \phpseclib\Crypt\Base::__construct()
* @param int $engine
* @access public
* @return bool
*/
function isValidEngine($engine)
{
switch ($engine) {
case CRYPT_ENGINE_OPENSSL:
if ($engine == Base::ENGINE_OPENSSL) {
if (version_compare(PHP_VERSION, '5.3.7') >= 0) {
$this->cipher_name_openssl = 'rc4-40';
} else {
switch (strlen($this->key)) {
case 5:
$this->cipher_name_openssl = 'rc4-40';
@ -194,6 +162,7 @@ class Crypt_RC4 extends Crypt_Base
return false;
}
}
}
return parent::isValidEngine($engine);
}
@ -245,7 +214,7 @@ class Crypt_RC4 extends Crypt_Base
/**
* Encrypts a message.
*
* @see Crypt_Base::decrypt()
* @see \phpseclib\Crypt\Base::decrypt()
* @see self::_crypt()
* @access public
* @param string $plaintext
@ -253,10 +222,10 @@ class Crypt_RC4 extends Crypt_Base
*/
function encrypt($plaintext)
{
if ($this->engine != CRYPT_ENGINE_INTERNAL) {
if ($this->engine != Base::ENGINE_INTERNAL) {
return parent::encrypt($plaintext);
}
return $this->_crypt($plaintext, CRYPT_RC4_ENCRYPT);
return $this->_crypt($plaintext, self::ENCRYPT);
}
/**
@ -265,7 +234,7 @@ class Crypt_RC4 extends Crypt_Base
* $this->decrypt($this->encrypt($plaintext)) == $this->encrypt($this->encrypt($plaintext)).
* At least if the continuous buffer is disabled.
*
* @see Crypt_Base::encrypt()
* @see \phpseclib\Crypt\Base::encrypt()
* @see self::_crypt()
* @access public
* @param string $ciphertext
@ -273,17 +242,38 @@ class Crypt_RC4 extends Crypt_Base
*/
function decrypt($ciphertext)
{
if ($this->engine != CRYPT_ENGINE_INTERNAL) {
if ($this->engine != Base::ENGINE_INTERNAL) {
return parent::decrypt($ciphertext);
}
return $this->_crypt($ciphertext, CRYPT_RC4_DECRYPT);
return $this->_crypt($ciphertext, self::DECRYPT);
}
/**
* Encrypts a block
*
* @access private
* @param string $in
*/
function _encryptBlock($in)
{
// RC4 does not utilize this method
}
/**
* Decrypts a block
*
* @access private
* @param string $in
*/
function _decryptBlock($in)
{
// RC4 does not utilize this method
}
/**
* Setup the key (expansion)
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -300,7 +290,7 @@ class Crypt_RC4 extends Crypt_Base
}
$this->stream = array();
$this->stream[CRYPT_RC4_DECRYPT] = $this->stream[CRYPT_RC4_ENCRYPT] = array(
$this->stream[self::DECRYPT] = $this->stream[self::ENCRYPT] = array(
0, // index $i
0, // index $j
$keyStream

File diff suppressed because it is too large Load Diff

View File

@ -3,57 +3,36 @@
/**
* Random Number Generator
*
* The idea behind this function is that it can be easily replaced with your own crypt_random_string()
* function. eg. maybe you have a better source of entropy for creating the initial states or whatever.
*
* PHP versions 4 and 5
* PHP version 5
*
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/Random.php';
* include 'vendor/autoload.php';
*
* echo bin2hex(crypt_random_string(8));
* echo bin2hex(\phpseclib\Crypt\Random::string(8));
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_Random
* @package Random
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
// laravel is a PHP framework that utilizes phpseclib. laravel workbenches may, independently,
// have phpseclib as a requirement as well. if you're developing such a program you may encounter
// a "Cannot redeclare crypt_random_string()" error.
if (!function_exists('crypt_random_string')) {
/**
* "Is Windows" test
*
* @access private
*/
define('CRYPT_RANDOM_IS_WINDOWS', strtoupper(substr(PHP_OS, 0, 3)) === 'WIN');
namespace phpseclib\Crypt;
/**
* Pure-PHP Random Number Generator
*
* @package Random
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Random
{
/**
* Generate a random string.
*
@ -63,14 +42,27 @@ if (!function_exists('crypt_random_string')) {
*
* @param int $length
* @return string
* @access public
*/
function crypt_random_string($length)
static function string($length)
{
if (CRYPT_RANDOM_IS_WINDOWS) {
// method 1. prior to PHP 5.3, mcrypt_create_iv() would call rand() on windows
if (extension_loaded('mcrypt') && version_compare(PHP_VERSION, '5.3.0', '>=')) {
return mcrypt_create_iv($length);
if (version_compare(PHP_VERSION, '7.0.0', '>=')) {
try {
return \random_bytes($length);
} catch (\Throwable $e) {
// If a sufficient source of randomness is unavailable, random_bytes() will throw an
// object that implements the Throwable interface (Exception, TypeError, Error).
// We don't actually need to do anything here. The string() method should just continue
// as normal. Note, however, that if we don't have a sufficient source of randomness for
// random_bytes(), most of the other calls here will fail too, so we'll end up using
// the PHP implementation.
}
}
if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
// method 1. prior to PHP 5.3 this would call rand() on windows hence the function_exists('class_alias') call.
// ie. class_alias is a function that was introduced in PHP 5.3
if (extension_loaded('mcrypt') && function_exists('class_alias')) {
return @mcrypt_create_iv($length);
}
// method 2. openssl_random_pseudo_bytes was introduced in PHP 5.3.0 but prior to PHP 5.3.4 there was,
// to quote <http://php.net/ChangeLog-5.php#5.3.4>, "possible blocking behavior". as of 5.3.4
@ -90,7 +82,7 @@ if (!function_exists('crypt_random_string')) {
}
} else {
// method 1. the fastest
if (extension_loaded('openssl') && version_compare(PHP_VERSION, '5.3.0', '>=')) {
if (extension_loaded('openssl')) {
return openssl_random_pseudo_bytes($length);
}
// method 2
@ -109,7 +101,7 @@ if (!function_exists('crypt_random_string')) {
// not doing. regardless, this'll only be called if this PHP script couldn't open /dev/urandom due to open_basedir
// restrictions or some such
if (extension_loaded('mcrypt')) {
return mcrypt_create_iv($length, MCRYPT_DEV_URANDOM);
return @mcrypt_create_iv($length, MCRYPT_DEV_URANDOM);
}
}
// at this point we have no choice but to use a pure-PHP CSPRNG
@ -193,44 +185,26 @@ if (!function_exists('crypt_random_string')) {
//
// http://en.wikipedia.org/wiki/Cryptographically_secure_pseudorandom_number_generator#Designs_based_on_cryptographic_primitives
switch (true) {
case phpseclib_resolve_include_path('Crypt/AES.php'):
if (!class_exists('Crypt_AES')) {
include_once 'AES.php';
}
$crypto = new Crypt_AES(CRYPT_AES_MODE_CTR);
case class_exists('\phpseclib\Crypt\AES'):
$crypto = new AES(Base::MODE_CTR);
break;
case phpseclib_resolve_include_path('Crypt/Twofish.php'):
if (!class_exists('Crypt_Twofish')) {
include_once 'Twofish.php';
}
$crypto = new Crypt_Twofish(CRYPT_TWOFISH_MODE_CTR);
case class_exists('\phpseclib\Crypt\Twofish'):
$crypto = new Twofish(Base::MODE_CTR);
break;
case phpseclib_resolve_include_path('Crypt/Blowfish.php'):
if (!class_exists('Crypt_Blowfish')) {
include_once 'Blowfish.php';
}
$crypto = new Crypt_Blowfish(CRYPT_BLOWFISH_MODE_CTR);
case class_exists('\phpseclib\Crypt\Blowfish'):
$crypto = new Blowfish(Base::MODE_CTR);
break;
case phpseclib_resolve_include_path('Crypt/TripleDES.php'):
if (!class_exists('Crypt_TripleDES')) {
include_once 'TripleDES.php';
}
$crypto = new Crypt_TripleDES(CRYPT_DES_MODE_CTR);
case class_exists('\phpseclib\Crypt\TripleDES'):
$crypto = new TripleDES(Base::MODE_CTR);
break;
case phpseclib_resolve_include_path('Crypt/DES.php'):
if (!class_exists('Crypt_DES')) {
include_once 'DES.php';
}
$crypto = new Crypt_DES(CRYPT_DES_MODE_CTR);
case class_exists('\phpseclib\Crypt\DES'):
$crypto = new DES(Base::MODE_CTR);
break;
case phpseclib_resolve_include_path('Crypt/RC4.php'):
if (!class_exists('Crypt_RC4')) {
include_once 'RC4.php';
}
$crypto = new Crypt_RC4();
case class_exists('\phpseclib\Crypt\RC4'):
$crypto = new RC4();
break;
default:
user_error('crypt_random_string requires at least one symmetric cipher be loaded');
user_error(__CLASS__ . ' requires at least one symmetric cipher be loaded');
return false;
}
@ -294,41 +268,3 @@ if (!function_exists('phpseclib_safe_serialize')) {
return serialize($safearr);
}
}
if (!function_exists('phpseclib_resolve_include_path')) {
/**
* Resolve filename against the include path.
*
* Wrapper around stream_resolve_include_path() (which was introduced in
* PHP 5.3.2) with fallback implementation for earlier PHP versions.
*
* @param string $filename
* @return string|false
* @access public
*/
function phpseclib_resolve_include_path($filename)
{
if (function_exists('stream_resolve_include_path')) {
return stream_resolve_include_path($filename);
}
// handle non-relative paths
if (file_exists($filename)) {
return realpath($filename);
}
$paths = PATH_SEPARATOR == ':' ?
preg_split('#(?<!phar):#', get_include_path()) :
explode(PATH_SEPARATOR, get_include_path());
foreach ($paths as $prefix) {
// path's specified in include_path don't always end in /
$ds = substr($prefix, -1) == DIRECTORY_SEPARATOR ? '' : DIRECTORY_SEPARATOR;
$file = $prefix . $ds . $filename;
if (file_exists($file)) {
return realpath($file);
}
}
return false;
}
}

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available/possible, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* If {@link self::setBlockLength() setBlockLength()} isn't called, it'll be assumed to be 128 bits. If
* {@link self::setKeyLength() setKeyLength()} isn't called, it'll be calculated from
@ -28,9 +28,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/Rijndael.php';
* include 'vendor/autoload.php';
*
* $rijndael = new Crypt_Rijndael();
* $rijndael = new \phpseclib\Crypt\Rijndael();
*
* $rijndael->setKey('abcdefghijklmnop');
*
@ -44,108 +44,35 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_Rijndael
* @package Rijndael
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2008 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_RIJNDAEL_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_RIJNDAEL_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_RIJNDAEL_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_RIJNDAEL_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_RIJNDAEL_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of Rijndael.
*
* @package Crypt_Rijndael
* @package Rijndael
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_Rijndael extends Crypt_Base
class Rijndael extends Base
{
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'RIJNDAEL';
/**
* The mcrypt specific name of the cipher
*
* Mcrypt is useable for 128/192/256-bit $block_size/$key_length. For 160/224 not.
* Crypt_Rijndael determines automatically whether mcrypt is useable
* \phpseclib\Crypt\Rijndael determines automatically whether mcrypt is useable
* or not for the current $block_size/$key_length.
* In case of, $cipher_name_mcrypt will be set dynamically at run time accordingly.
*
* @see Crypt_Base::cipher_name_mcrypt
* @see Crypt_Base::engine
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::engine
* @see self::isValidEngine()
* @var string
* @access private
@ -155,8 +82,8 @@ class Crypt_Rijndael extends Crypt_Base
/**
* The default salt used by setPassword()
*
* @see Crypt_Base::password_default_salt
* @see Crypt_Base::setPassword()
* @see \phpseclib\Crypt\Base::password_default_salt
* @see \phpseclib\Crypt\Base::setPassword()
* @var string
* @access private
*/
@ -242,76 +169,7 @@ class Crypt_Rijndael extends Crypt_Base
var $kl;
/**
* Default Constructor.
*
* Determines whether or not the mcrypt extension should be used.
*
* $mode could be:
*
* - CRYPT_RIJNDAEL_MODE_ECB
*
* - CRYPT_RIJNDAEL_MODE_CBC
*
* - CRYPT_RIJNDAEL_MODE_CTR
*
* - CRYPT_RIJNDAEL_MODE_CFB
*
* - CRYPT_RIJNDAEL_MODE_OFB
*
* If not explictly set, CRYPT_RIJNDAEL_MODE_CBC will be used.
*
* @see Crypt_Base::Crypt_Base()
* @param int $mode
* @access public
*/
function Crypt_Rijndael($mode = CRYPT_RIJNDAEL_MODE_CBC)
{
parent::Crypt_Base($mode);
}
/**
* Sets the key.
*
* Keys can be of any length. Rijndael, itself, requires the use of a key that's between 128-bits and 256-bits long and
* whose length is a multiple of 32. If the key is less than 256-bits and the key length isn't set, we round the length
* up to the closest valid key length, padding $key with null bytes. If the key is more than 256-bits, we trim the
* excess bits.
*
* If the key is not explicitly set, it'll be assumed to be all null bytes.
*
* Note: 160/224-bit keys must explicitly set by setKeyLength(), otherwise they will be round/pad up to 192/256 bits.
*
* @see Crypt_Base:setKey()
* @see self::setKeyLength()
* @access public
* @param string $key
*/
function setKey($key)
{
if (!$this->explicit_key_length) {
$length = strlen($key);
switch (true) {
case $length <= 16:
$this->key_size = 16;
break;
case $length <= 20:
$this->key_size = 20;
break;
case $length <= 24:
$this->key_size = 24;
break;
case $length <= 28:
$this->key_size = 28;
break;
default:
$this->key_size = 32;
}
}
parent::setKey($key);
}
/**
* Sets the key length
* Sets the key length.
*
* Valid key lengths are 128, 160, 192, 224, and 256. If the length is less than 128, it will be rounded up to
* 128. If the length is greater than 128 and invalid, it will be rounded down to the closest valid amount.
@ -378,9 +236,9 @@ class Crypt_Rijndael extends Crypt_Base
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::Crypt_Base()
* @see \phpseclib\Crypt\Base::__construct()
* @param int $engine
* @access public
* @return bool
@ -388,14 +246,14 @@ class Crypt_Rijndael extends Crypt_Base
function isValidEngine($engine)
{
switch ($engine) {
case CRYPT_ENGINE_OPENSSL:
case self::ENGINE_OPENSSL:
if ($this->block_size != 16) {
return false;
}
$this->cipher_name_openssl_ecb = 'aes-' . ($this->key_length << 3) . '-ecb';
$this->cipher_name_openssl = 'aes-' . ($this->key_length << 3) . '-' . $this->_openssl_translate_mode();
break;
case CRYPT_ENGINE_MCRYPT:
case self::ENGINE_MCRYPT:
$this->cipher_name_mcrypt = 'rijndael-' . ($this->block_size << 3);
if ($this->key_length % 8) { // is it a 160/224-bit key?
// mcrypt is not usable for them, only for 128/192/256-bit keys
@ -600,7 +458,7 @@ class Crypt_Rijndael extends Crypt_Base
/**
* Setup the key (expansion)
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -732,9 +590,9 @@ class Crypt_Rijndael extends Crypt_Base
/**
* Provides the mixColumns and sboxes tables
*
* @see Crypt_Rijndael:_encryptBlock()
* @see Crypt_Rijndael:_setupInlineCrypt()
* @see Crypt_Rijndael:_subWord()
* @see self::_encryptBlock()
* @see self::_setupInlineCrypt()
* @see self::_subWord()
* @access private
* @return array &$tables
*/
@ -821,9 +679,9 @@ class Crypt_Rijndael extends Crypt_Base
/**
* Provides the inverse mixColumns and inverse sboxes tables
*
* @see Crypt_Rijndael:_decryptBlock()
* @see Crypt_Rijndael:_setupInlineCrypt()
* @see Crypt_Rijndael:_setupKey()
* @see self::_decryptBlock()
* @see self::_setupInlineCrypt()
* @see self::_setupKey()
* @access private
* @return array &$tables
*/
@ -905,7 +763,7 @@ class Crypt_Rijndael extends Crypt_Base
/**
* Setup the performance-optimized function for de/encrypt()
*
* @see Crypt_Base::_setupInlineCrypt()
* @see \phpseclib\Crypt\Base::_setupInlineCrypt()
* @access private
*/
function _setupInlineCrypt()
@ -914,7 +772,7 @@ class Crypt_Rijndael extends Crypt_Base
// So here we are'nt under the same heavy timing-stress as we are in _de/encryptBlock() or de/encrypt().
// However...the here generated function- $code, stored as php callback in $this->inline_crypt, must work as fast as even possible.
$lambda_functions =& Crypt_Rijndael::_getLambdaFunctions();
$lambda_functions =& self::_getLambdaFunctions();
// We create max. 10 hi-optimized code for memory reason. Means: For each $key one ultra fast inline-crypt function.
// (Currently, for Crypt_Rijndael/AES, one generated $lambda_function cost on php5.5@32bit ~80kb unfreeable mem and ~130kb on php5.5@64bit)

View File

@ -5,14 +5,14 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise. Operates in the EDE3 mode (encrypt-decrypt-encrypt).
*
* PHP versions 4 and 5
* PHP version 5
*
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/TripleDES.php';
* include 'vendor/autoload.php';
*
* $des = new Crypt_TripleDES();
* $des = new \phpseclib\Crypt\TripleDES();
*
* $des->setKey('abcdefghijklmnopqrstuvwx');
*
@ -26,78 +26,43 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_TripleDES
* @package TripleDES
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_DES
*/
if (!class_exists('Crypt_DES')) {
include_once 'DES.php';
}
/**#@+
* @access public
* @see self::Crypt_TripleDES()
*/
/**
* Encrypt / decrypt using inner chaining
*
* Inner chaining is used by SSH-1 and is generally considered to be less secure then outer chaining (CRYPT_DES_MODE_CBC3).
*/
define('CRYPT_MODE_3CBC', -2);
/**
* BC version of the above.
*/
define('CRYPT_DES_MODE_3CBC', -2);
/**
* Encrypt / decrypt using outer chaining
*
* Outer chaining is used by SSH-2 and when the mode is set to CRYPT_DES_MODE_CBC.
*/
define('CRYPT_MODE_CBC3', CRYPT_MODE_CBC);
/**
* BC version of the above.
*/
define('CRYPT_DES_MODE_CBC3', CRYPT_MODE_CBC3);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of Triple DES.
*
* @package Crypt_TripleDES
* @package TripleDES
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Crypt_TripleDES extends Crypt_DES
class TripleDES extends DES
{
/**
* Encrypt / decrypt using inner chaining
*
* Inner chaining is used by SSH-1 and is generally considered to be less secure then outer chaining (self::MODE_CBC3).
*/
const MODE_3CBC = -2;
/**
* Encrypt / decrypt using outer chaining
*
* Outer chaining is used by SSH-2 and when the mode is set to \phpseclib\Crypt\Base::MODE_CBC.
*/
const MODE_CBC3 = Base::MODE_CBC;
/**
* Key Length (in bytes)
*
* @see Crypt_TripleDES::setKeyLength()
* @see \phpseclib\Crypt\TripleDES::setKeyLength()
* @var int
* @access private
*/
@ -106,28 +71,18 @@ class Crypt_TripleDES extends Crypt_DES
/**
* The default salt used by setPassword()
*
* @see Crypt_Base::password_default_salt
* @see Crypt_Base::setPassword()
* @see \phpseclib\Crypt\Base::password_default_salt
* @see \phpseclib\Crypt\Base::setPassword()
* @var string
* @access private
*/
var $password_default_salt = 'phpseclib';
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_DES::const_namespace
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'DES';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_DES::cipher_name_mcrypt
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\DES::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -136,7 +91,7 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Optimizing value while CFB-encrypting
*
* @see Crypt_Base::cfb_init_len
* @see \phpseclib\Crypt\Base::cfb_init_len
* @var int
* @access private
*/
@ -146,14 +101,14 @@ class Crypt_TripleDES extends Crypt_DES
* max possible size of $key
*
* @see self::setKey()
* @see Crypt_DES::setKey()
* @see \phpseclib\Crypt\DES::setKey()
* @var string
* @access private
*/
var $key_length_max = 24;
/**
* Internal flag whether using CRYPT_DES_MODE_3CBC or not
* Internal flag whether using self::MODE_3CBC or not
*
* @var bool
* @access private
@ -161,7 +116,7 @@ class Crypt_TripleDES extends Crypt_DES
var $mode_3cbc;
/**
* The Crypt_DES objects
* The \phpseclib\Crypt\DES objects
*
* Used only if $mode_3cbc === true
*
@ -177,65 +132,65 @@ class Crypt_TripleDES extends Crypt_DES
*
* $mode could be:
*
* - CRYPT_DES_MODE_ECB
* - \phpseclib\Crypt\Base::MODE_ECB
*
* - CRYPT_DES_MODE_CBC
* - \phpseclib\Crypt\Base::MODE_CBC
*
* - CRYPT_DES_MODE_CTR
* - \phpseclib\Crypt\Base::MODE_CTR
*
* - CRYPT_DES_MODE_CFB
* - \phpseclib\Crypt\Base::MODE_CFB
*
* - CRYPT_DES_MODE_OFB
* - \phpseclib\Crypt\Base::MODE_OFB
*
* - CRYPT_DES_MODE_3CBC
* - \phpseclib\Crypt\TripleDES::MODE_3CBC
*
* If not explicitly set, CRYPT_DES_MODE_CBC will be used.
* If not explicitly set, \phpseclib\Crypt\Base::MODE_CBC will be used.
*
* @see Crypt_DES::Crypt_DES()
* @see Crypt_Base::Crypt_Base()
* @see \phpseclib\Crypt\DES::__construct()
* @see \phpseclib\Crypt\Base::__construct()
* @param int $mode
* @access public
*/
function Crypt_TripleDES($mode = CRYPT_MODE_CBC)
function __construct($mode = Base::MODE_CBC)
{
switch ($mode) {
// In case of CRYPT_DES_MODE_3CBC, we init as CRYPT_DES_MODE_CBC
// In case of self::MODE_3CBC, we init as CRYPT_DES_MODE_CBC
// and additional flag us internally as 3CBC
case CRYPT_DES_MODE_3CBC:
parent::Crypt_Base(CRYPT_MODE_CBC);
case self::MODE_3CBC:
parent::__construct(Base::MODE_CBC);
$this->mode_3cbc = true;
// This three $des'es will do the 3CBC work (if $key > 64bits)
$this->des = array(
new Crypt_DES(CRYPT_MODE_CBC),
new Crypt_DES(CRYPT_MODE_CBC),
new Crypt_DES(CRYPT_MODE_CBC),
new DES(Base::MODE_CBC),
new DES(Base::MODE_CBC),
new DES(Base::MODE_CBC),
);
// we're going to be doing the padding, ourselves, so disable it in the Crypt_DES objects
// we're going to be doing the padding, ourselves, so disable it in the \phpseclib\Crypt\DES objects
$this->des[0]->disablePadding();
$this->des[1]->disablePadding();
$this->des[2]->disablePadding();
break;
// If not 3CBC, we init as usual
default:
parent::Crypt_Base($mode);
parent::__construct($mode);
}
}
/**
* Test for engine validity
*
* This is mainly just a wrapper to set things up for Crypt_Base::isValidEngine()
* This is mainly just a wrapper to set things up for \phpseclib\Crypt\Base::isValidEngine()
*
* @see Crypt_Base::Crypt_Base()
* @see \phpseclib\Crypt\Base::__construct()
* @param int $engine
* @access public
* @return bool
*/
function isValidEngine($engine)
{
if ($engine == CRYPT_ENGINE_OPENSSL) {
if ($engine == self::ENGINE_OPENSSL) {
$this->cipher_name_openssl_ecb = 'des-ede3';
$mode = $this->_openssl_translate_mode();
$this->cipher_name_openssl = $mode == 'ecb' ? 'des-ede3' : 'des-ede3-' . $mode;
@ -247,10 +202,10 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Sets the initialization vector. (optional)
*
* SetIV is not required when CRYPT_DES_MODE_ECB is being used. If not explicitly set, it'll be assumed
* SetIV is not required when \phpseclib\Crypt\Base::MODE_ECB is being used. If not explicitly set, it'll be assumed
* to be all zero's.
*
* @see Crypt_Base::setIV()
* @see \phpseclib\Crypt\Base::setIV()
* @access public
* @param string $iv
*/
@ -269,7 +224,7 @@ class Crypt_TripleDES extends Crypt_DES
*
* Valid key lengths are 64, 128 and 192
*
* @see Crypt_Base:setKeyLength()
* @see \phpseclib\Crypt\Base:setKeyLength()
* @access public
* @param int $length
*/
@ -301,8 +256,8 @@ class Crypt_TripleDES extends Crypt_DES
* If the key is not explicitly set, it'll be assumed to be all null bytes.
*
* @access public
* @see Crypt_DES::setKey()
* @see Crypt_Base::setKey()
* @see \phpseclib\Crypt\DES::setKey()
* @see \phpseclib\Crypt\Base::setKey()
* @param string $key
*/
function setKey($key)
@ -318,7 +273,7 @@ class Crypt_TripleDES extends Crypt_DES
}
parent::setKey($key);
// And in case of CRYPT_DES_MODE_3CBC:
// And in case of self::MODE_3CBC:
// if key <= 64bits we not need the 3 $des to work,
// because we will then act as regular DES-CBC with just a <= 64bit key.
// So only if the key > 64bits (> 8 bytes) we will call setKey() for the 3 $des.
@ -332,7 +287,7 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Encrypts a message.
*
* @see Crypt_Base::encrypt()
* @see \phpseclib\Crypt\Base::encrypt()
* @access public
* @param string $plaintext
* @return string $cipertext
@ -340,7 +295,7 @@ class Crypt_TripleDES extends Crypt_DES
function encrypt($plaintext)
{
// parent::en/decrypt() is able to do all the work for all modes and keylengths,
// except for: CRYPT_MODE_3CBC (inner chaining CBC) with a key > 64bits
// except for: self::MODE_3CBC (inner chaining CBC) with a key > 64bits
// if the key is smaller then 8, do what we'd normally do
if ($this->mode_3cbc && strlen($this->key) > 8) {
@ -359,7 +314,7 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Decrypts a message.
*
* @see Crypt_Base::decrypt()
* @see \phpseclib\Crypt\Base::decrypt()
* @access public
* @param string $ciphertext
* @return string $plaintext
@ -410,12 +365,12 @@ class Crypt_TripleDES extends Crypt_DES
* outputs. The reason is due to the fact that the initialization vector's change after every encryption /
* decryption round when the continuous buffer is enabled. When it's disabled, they remain constant.
*
* Put another way, when the continuous buffer is enabled, the state of the Crypt_DES() object changes after each
* Put another way, when the continuous buffer is enabled, the state of the \phpseclib\Crypt\DES() object changes after each
* encryption / decryption round, whereas otherwise, it'd remain constant. For this reason, it's recommended that
* continuous buffers not be used. They do offer better security and are, in fact, sometimes required (SSH uses them),
* however, they are also less intuitive and more likely to cause you problems.
*
* @see Crypt_Base::enableContinuousBuffer()
* @see \phpseclib\Crypt\Base::enableContinuousBuffer()
* @see self::disableContinuousBuffer()
* @access public
*/
@ -434,7 +389,7 @@ class Crypt_TripleDES extends Crypt_DES
*
* The default behavior.
*
* @see Crypt_Base::disableContinuousBuffer()
* @see \phpseclib\Crypt\Base::disableContinuousBuffer()
* @see self::enableContinuousBuffer()
* @access public
*/
@ -451,8 +406,8 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Creates the key schedule
*
* @see Crypt_DES::_setupKey()
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\DES::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -486,8 +441,8 @@ class Crypt_TripleDES extends Crypt_DES
/**
* Sets the internal crypt engine
*
* @see Crypt_Base::Crypt_Base()
* @see Crypt_Base::setPreferredEngine()
* @see \phpseclib\Crypt\Base::__construct()
* @see \phpseclib\Crypt\Base::setPreferredEngine()
* @param int $engine
* @access public
* @return int

View File

@ -5,7 +5,7 @@
*
* Uses mcrypt, if available, and an internal implementation, otherwise.
*
* PHP versions 4 and 5
* PHP version 5
*
* Useful resources are as follows:
*
@ -14,9 +14,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Crypt/Twofish.php';
* include 'vendor/autoload.php';
*
* $twofish = new Crypt_Twofish();
* $twofish = new \phpseclib\Crypt\Twofish();
*
* $twofish->setKey('12345678901234567890123456789012');
*
@ -26,26 +26,8 @@
* ?>
* </code>
*
* 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 Crypt
* @package Crypt_Twofish
* @package Twofish
* @author Jim Wigginton <terrafrost@php.net>
* @author Hans-Juergen Petrich <petrich@tronic-media.com>
* @copyright 2007 Jim Wigginton
@ -53,77 +35,22 @@
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Crypt_Base
*
* Base cipher class
*/
if (!class_exists('Crypt_Base')) {
include_once 'Base.php';
}
/**#@+
* @access public
* @see self::encrypt()
* @see self::decrypt()
*/
/**
* Encrypt / decrypt using the Counter mode.
*
* Set to -1 since that's what Crypt/Random.php uses to index the CTR mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Counter_.28CTR.29
*/
define('CRYPT_TWOFISH_MODE_CTR', CRYPT_MODE_CTR);
/**
* Encrypt / decrypt using the Electronic Code Book mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Electronic_codebook_.28ECB.29
*/
define('CRYPT_TWOFISH_MODE_ECB', CRYPT_MODE_ECB);
/**
* Encrypt / decrypt using the Code Book Chaining mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher-block_chaining_.28CBC.29
*/
define('CRYPT_TWOFISH_MODE_CBC', CRYPT_MODE_CBC);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Cipher_feedback_.28CFB.29
*/
define('CRYPT_TWOFISH_MODE_CFB', CRYPT_MODE_CFB);
/**
* Encrypt / decrypt using the Cipher Feedback mode.
*
* @link http://en.wikipedia.org/wiki/Block_cipher_modes_of_operation#Output_feedback_.28OFB.29
*/
define('CRYPT_TWOFISH_MODE_OFB', CRYPT_MODE_OFB);
/**#@-*/
namespace phpseclib\Crypt;
/**
* Pure-PHP implementation of Twofish.
*
* @package Crypt_Twofish
* @package Twofish
* @author Jim Wigginton <terrafrost@php.net>
* @author Hans-Juergen Petrich <petrich@tronic-media.com>
* @access public
*/
class Crypt_Twofish extends Crypt_Base
class Twofish extends Base
{
/**
* The namespace used by the cipher for its constants.
*
* @see Crypt_Base::const_namespace
* @var string
* @access private
*/
var $const_namespace = 'TWOFISH';
/**
* The mcrypt specific name of the cipher
*
* @see Crypt_Base::cipher_name_mcrypt
* @see \phpseclib\Crypt\Base::cipher_name_mcrypt
* @var string
* @access private
*/
@ -132,7 +59,7 @@ class Crypt_Twofish extends Crypt_Base
/**
* Optimizing value while CFB-encrypting
*
* @see Crypt_Base::cfb_init_len
* @see \phpseclib\Crypt\Base::cfb_init_len
* @var int
* @access private
*/
@ -468,7 +395,7 @@ class Crypt_Twofish extends Crypt_Base
/**
* Setup the key (expansion)
*
* @see Crypt_Base::_setupKey()
* @see \phpseclib\Crypt\Base::_setupKey()
* @access private
*/
function _setupKey()
@ -735,18 +662,18 @@ class Crypt_Twofish extends Crypt_Base
/**
* Setup the performance-optimized function for de/encrypt()
*
* @see Crypt_Base::_setupInlineCrypt()
* @see \phpseclib\Crypt\Base::_setupInlineCrypt()
* @access private
*/
function _setupInlineCrypt()
{
$lambda_functions =& Crypt_Twofish::_getLambdaFunctions();
$lambda_functions =& self::_getLambdaFunctions();
// Max. 10 Ultra-Hi-optimized inline-crypt functions. After that, we'll (still) create very fast code, but not the ultimate fast one.
// (Currently, for Crypt_Twofish, one generated $lambda_function cost on php5.5@32bit ~140kb unfreeable mem and ~240kb on php5.5@64bit)
$gen_hi_opt_code = (bool)(count($lambda_functions) < 10);
// Generation of a uniqe hash for our generated code
// Generation of a unique hash for our generated code
$code_hash = "Crypt_Twofish, {$this->mode}";
if ($gen_hi_opt_code) {
$code_hash = str_pad($code_hash, 32) . $this->_hashInlineCryptFunction($this->key);

View File

@ -3,47 +3,31 @@
/**
* Pure-PHP ANSI Decoder
*
* PHP versions 4 and 5
* PHP version 5
*
* If you call read() in Net_SSH2 you may get {@link http://en.wikipedia.org/wiki/ANSI_escape_code ANSI escape codes} back.
* If you call read() in \phpseclib\Net\SSH2 you may get {@link http://en.wikipedia.org/wiki/ANSI_escape_code ANSI escape codes} back.
* They'd look like chr(0x1B) . '[00m' or whatever (0x1B = ESC). They tell a
* {@link http://en.wikipedia.org/wiki/Terminal_emulator terminal emulator} how to format the characters, what
* color to display them in, etc. File_ANSI is a {@link http://en.wikipedia.org/wiki/VT100 VT100} terminal emulator.
*
* 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.
* color to display them in, etc. \phpseclib\File\ANSI is a {@link http://en.wikipedia.org/wiki/VT100 VT100} terminal emulator.
*
* @category File
* @package File_ANSI
* @package ANSI
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2012 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
namespace phpseclib\File;
/**
* Pure-PHP ANSI Decoder
*
* @package File_ANSI
* @package ANSI
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class File_ANSI
class ANSI
{
/**
* Max Width
@ -176,20 +160,20 @@ class File_ANSI
/**
* Default Constructor.
*
* @return File_ANSI
* @return \phpseclib\File\ANSI
* @access public
*/
function File_ANSI()
function __construct()
{
$attr_cell = new stdClass();
$attr_cell = new \stdClass();
$attr_cell->bold = false;
$attr_cell->underline = false;
$attr_cell->blink = false;
$attr_cell->background = 'black';
$attr_cell->foreground = 'white';
$attr_cell->reverse = false;
$this->base_attr_cell = clone($attr_cell);
$this->attr_cell = clone($attr_cell);
$this->base_attr_cell = clone $attr_cell;
$this->attr_cell = clone $attr_cell;
$this->setHistory(200);
$this->setDimensions(80, 24);
@ -330,7 +314,7 @@ class File_ANSI
foreach ($mods as $mod) {
switch ($mod) {
case 0: // Turn off character attributes
$attr_cell = clone($this->base_attr_cell);
$attr_cell = clone $this->base_attr_cell;
break;
case 1: // Turn bold mode on
$attr_cell->bold = true;
@ -400,7 +384,7 @@ class File_ANSI
case "\x08": // backspace
if ($this->x) {
$this->x--;
$this->attrs[$this->y][$this->x] = clone($this->base_attr_cell);
$this->attrs[$this->y][$this->x] = clone $this->base_attr_cell;
$this->screen[$this->y] = substr_replace(
$this->screen[$this->y],
$source[$i],
@ -419,7 +403,7 @@ class File_ANSI
$this->ansi.= "\x1B";
break;
default:
$this->attrs[$this->y][$this->x] = clone($this->attr_cell);
$this->attrs[$this->y][$this->x] = clone $this->attr_cell;
if ($this->x > strlen($this->screen[$this->y])) {
$this->screen[$this->y] = str_repeat(' ', $this->x);
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,47 @@
<?php
/**
* Pure-PHP ASN.1 Parser
*
* PHP version 5
*
* @category File
* @package ASN1
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2012 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
namespace phpseclib\File\ASN1;
/**
* ASN.1 Element
*
* Bypass normal encoding rules in phpseclib\File\ASN1::encodeDER()
*
* @package ASN1
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Element
{
/**
* Raw element value
*
* @var string
* @access private
*/
var $element;
/**
* Constructor
*
* @param string $encoded
* @return \phpseclib\File\ASN1\Element
* @access public
*/
function __construct($encoded)
{
$this->element = $encoded;
}
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -3,90 +3,73 @@
/**
* Pure-PHP implementation of SCP.
*
* PHP versions 4 and 5
* PHP version 5
*
* The API for this library is modeled after the API from PHP's {@link http://php.net/book.ftp FTP extension}.
*
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Net/SCP.php';
* include 'Net/SSH2.php';
* include 'vendor/autoload.php';
*
* $ssh = new Net_SSH2('www.domain.tld');
* $ssh = new \phpseclib\Net\SSH2('www.domain.tld');
* if (!$ssh->login('username', 'password')) {
* exit('bad login');
* }
* $scp = new \phpseclib\Net\SCP($ssh);
*
* $scp = new Net_SCP($ssh);
* $scp->put('abcd', str_repeat('x', 1024*1024));
* ?>
* </code>
*
* 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 Net
* @package Net_SCP
* @package SCP
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2010 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**#@+
* @access public
* @see self::put()
*/
/**
* Reads data from a local file.
*/
define('NET_SCP_LOCAL_FILE', 1);
/**
* Reads data from a string.
*/
define('NET_SCP_STRING', 2);
/**#@-*/
/**#@+
* @access private
* @see self::_send()
* @see self::_receive()
*/
/**
* SSH1 is being used.
*/
define('NET_SCP_SSH1', 1);
/**
* SSH2 is being used.
*/
define('NET_SCP_SSH2', 2);
/**#@-*/
namespace phpseclib\Net;
/**
* Pure-PHP implementations of SCP.
*
* @package Net_SCP
* @package SCP
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Net_SCP
class SCP
{
/**#@+
* @access public
* @see \phpseclib\Net\SCP::put()
*/
/**
* Reads data from a local file.
*/
const SOURCE_LOCAL_FILE = 1;
/**
* Reads data from a string.
*/
const SOURCE_STRING = 2;
/**#@-*/
/**#@+
* @access private
* @see \phpseclib\Net\SCP::_send()
* @see \phpseclib\Net\SCP::_receive()
*/
/**
* SSH1 is being used.
*/
const MODE_SSH1 = 1;
/**
* SSH2 is being used.
*/
const MODE_SSH2 = 2;
/**#@-*/
/**
* SSH Object
*
@ -116,27 +99,18 @@ class Net_SCP
*
* Connects to an SSH server
*
* @param string $host
* @param int $port
* @param int $timeout
* @return Net_SCP
* @param \phpseclib\Net\SSH1|\phpseclib\Net\SSH2 $ssh
* @return \phpseclib\Net\SCP
* @access public
*/
function Net_SCP($ssh)
function __construct($ssh)
{
if (!is_object($ssh)) {
return;
}
switch (strtolower(get_class($ssh))) {
case 'net_ssh2':
$this->mode = NET_SCP_SSH2;
break;
case 'net_ssh1':
if ($ssh instanceof SSH2) {
$this->mode = self::MODE_SSH2;
} elseif ($ssh instanceof SSH1) {
$this->packet_size = 50000;
$this->mode = NET_SCP_SSH1;
break;
default:
$this->mode = self::MODE_SSH1;
} else {
return;
}
@ -146,11 +120,11 @@ class Net_SCP
/**
* Uploads a file to the SCP server.
*
* By default, Net_SCP::put() does not read from the local filesystem. $data is dumped directly into $remote_file.
* So, for example, if you set $data to 'filename.ext' and then do Net_SCP::get(), you will get a file, twelve bytes
* By default, \phpseclib\Net\SCP::put() does not read from the local filesystem. $data is dumped directly into $remote_file.
* So, for example, if you set $data to 'filename.ext' and then do \phpseclib\Net\SCP::get(), you will get a file, twelve bytes
* long, containing 'filename.ext' as its contents.
*
* Setting $mode to NET_SCP_LOCAL_FILE will change the above behavior. With NET_SCP_LOCAL_FILE, $remote_file will
* Setting $mode to self::SOURCE_LOCAL_FILE will change the above behavior. With self::SOURCE_LOCAL_FILE, $remote_file will
* contain as many bytes as filename.ext does on your local filesystem. If your filename.ext is 1MB then that is how
* large $remote_file will be, as well.
*
@ -164,7 +138,7 @@ class Net_SCP
* @return bool
* @access public
*/
function put($remote_file, $data, $mode = NET_SCP_STRING, $callback = null)
function put($remote_file, $data, $mode = self::SOURCE_STRING, $callback = null)
{
if (!isset($this->ssh)) {
return false;
@ -179,13 +153,13 @@ class Net_SCP
return false;
}
if ($this->mode == NET_SCP_SSH2) {
$this->packet_size = $this->ssh->packet_size_client_to_server[NET_SSH2_CHANNEL_EXEC] - 4;
if ($this->mode == self::MODE_SSH2) {
$this->packet_size = $this->ssh->packet_size_client_to_server[SSH2::CHANNEL_EXEC] - 4;
}
$remote_file = basename($remote_file);
if ($mode == NET_SCP_STRING) {
if ($mode == self::SOURCE_STRING) {
$size = strlen($data);
} else {
if (!is_file($data)) {
@ -209,7 +183,7 @@ class Net_SCP
$sent = 0;
while ($sent < $size) {
$temp = $mode & NET_SCP_STRING ? substr($data, $sent, $this->packet_size) : fread($fp, $this->packet_size);
$temp = $mode & self::SOURCE_STRING ? substr($data, $sent, $this->packet_size) : fread($fp, $this->packet_size);
$this->_send($temp);
$sent+= strlen($temp);
@ -219,7 +193,7 @@ class Net_SCP
}
$this->_close();
if ($mode != NET_SCP_STRING) {
if ($mode != self::SOURCE_STRING) {
fclose($fp);
}
@ -297,10 +271,10 @@ class Net_SCP
function _send($data)
{
switch ($this->mode) {
case NET_SCP_SSH2:
$this->ssh->_send_channel_packet(NET_SSH2_CHANNEL_EXEC, $data);
case self::MODE_SSH2:
$this->ssh->_send_channel_packet(SSH2::CHANNEL_EXEC, $data);
break;
case NET_SCP_SSH1:
case self::MODE_SSH1:
$data = pack('CNa*', NET_SSH1_CMSG_STDIN_DATA, strlen($data), $data);
$this->ssh->_send_binary_packet($data);
}
@ -315,18 +289,21 @@ class Net_SCP
function _receive()
{
switch ($this->mode) {
case NET_SCP_SSH2:
return $this->ssh->_get_channel_packet(NET_SSH2_CHANNEL_EXEC, true);
case NET_SCP_SSH1:
case self::MODE_SSH2:
return $this->ssh->_get_channel_packet(SSH2::CHANNEL_EXEC, true);
case self::MODE_SSH1:
if (!$this->ssh->bitmap) {
return false;
}
while (true) {
$response = $this->ssh->_get_binary_packet();
switch ($response[NET_SSH1_RESPONSE_TYPE]) {
switch ($response[SSH1::RESPONSE_TYPE]) {
case NET_SSH1_SMSG_STDOUT_DATA:
extract(unpack('Nlength', $response[NET_SSH1_RESPONSE_DATA]));
return $this->ssh->_string_shift($response[NET_SSH1_RESPONSE_DATA], $length);
if (strlen($response[SSH1::RESPONSE_DATA]) < 4) {
return false;
}
extract(unpack('Nlength', $response[SSH1::RESPONSE_DATA]));
return $this->ssh->_string_shift($response[SSH1::RESPONSE_DATA], $length);
case NET_SSH1_SMSG_STDERR_DATA:
break;
case NET_SSH1_SMSG_EXITSTATUS:
@ -350,10 +327,10 @@ class Net_SCP
function _close()
{
switch ($this->mode) {
case NET_SCP_SSH2:
$this->ssh->_close_channel(NET_SSH2_CHANNEL_EXEC, true);
case self::MODE_SSH2:
$this->ssh->_close_channel(SSH2::CHANNEL_EXEC, true);
break;
case NET_SCP_SSH1:
case self::MODE_SSH1:
$this->ssh->disconnect();
}
}

View File

@ -3,7 +3,7 @@
/**
* Pure-PHP implementation of SFTP.
*
* PHP versions 4 and 5
* PHP version 5
*
* Currently only supports SFTPv2 and v3, which, according to wikipedia.org, "is the most widely used version,
* implemented by the popular OpenSSH SFTP server". If you want SFTPv4/5/6 support, provide me with access
@ -14,9 +14,9 @@
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Net/SFTP.php';
* include 'vendor/autoload.php';
*
* $sftp = new Net_SFTP('www.domain.tld');
* $sftp = new \phpseclib\Net\SFTP('www.domain.tld');
* if (!$sftp->login('username', 'password')) {
* exit('Login Failed');
* }
@ -27,109 +27,68 @@
* ?>
* </code>
*
* 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 Net
* @package Net_SFTP
* @package SFTP
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2009 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
/**
* Include Net_SSH2
*/
if (!class_exists('Net_SSH2')) {
include_once 'SSH2.php';
}
/**#@+
* @access public
* @see self::getLog()
*/
/**
* Returns the message numbers
*/
define('NET_SFTP_LOG_SIMPLE', NET_SSH2_LOG_SIMPLE);
/**
* Returns the message content
*/
define('NET_SFTP_LOG_COMPLEX', NET_SSH2_LOG_COMPLEX);
/**
* Outputs the message content in real-time.
*/
define('NET_SFTP_LOG_REALTIME', 3);
/**#@-*/
/**
* SFTP channel constant
*
* Net_SSH2::exec() uses 0 and Net_SSH2::read() / Net_SSH2::write() use 1.
*
* @see Net_SSH2::_send_channel_packet()
* @see Net_SSH2::_get_channel_packet()
* @access private
*/
define('NET_SFTP_CHANNEL', 0x100);
/**#@+
* @access public
* @see self::put()
*/
/**
* Reads data from a local file.
*/
define('NET_SFTP_LOCAL_FILE', 1);
/**
* Reads data from a string.
*/
// this value isn't really used anymore but i'm keeping it reserved for historical reasons
define('NET_SFTP_STRING', 2);
/**
* Reads data from callback:
* function callback($length) returns string to proceed, null for EOF
*/
define('NET_SFTP_CALLBACK', 16);
/**
* Resumes an upload
*/
define('NET_SFTP_RESUME', 4);
/**
* Append a local file to an already existing remote file
*/
define('NET_SFTP_RESUME_START', 8);
/**#@-*/
namespace phpseclib\Net;
/**
* Pure-PHP implementations of SFTP.
*
* @package Net_SFTP
* @package SFTP
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Net_SFTP extends Net_SSH2
class SFTP extends SSH2
{
/**
* SFTP channel constant
*
* \phpseclib\Net\SSH2::exec() uses 0 and \phpseclib\Net\SSH2::read() / \phpseclib\Net\SSH2::write() use 1.
*
* @see \phpseclib\Net\SSH2::_send_channel_packet()
* @see \phpseclib\Net\SSH2::_get_channel_packet()
* @access private
*/
const CHANNEL = 0x100;
/**#@+
* @access public
* @see \phpseclib\Net\SFTP::put()
*/
/**
* Reads data from a local file.
*/
const SOURCE_LOCAL_FILE = 1;
/**
* Reads data from a string.
*/
// this value isn't really used anymore but i'm keeping it reserved for historical reasons
const SOURCE_STRING = 2;
/**
* Reads data from callback:
* function callback($length) returns string to proceed, null for EOF
*/
const SOURCE_CALLBACK = 16;
/**
* Resumes an upload
*/
const RESUME = 4;
/**
* Append a local file to an already existing remote file
*/
const RESUME_START = 8;
/**#@-*/
/**
* Packet Types
*
* @see self::Net_SFTP()
* @see self::__construct()
* @var array
* @access private
*/
@ -138,7 +97,7 @@ class Net_SFTP extends Net_SSH2
/**
* Status Codes
*
* @see self::Net_SFTP()
* @see self::__construct()
* @var array
* @access private
*/
@ -250,7 +209,7 @@ class Net_SFTP extends Net_SSH2
/**
* Max SFTP Packet Size
*
* @see self::Net_SFTP()
* @see self::__construct()
* @see self::get()
* @var array
* @access private
@ -285,12 +244,12 @@ class Net_SFTP extends Net_SSH2
* @param string $host
* @param int $port
* @param int $timeout
* @return Net_SFTP
* @return \phpseclib\Net\SFTP
* @access public
*/
function Net_SFTP($host, $port = 22, $timeout = 10)
function __construct($host, $port = 22, $timeout = 10)
{
parent::Net_SSH2($host, $port, $timeout);
parent::__construct($host, $port, $timeout);
$this->max_sftp_packet = 1 << 15;
@ -366,7 +325,7 @@ class Net_SFTP extends Net_SSH2
31 => 'NET_SFTP_STATUS_NO_MATCHING_BYTE_RANGE_LOCK'
);
// http://tools.ietf.org/html/draft-ietf-secsh-filexfer-13#section-7.1
// the order, in this case, matters quite a lot - see Net_SFTP::_parseAttributes() to understand why
// the order, in this case, matters quite a lot - see \phpseclib\Net\SFTP::_parseAttributes() to understand why
$this->attributes = array(
0x00000001 => 'NET_SFTP_ATTR_SIZE',
0x00000002 => 'NET_SFTP_ATTR_UIDGID', // defined in SFTPv3, removed in SFTPv4+
@ -380,7 +339,7 @@ class Net_SFTP extends Net_SSH2
);
// http://tools.ietf.org/html/draft-ietf-secsh-filexfer-04#section-6.3
// the flag definitions change somewhat in SFTPv5+. if SFTPv5+ support is added to this library, maybe name
// the array for that $this->open5_flags and similarily alter the constant names.
// the array for that $this->open5_flags and similarly alter the constant names.
$this->open_flags = array(
0x00000001 => 'NET_SFTP_OPEN_READ',
0x00000002 => 'NET_SFTP_OPEN_WRITE',
@ -390,7 +349,7 @@ class Net_SFTP extends Net_SSH2
0x00000020 => 'NET_SFTP_OPEN_EXCL'
);
// http://tools.ietf.org/html/draft-ietf-secsh-filexfer-04#section-5.2
// see Net_SFTP::_parseLongname() for an explanation
// see \phpseclib\Net\SFTP::_parseLongname() for an explanation
$this->file_types = array(
1 => 'NET_SFTP_TYPE_REGULAR',
2 => 'NET_SFTP_TYPE_DIRECTORY',
@ -413,7 +372,7 @@ class Net_SFTP extends Net_SSH2
);
if (!defined('NET_SFTP_QUEUE_SIZE')) {
define('NET_SFTP_QUEUE_SIZE', 50);
define('NET_SFTP_QUEUE_SIZE', 32);
}
}
@ -432,14 +391,14 @@ class Net_SFTP extends Net_SSH2
return false;
}
$this->window_size_server_to_client[NET_SFTP_CHANNEL] = $this->window_size;
$this->window_size_server_to_client[self::CHANNEL] = $this->window_size;
$packet = pack(
'CNa*N3',
NET_SSH2_MSG_CHANNEL_OPEN,
strlen('session'),
'session',
NET_SFTP_CHANNEL,
self::CHANNEL,
$this->window_size,
0x4000
);
@ -448,9 +407,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
$this->channel_status[NET_SFTP_CHANNEL] = NET_SSH2_MSG_CHANNEL_OPEN;
$this->channel_status[self::CHANNEL] = NET_SSH2_MSG_CHANNEL_OPEN;
$response = $this->_get_channel_packet(NET_SFTP_CHANNEL);
$response = $this->_get_channel_packet(self::CHANNEL);
if ($response === false) {
return false;
}
@ -458,7 +417,7 @@ class Net_SFTP extends Net_SSH2
$packet = pack(
'CNNa*CNa*',
NET_SSH2_MSG_CHANNEL_REQUEST,
$this->server_channels[NET_SFTP_CHANNEL],
$this->server_channels[self::CHANNEL],
strlen('subsystem'),
'subsystem',
1,
@ -469,9 +428,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
$this->channel_status[NET_SFTP_CHANNEL] = NET_SSH2_MSG_CHANNEL_REQUEST;
$this->channel_status[self::CHANNEL] = NET_SSH2_MSG_CHANNEL_REQUEST;
$response = $this->_get_channel_packet(NET_SFTP_CHANNEL);
$response = $this->_get_channel_packet(self::CHANNEL);
if ($response === false) {
// from PuTTY's psftp.exe
$command = "test -x /usr/lib/sftp-server && exec /usr/lib/sftp-server\n" .
@ -482,7 +441,7 @@ class Net_SFTP extends Net_SSH2
$packet = pack(
'CNNa*CNa*',
NET_SSH2_MSG_CHANNEL_REQUEST,
$this->server_channels[NET_SFTP_CHANNEL],
$this->server_channels[self::CHANNEL],
strlen('exec'),
'exec',
1,
@ -493,15 +452,15 @@ class Net_SFTP extends Net_SSH2
return false;
}
$this->channel_status[NET_SFTP_CHANNEL] = NET_SSH2_MSG_CHANNEL_REQUEST;
$this->channel_status[self::CHANNEL] = NET_SSH2_MSG_CHANNEL_REQUEST;
$response = $this->_get_channel_packet(NET_SFTP_CHANNEL);
$response = $this->_get_channel_packet(self::CHANNEL);
if ($response === false) {
return false;
}
}
$this->channel_status[NET_SFTP_CHANNEL] = NET_SSH2_MSG_CHANNEL_DATA;
$this->channel_status[self::CHANNEL] = NET_SSH2_MSG_CHANNEL_DATA;
if (!$this->_send_sftp_packet(NET_SFTP_INIT, "\0\0\0\3")) {
return false;
@ -513,11 +472,20 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nversion', $this->_string_shift($response, 4)));
$this->version = $version;
while (!empty($response)) {
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$key = $this->_string_shift($response, $length);
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$value = $this->_string_shift($response, $length);
$this->extensions[$key] = $value;
@ -559,7 +527,7 @@ class Net_SFTP extends Net_SSH2
So what do you do if you have a client whose initial SSH_FXP_INIT packet says it implements v3 and
a server whose initial SSH_FXP_VERSION reply says it implements v4 and only v4? If it only implements
v4, the "versions" extension is likely not going to have been sent so version re-negotiation as discussed
in draft-ietf-secsh-filexfer-13 would be quite impossible. As such, what Net_SFTP would do is close the
in draft-ietf-secsh-filexfer-13 would be quite impossible. As such, what \phpseclib\Net\SFTP would do is close the
channel and reopen it with a new and updated SSH_FXP_INIT packet.
*/
switch ($this->version) {
@ -628,12 +596,15 @@ class Net_SFTP extends Net_SSH2
function _logError($response, $status = -1)
{
if ($status == -1) {
if (strlen($response) < 4) {
return;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
}
$error = $this->status_codes[$status];
if ($this->version > 2) {
if ($this->version > 2 || strlen($response) < 4) {
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$this->sftp_errors[] = $error . ': ' . $this->_string_shift($response, $length);
} else {
@ -641,6 +612,21 @@ class Net_SFTP extends Net_SSH2
}
}
/**
* Returns canonicalized absolute pathname
*
* realpath() expands all symbolic links and resolves references to '/./', '/../' and extra '/' characters in the input
* path and returns the canonicalized absolute pathname.
*
* @param string $path
* @return mixed
* @access public
*/
function realpath($path)
{
return $this->_realpath($path);
}
/**
* Canonicalize the Server-Side Path Name
*
@ -667,6 +653,9 @@ class Net_SFTP extends Net_SSH2
// should work on all SFTP versions since the only part of the SSH_FXP_NAME packet the following looks
// at is the first part and that part is defined the same in SFTP versions 3 through 6.
$this->_string_shift($response, 4); // skip over the count - it should be 1, anyway
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
return $this->_string_shift($response, $length);
case NET_SFTP_STATUS:
@ -710,7 +699,7 @@ class Net_SFTP extends Net_SSH2
*/
function chdir($dir)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -739,7 +728,7 @@ class Net_SFTP extends Net_SSH2
return false;
}
// see Net_SFTP::nlist() for a more thorough explanation of the following
// see \phpseclib\Net\SFTP::nlist() for a more thorough explanation of the following
$response = $this->_get_sftp_packet();
switch ($this->packet_type) {
case NET_SFTP_HANDLE:
@ -856,7 +845,7 @@ class Net_SFTP extends Net_SSH2
*/
function _list($dir, $raw = true)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -901,10 +890,19 @@ class Net_SFTP extends Net_SSH2
$response = $this->_get_sftp_packet();
switch ($this->packet_type) {
case NET_SFTP_NAME:
if (strlen($response) < 4) {
return false;
}
extract(unpack('Ncount', $this->_string_shift($response, 4)));
for ($i = 0; $i < $count; $i++) {
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$shortname = $this->_string_shift($response, $length);
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$longname = $this->_string_shift($response, $length);
$attributes = $this->_parseAttributes($response);
@ -931,6 +929,9 @@ class Net_SFTP extends Net_SSH2
}
break;
case NET_SFTP_STATUS:
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_EOF) {
$this->_logError($response, $status);
@ -1065,7 +1066,7 @@ class Net_SFTP extends Net_SSH2
*/
function size($filename)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1179,7 +1180,7 @@ class Net_SFTP extends Net_SSH2
*/
function stat($filename)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1236,7 +1237,7 @@ class Net_SFTP extends Net_SSH2
*/
function lstat($filename)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1293,7 +1294,7 @@ class Net_SFTP extends Net_SSH2
/**
* Returns general information about a file or symbolic link
*
* Determines information without calling Net_SFTP::_realpath().
* Determines information without calling \phpseclib\Net\SFTP::_realpath().
* The second parameter can be either NET_SFTP_STAT or NET_SFTP_LSTAT.
*
* @param string $filename
@ -1350,7 +1351,7 @@ class Net_SFTP extends Net_SSH2
*/
function touch($filename, $time = null, $atime = null)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1488,7 +1489,7 @@ class Net_SFTP extends Net_SSH2
*/
function _setstat($filename, $attr, $recursive)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1525,6 +1526,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -1615,7 +1619,7 @@ class Net_SFTP extends Net_SSH2
*/
function readlink($link)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1637,12 +1641,18 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Ncount', $this->_string_shift($response, 4)));
// the file isn't a symlink
if (!$count) {
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
return $this->_string_shift($response, $length);
}
@ -1659,11 +1669,11 @@ class Net_SFTP extends Net_SSH2
*/
function symlink($target, $link)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
$target = $this->_realpath($target);
//$target = $this->_realpath($target);
$link = $this->_realpath($link);
$packet = pack('Na*Na*', strlen($target), $target, strlen($link), $link);
@ -1677,6 +1687,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -1695,7 +1708,7 @@ class Net_SFTP extends Net_SSH2
*/
function mkdir($dir, $mode = -1, $recursive = false)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1740,6 +1753,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -1758,7 +1774,7 @@ class Net_SFTP extends Net_SSH2
*/
function rmdir($dir)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1777,6 +1793,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
// presumably SSH_FX_NO_SUCH_FILE or SSH_FX_PERMISSION_DENIED?
@ -1796,39 +1815,37 @@ class Net_SFTP extends Net_SSH2
/**
* Uploads a file to the SFTP server.
*
* By default, Net_SFTP::put() does not read from the local filesystem. $data is dumped directly into $remote_file.
* So, for example, if you set $data to 'filename.ext' and then do Net_SFTP::get(), you will get a file, twelve bytes
* By default, \phpseclib\Net\SFTP::put() does not read from the local filesystem. $data is dumped directly into $remote_file.
* So, for example, if you set $data to 'filename.ext' and then do \phpseclib\Net\SFTP::get(), you will get a file, twelve bytes
* long, containing 'filename.ext' as its contents.
*
* Setting $mode to NET_SFTP_LOCAL_FILE will change the above behavior. With NET_SFTP_LOCAL_FILE, $remote_file will
* Setting $mode to self::SOURCE_LOCAL_FILE will change the above behavior. With self::SOURCE_LOCAL_FILE, $remote_file will
* contain as many bytes as filename.ext does on your local filesystem. If your filename.ext is 1MB then that is how
* large $remote_file will be, as well.
*
* Setting $mode to self::SOURCE_CALLBACK will use $data as callback function, which gets only one parameter -- number of bytes to return, and returns a string if there is some data or null if there is no more data
*
* If $data is a resource then it'll be used as a resource instead.
*
*
* Setting $mode to NET_SFTP_CALLBACK will use $data as callback function, which gets only one parameter -- number
* of bytes to return, and returns a string if there is some data or null if there is no more data
*
* Currently, only binary mode is supported. As such, if the line endings need to be adjusted, you will need to take
* care of that, yourself.
*
* $mode can take an additional two parameters - NET_SFTP_RESUME and NET_SFTP_RESUME_START. These are bitwise AND'd with
* $mode can take an additional two parameters - self::RESUME and self::RESUME_START. These are bitwise AND'd with
* $mode. So if you want to resume upload of a 300mb file on the local file system you'd set $mode to the following:
*
* NET_SFTP_LOCAL_FILE | NET_SFTP_RESUME
* self::SOURCE_LOCAL_FILE | self::RESUME
*
* If you wanted to simply append the full contents of a local file to the full contents of a remote file you'd replace
* NET_SFTP_RESUME with NET_SFTP_RESUME_START.
* self::RESUME with self::RESUME_START.
*
* If $mode & (NET_SFTP_RESUME | NET_SFTP_RESUME_START) then NET_SFTP_RESUME_START will be assumed.
* If $mode & (self::RESUME | self::RESUME_START) then self::RESUME_START will be assumed.
*
* $start and $local_start give you more fine grained control over this process and take precident over NET_SFTP_RESUME
* when they're non-negative. ie. $start could let you write at the end of a file (like NET_SFTP_RESUME) or in the middle
* of one. $local_start could let you start your reading from the end of a file (like NET_SFTP_RESUME_START) or in the
* $start and $local_start give you more fine grained control over this process and take precident over self::RESUME
* when they're non-negative. ie. $start could let you write at the end of a file (like self::RESUME) or in the middle
* of one. $local_start could let you start your reading from the end of a file (like self::RESUME_START) or in the
* middle of one.
*
* Setting $local_start to > 0 or $mode | NET_SFTP_RESUME_START doesn't do anything unless $mode | NET_SFTP_LOCAL_FILE.
* Setting $local_start to > 0 or $mode | self::RESUME_START doesn't do anything unless $mode | self::SOURCE_LOCAL_FILE.
*
* @param string $remote_file
* @param string|resource $data
@ -1838,11 +1855,11 @@ class Net_SFTP extends Net_SSH2
* @param callable|null $progressCallback
* @return bool
* @access public
* @internal ASCII mode for SFTPv4/5/6 can be supported by adding a new function - Net_SFTP::setMode().
* @internal ASCII mode for SFTPv4/5/6 can be supported by adding a new function - \phpseclib\Net\SFTP::setMode().
*/
function put($remote_file, $data, $mode = NET_SFTP_STRING, $start = -1, $local_start = -1, $progressCallback = null)
function put($remote_file, $data, $mode = self::SOURCE_STRING, $start = -1, $local_start = -1, $progressCallback = null)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -1856,11 +1873,11 @@ class Net_SFTP extends Net_SSH2
$flags = NET_SFTP_OPEN_WRITE | NET_SFTP_OPEN_CREATE;
// according to the SFTP specs, NET_SFTP_OPEN_APPEND should "force all writes to append data at the end of the file."
// in practice, it doesn't seem to do that.
//$flags|= ($mode & NET_SFTP_RESUME) ? NET_SFTP_OPEN_APPEND : NET_SFTP_OPEN_TRUNCATE;
//$flags|= ($mode & self::RESUME) ? NET_SFTP_OPEN_APPEND : NET_SFTP_OPEN_TRUNCATE;
if ($start >= 0) {
$offset = $start;
} elseif ($mode & NET_SFTP_RESUME) {
} elseif ($mode & self::RESUME) {
// if NET_SFTP_OPEN_APPEND worked as it should _size() wouldn't need to be called
$size = $this->size($remote_file);
$offset = $size !== false ? $size : 0;
@ -1890,18 +1907,25 @@ class Net_SFTP extends Net_SSH2
// http://tools.ietf.org/html/draft-ietf-secsh-filexfer-13#section-8.2.3
$dataCallback = false;
switch (true) {
case $mode & NET_SFTP_CALLBACK:
case $mode & self::SOURCE_CALLBACK:
if (!is_callable($data)) {
user_error("\$data should be is_callable if you set NET_SFTP_CALLBACK flag");
user_error("\$data should be is_callable() if you specify SOURCE_CALLBACK flag");
}
$dataCallback = $data;
// do nothing
break;
case is_resource($data):
$mode = $mode & ~NET_SFTP_LOCAL_FILE;
$mode = $mode & ~self::SOURCE_LOCAL_FILE;
$info = stream_get_meta_data($data);
if ($info['wrapper_type'] == 'PHP' && $info['stream_type'] == 'Input') {
$fp = fopen('php://memory', 'w+');
stream_copy_to_stream($data, $fp);
rewind($fp);
} else {
$fp = $data;
}
break;
case $mode & NET_SFTP_LOCAL_FILE:
case $mode & self::SOURCE_LOCAL_FILE:
if (!is_file($data)) {
user_error("$data is not a valid file");
return false;
@ -1933,7 +1957,7 @@ class Net_SFTP extends Net_SSH2
// make the SFTP packet be exactly 4096 bytes by including the bytes in the NET_SFTP_WRITE packets "header"
$sftp_packet_size-= strlen($handle) + 25;
$i = 0;
while ($dataCallback || ($sent < $size)) {
while ($dataCallback || ($size === 0 || $sent < $size)) {
if ($dataCallback) {
$temp = call_user_func($dataCallback, $sftp_packet_size);
if (is_null($temp)) {
@ -1941,11 +1965,15 @@ class Net_SFTP extends Net_SSH2
}
} else {
$temp = isset($fp) ? fread($fp, $sftp_packet_size) : substr($data, $sent, $sftp_packet_size);
if ($temp === false || $temp === '') {
break;
}
}
$subtemp = $offset + $sent;
$packet = pack('Na*N3a*', strlen($handle), $handle, $subtemp / 4294967296, $subtemp, strlen($temp), $temp);
if (!$this->_send_sftp_packet(NET_SFTP_WRITE, $packet)) {
if ($mode & NET_SFTP_LOCAL_FILE) {
if ($mode & self::SOURCE_LOCAL_FILE) {
fclose($fp);
}
return false;
@ -1967,14 +1995,14 @@ class Net_SFTP extends Net_SSH2
}
if (!$this->_read_put_responses($i)) {
if ($mode & NET_SFTP_LOCAL_FILE) {
if ($mode & self::SOURCE_LOCAL_FILE) {
fclose($fp);
}
$this->_close_handle($handle);
return false;
}
if ($mode & NET_SFTP_LOCAL_FILE) {
if ($mode & self::SOURCE_LOCAL_FILE) {
fclose($fp);
}
@ -2000,6 +2028,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -2031,6 +2062,9 @@ class Net_SFTP extends Net_SSH2
return false;
}
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -2058,7 +2092,7 @@ class Net_SFTP extends Net_SSH2
*/
function get($remote_file, $local_file = false, $offset = 0, $length = -1)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -2104,17 +2138,42 @@ class Net_SFTP extends Net_SSH2
$fclose_check = $local_file !== false && !is_resource($local_file);
$start = $offset;
$size = $this->max_sftp_packet < $length || $length < 0 ? $this->max_sftp_packet : $length;
$read = 0;
while (true) {
$packet = pack('Na*N3', strlen($handle), $handle, $offset / 4294967296, $offset, $size);
$i = 0;
while ($i < NET_SFTP_QUEUE_SIZE && ($length < 0 || $read < $length)) {
$tempoffset = $start + $read;
$packet_size = $length > 0 ? min($this->max_sftp_packet, $length - $read) : $this->max_sftp_packet;
$packet = pack('Na*N3', strlen($handle), $handle, $tempoffset / 4294967296, $tempoffset, $packet_size);
if (!$this->_send_sftp_packet(NET_SFTP_READ, $packet)) {
if ($fclose_check) {
fclose($fp);
}
return false;
}
$packet = null;
$read+= $packet_size;
$i++;
}
if (!$i) {
break;
}
$clear_responses = false;
while ($i > 0) {
$i--;
if ($clear_responses) {
$this->_get_sftp_packet();
continue;
} else {
$response = $this->_get_sftp_packet();
}
switch ($this->packet_type) {
case NET_SFTP_DATA:
$temp = substr($response, 4);
@ -2124,20 +2183,23 @@ class Net_SFTP extends Net_SSH2
} else {
fputs($fp, $temp);
}
$temp = null;
break;
case NET_SFTP_STATUS:
// could, in theory, return false if !strlen($content) but we'll hold off for the time being
$this->_logError($response);
break 2;
$clear_responses = true; // don't break out of the loop yet, so we can read the remaining responses
break;
default:
user_error('Expected SSH_FXP_DATA or SSH_FXP_STATUS');
if ($fclose_check) {
fclose($fp);
}
return false;
user_error('Expected SSH_FX_DATA or SSH_FXP_STATUS');
}
$response = null;
}
if ($length > 0 && $length <= $offset - $start) {
if ($clear_responses) {
break;
}
}
@ -2172,7 +2234,16 @@ class Net_SFTP extends Net_SSH2
*/
function delete($path, $recursive = true)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
if (is_object($path)) {
// It's an object. Cast it as string before we check anything else.
$path = (string) $path;
}
if (!is_string($path) || $path == '') {
return false;
}
@ -2193,6 +2264,9 @@ class Net_SFTP extends Net_SSH2
}
// if $status isn't SSH_FX_OK it's probably SSH_FX_NO_SUCH_FILE or SSH_FX_PERMISSION_DENIED
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -2595,7 +2669,7 @@ class Net_SFTP extends Net_SSH2
*/
function rename($oldname, $newname)
{
if (!($this->bitmap & NET_SSH2_MASK_LOGIN)) {
if (!($this->bitmap & SSH2::MASK_LOGIN)) {
return false;
}
@ -2618,6 +2692,9 @@ class Net_SFTP extends Net_SSH2
}
// if $status isn't SSH_FX_OK it's probably SSH_FX_NO_SUCH_FILE or SSH_FX_PERMISSION_DENIED
if (strlen($response) < 4) {
return false;
}
extract(unpack('Nstatus', $this->_string_shift($response, 4)));
if ($status != NET_SFTP_STATUS_OK) {
$this->_logError($response, $status);
@ -2645,6 +2722,10 @@ class Net_SFTP extends Net_SSH2
function _parseAttributes(&$response)
{
$attr = array();
if (strlen($response) < 4) {
user_error('Malformed file attributes');
return array();
}
extract(unpack('Nflags', $this->_string_shift($response, 4)));
// SFTPv4+ have a type field (a byte) that follows the above flag field
foreach ($this->attributes as $key => $value) {
@ -2659,9 +2740,17 @@ class Net_SFTP extends Net_SSH2
$attr['size'] = hexdec(bin2hex($this->_string_shift($response, 8)));
break;
case NET_SFTP_ATTR_UIDGID: // 0x00000002 (SFTPv3 only)
if (strlen($response) < 8) {
user_error('Malformed file attributes');
return $attr;
}
$attr+= unpack('Nuid/Ngid', $this->_string_shift($response, 8));
break;
case NET_SFTP_ATTR_PERMISSIONS: // 0x00000004
if (strlen($response) < 4) {
user_error('Malformed file attributes');
return $attr;
}
$attr+= unpack('Npermissions', $this->_string_shift($response, 4));
// mode == permissions; permissions was the original array key and is retained for bc purposes.
// mode was added because that's the more industry standard terminology
@ -2672,13 +2761,29 @@ class Net_SFTP extends Net_SSH2
}
break;
case NET_SFTP_ATTR_ACCESSTIME: // 0x00000008
if (strlen($response) < 8) {
user_error('Malformed file attributes');
return $attr;
}
$attr+= unpack('Natime/Nmtime', $this->_string_shift($response, 8));
break;
case NET_SFTP_ATTR_EXTENDED: // 0x80000000
if (strlen($response) < 4) {
user_error('Malformed file attributes');
return $attr;
}
extract(unpack('Ncount', $this->_string_shift($response, 4)));
for ($i = 0; $i < $count; $i++) {
if (strlen($response) < 4) {
user_error('Malformed file attributes');
return $attr;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$key = $this->_string_shift($response, $length);
if (strlen($response) < 4) {
user_error('Malformed file attributes');
return $attr;
}
extract(unpack('Nlength', $this->_string_shift($response, 4)));
$attr[$key] = $this->_string_shift($response, $length);
}
@ -2771,7 +2876,7 @@ class Net_SFTP extends Net_SSH2
* @param int $type
* @param string $data
* @see self::_get_sftp_packet()
* @see Net_SSH2::_send_channel_packet()
* @see self::_send_channel_packet()
* @return bool
* @access private
*/
@ -2782,19 +2887,19 @@ class Net_SFTP extends Net_SSH2
pack('NCa*', strlen($data) + 1, $type, $data);
$start = strtok(microtime(), ' ') + strtok(''); // http://php.net/microtime#61838
$result = $this->_send_channel_packet(NET_SFTP_CHANNEL, $packet);
$result = $this->_send_channel_packet(self::CHANNEL, $packet);
$stop = strtok(microtime(), ' ') + strtok('');
if (defined('NET_SFTP_LOGGING')) {
$packet_type = '-> ' . $this->packet_types[$type] .
' (' . round($stop - $start, 4) . 's)';
if (NET_SFTP_LOGGING == NET_SFTP_LOG_REALTIME) {
if (NET_SFTP_LOGGING == self::LOG_REALTIME) {
echo "<pre>\r\n" . $this->_format_log(array($data), array($packet_type)) . "\r\n</pre>\r\n";
flush();
ob_flush();
} else {
$this->packet_type_log[] = $packet_type;
if (NET_SFTP_LOGGING == NET_SFTP_LOG_COMPLEX) {
if (NET_SFTP_LOGGING == self::LOG_COMPLEX) {
$this->packet_log[] = $data;
}
}
@ -2824,7 +2929,7 @@ class Net_SFTP extends Net_SSH2
// SFTP packet length
while (strlen($this->packet_buffer) < 4) {
$temp = $this->_get_channel_packet(NET_SFTP_CHANNEL);
$temp = $this->_get_channel_packet(self::CHANNEL);
if (is_bool($temp)) {
$this->packet_type = false;
$this->packet_buffer = '';
@ -2832,13 +2937,16 @@ class Net_SFTP extends Net_SSH2
}
$this->packet_buffer.= $temp;
}
if (strlen($this->packet_buffer) < 4) {
return false;
}
extract(unpack('Nlength', $this->_string_shift($this->packet_buffer, 4)));
$tempLength = $length;
$tempLength-= strlen($this->packet_buffer);
// SFTP packet type and data payload
while ($tempLength > 0) {
$temp = $this->_get_channel_packet(NET_SFTP_CHANNEL);
$temp = $this->_get_channel_packet(self::CHANNEL);
if (is_bool($temp)) {
$this->packet_type = false;
$this->packet_buffer = '';
@ -2864,13 +2972,13 @@ class Net_SFTP extends Net_SSH2
if (defined('NET_SFTP_LOGGING')) {
$packet_type = '<- ' . $this->packet_types[$this->packet_type] .
' (' . round($stop - $start, 4) . 's)';
if (NET_SFTP_LOGGING == NET_SFTP_LOG_REALTIME) {
if (NET_SFTP_LOGGING == self::LOG_REALTIME) {
echo "<pre>\r\n" . $this->_format_log(array($packet), array($packet_type)) . "\r\n</pre>\r\n";
flush();
ob_flush();
} else {
$this->packet_type_log[] = $packet_type;
if (NET_SFTP_LOGGING == NET_SFTP_LOG_COMPLEX) {
if (NET_SFTP_LOGGING == self::LOG_COMPLEX) {
$this->packet_log[] = $packet;
}
}
@ -2894,10 +3002,10 @@ class Net_SFTP extends Net_SSH2
}
switch (NET_SFTP_LOGGING) {
case NET_SFTP_LOG_COMPLEX:
case self::LOG_COMPLEX:
return $this->_format_log($this->packet_log, $this->packet_type_log);
break;
//case NET_SFTP_LOG_SIMPLE:
//case self::LOG_SIMPLE:
default:
return $this->packet_type_log;
}

View File

@ -7,40 +7,27 @@
*
* PHP version 5
*
* 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 Net
* @package Net_SFTP_Stream
* @package SFTP
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2013 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
namespace phpseclib\Net\SFTP;
use phpseclib\Crypt\RSA;
use phpseclib\Net\SFTP;
/**
* SFTP Stream Wrapper
*
* @package Net_SFTP_Stream
* @package SFTP
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Net_SFTP_Stream
class Stream
{
/**
* SFTP instances
@ -137,8 +124,7 @@ class Net_SFTP_Stream
if (in_array($protocol, stream_get_wrappers(), true)) {
return false;
}
$class = function_exists('get_called_class') ? get_called_class() : __CLASS__;
return stream_wrapper_register($protocol, $class);
return stream_wrapper_register($protocol, get_called_class());
}
/**
@ -146,15 +132,11 @@ class Net_SFTP_Stream
*
* @access public
*/
function Net_SFTP_Stream()
function __construct()
{
if (defined('NET_SFTP_STREAM_LOGGING')) {
echo "__construct()\r\n";
}
if (!class_exists('Net_SFTP')) {
include_once 'Net/SFTP.php';
}
}
/**
@ -198,7 +180,7 @@ class Net_SFTP_Stream
if ($host[0] == '$') {
$host = substr($host, 1);
global $$host;
if (!is_object($$host) || get_class($$host) != 'Net_SFTP') {
if (($$host instanceof SFTP) === false) {
return false;
}
$this->sftp = $$host;
@ -212,7 +194,7 @@ class Net_SFTP_Stream
if (isset($context[$scheme]['sftp'])) {
$sftp = $context[$scheme]['sftp'];
}
if (isset($sftp) && is_object($sftp) && get_class($sftp) == 'Net_SFTP') {
if (isset($sftp) && $sftp instanceof SFTP) {
$this->sftp = $sftp;
return $path;
}
@ -222,7 +204,7 @@ class Net_SFTP_Stream
if (isset($context[$scheme]['password'])) {
$pass = $context[$scheme]['password'];
}
if (isset($context[$scheme]['privkey']) && is_object($context[$scheme]['privkey']) && get_Class($context[$scheme]['privkey']) == 'Crypt_RSA') {
if (isset($context[$scheme]['privkey']) && $context[$scheme]['privkey'] instanceof RSA) {
$pass = $context[$scheme]['privkey'];
}
@ -230,11 +212,11 @@ class Net_SFTP_Stream
return false;
}
// casting $pass to a string is necessary in the event that it's a Crypt_RSA object
// casting $pass to a string is necessary in the event that it's a \phpseclib\Crypt\RSA object
if (isset(self::$instances[$host][$port][$user][(string) $pass])) {
$this->sftp = self::$instances[$host][$port][$user][(string) $pass];
} else {
$this->sftp = new Net_SFTP($host, $port);
$this->sftp = new SFTP($host, $port);
$this->sftp->disableStatCache();
if (isset($this->notification) && is_callable($this->notification)) {
/* if !is_callable($this->notification) we could do this:
@ -366,7 +348,7 @@ class Net_SFTP_Stream
return false;
}
$result = $this->sftp->put($this->path, $data, NET_SFTP_STRING, $this->pos);
$result = $this->sftp->put($this->path, $data, SFTP::SOURCE_STRING, $this->pos);
if (isset($this->notification) && is_callable($this->notification)) {
if (!$result) {
call_user_func($this->notification, STREAM_NOTIFY_FAILURE, STREAM_NOTIFY_SEVERITY_ERR, $this->sftp->getLastSFTPError(), NET_SFTP_OPEN, 0, 0);
@ -506,7 +488,7 @@ class Net_SFTP_Stream
* Renames a file or directory
*
* Attempts to rename oldname to newname, moving it between directories if necessary.
* If newname exists, it will be overwritten. This is a departure from what Net_SFTP
* If newname exists, it will be overwritten. This is a departure from what \phpseclib\Net\SFTP
* does.
*
* @param string $path_from
@ -662,7 +644,7 @@ class Net_SFTP_Stream
/**
* Flushes the output
*
* See <http://php.net/fflush>. Always returns true because Net_SFTP doesn't cache stuff before writing
* See <http://php.net/fflush>. Always returns true because \phpseclib\Net\SFTP doesn't cache stuff before writing
*
* @return bool
* @access public
@ -707,7 +689,7 @@ class Net_SFTP_Stream
/**
* Retrieve information about a file
*
* Ignores the STREAM_URL_STAT_QUIET flag because the entirety of Net_SFTP_Stream is quiet by default
* Ignores the STREAM_URL_STAT_QUIET flag because the entirety of \phpseclib\Net\SFTP\Stream is quiet by default
* might be worthwhile to reconstruct bits 12-16 (ie. the file type) if mode doesn't have them but we'll
* cross that bridge when and if it's reached
*
@ -754,7 +736,7 @@ class Net_SFTP_Stream
* Change stream options
*
* STREAM_OPTION_WRITE_BUFFER isn't supported for the same reason stream_flush isn't.
* The other two aren't supported because of limitations in Net_SFTP.
* The other two aren't supported because of limitations in \phpseclib\Net\SFTP.
*
* @param int $option
* @param int $arg1
@ -811,5 +793,3 @@ class Net_SFTP_Stream
return call_user_func_array(array($this, $name), $arguments);
}
}
Net_SFTP_Stream::register();

View File

@ -3,14 +3,14 @@
/**
* Pure-PHP implementation of SSHv1.
*
* PHP versions 4 and 5
* PHP version 5
*
* Here's a short example of how to use this library:
* <code>
* <?php
* include 'Net/SSH1.php';
* include 'vendor/autoload.php';
*
* $ssh = new Net_SSH1('www.domain.tld');
* $ssh = new \phpseclib\Net\SSH1('www.domain.tld');
* if (!$ssh->login('username', 'password')) {
* exit('Login Failed');
* }
@ -22,9 +22,9 @@
* Here's another short example:
* <code>
* <?php
* include 'Net/SSH1.php';
* include 'vendor/autoload.php';
*
* $ssh = new Net_SSH1('www.domain.tld');
* $ssh = new \phpseclib\Net\SSH1('www.domain.tld');
* if (!$ssh->login('username', 'password')) {
* exit('Login Failed');
* }
@ -38,36 +38,34 @@
* More information on the SSHv1 specification can be found by reading
* {@link http://www.snailbook.com/docs/protocol-1.5.txt protocol-1.5.txt}.
*
* 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 Net
* @package Net_SSH1
* @package SSH1
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2007 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://phpseclib.sourceforge.net
*/
namespace phpseclib\Net;
use phpseclib\Crypt\DES;
use phpseclib\Crypt\Random;
use phpseclib\Crypt\TripleDES;
use phpseclib\Math\BigInteger;
/**
* Pure-PHP implementation of SSHv1.
*
* @package SSH1
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class SSH1
{
/**#@+
* Encryption Methods
*
* @see self::getSupportedCiphers()
* @see \phpseclib\Net\SSH1::getSupportedCiphers()
* @access public
*/
/**
@ -75,30 +73,30 @@
*
* Not supported.
*/
define('NET_SSH1_CIPHER_NONE', 0);
const CIPHER_NONE = 0;
/**
* IDEA in CFB mode
*
* Not supported.
*/
define('NET_SSH1_CIPHER_IDEA', 1);
const CIPHER_IDEA = 1;
/**
* DES in CBC mode
*/
define('NET_SSH1_CIPHER_DES', 2);
const CIPHER_DES = 2;
/**
* Triple-DES in CBC mode
*
* All implementations are required to support this
*/
define('NET_SSH1_CIPHER_3DES', 3);
const CIPHER_3DES = 3;
/**
* TRI's Simple Stream encryption CBC
*
* Not supported nor is it defined in the official SSH1 specs. OpenSSH, however, does define it (see cipher.h),
* although it doesn't use it (see cipher.c)
*/
define('NET_SSH1_CIPHER_BROKEN_TSS', 4);
const CIPHER_BROKEN_TSS = 4;
/**
* RC4
*
@ -114,40 +112,40 @@ define('NET_SSH1_CIPHER_BROKEN_TSS', 4);
* This library currently only supports encryption when the same key is being used for both directions. This is
* because there's only one $crypto object. Two could be added ($encrypt and $decrypt, perhaps).
*/
define('NET_SSH1_CIPHER_RC4', 5);
const CIPHER_RC4 = 5;
/**
* Blowfish
*
* Not supported nor is it defined in the official SSH1 specs. OpenSSH, however, defines it (see cipher.h) and
* uses it (see cipher.c)
*/
define('NET_SSH1_CIPHER_BLOWFISH', 6);
const CIPHER_BLOWFISH = 6;
/**#@-*/
/**#@+
* Authentication Methods
*
* @see self::getSupportedAuthentications()
* @see \phpseclib\Net\SSH1::getSupportedAuthentications()
* @access public
*/
/**
* .rhosts or /etc/hosts.equiv
*/
define('NET_SSH1_AUTH_RHOSTS', 1);
const AUTH_RHOSTS = 1;
/**
* pure RSA authentication
*/
define('NET_SSH1_AUTH_RSA', 2);
const AUTH_RSA = 2;
/**
* password authentication
*
* This is the only method that is supported by this library.
*/
define('NET_SSH1_AUTH_PASSWORD', 3);
const AUTH_PASSWORD = 3;
/**
* .rhosts with RSA host authentication
*/
define('NET_SSH1_AUTH_RHOSTS_RSA', 4);
const AUTH_RHOSTS_RSA = 4;
/**#@-*/
/**#@+
@ -156,82 +154,73 @@ define('NET_SSH1_AUTH_RHOSTS_RSA', 4);
* @link http://3sp.com/content/developer/maverick-net/docs/Maverick.SSH.PseudoTerminalModesMembers.html
* @access private
*/
define('NET_SSH1_TTY_OP_END', 0);
const TTY_OP_END = 0;
/**#@-*/
/**
* The Response Type
*
* @see self::_get_binary_packet()
* @see \phpseclib\Net\SSH1::_get_binary_packet()
* @access private
*/
define('NET_SSH1_RESPONSE_TYPE', 1);
const RESPONSE_TYPE = 1;
/**
* The Response Data
*
* @see self::_get_binary_packet()
* @see \phpseclib\Net\SSH1::_get_binary_packet()
* @access private
*/
define('NET_SSH1_RESPONSE_DATA', 2);
const RESPONSE_DATA = 2;
/**#@+
* Execution Bitmap Masks
*
* @see self::bitmap
* @see \phpseclib\Net\SSH1::bitmap
* @access private
*/
define('NET_SSH1_MASK_CONSTRUCTOR', 0x00000001);
define('NET_SSH1_MASK_CONNECTED', 0x00000002);
define('NET_SSH1_MASK_LOGIN', 0x00000004);
define('NET_SSH1_MASK_SHELL', 0x00000008);
const MASK_CONSTRUCTOR = 0x00000001;
const MASK_CONNECTED = 0x00000002;
const MASK_LOGIN = 0x00000004;
const MASK_SHELL = 0x00000008;
/**#@-*/
/**#@+
* @access public
* @see self::getLog()
* @see \phpseclib\Net\SSH1::getLog()
*/
/**
* Returns the message numbers
*/
define('NET_SSH1_LOG_SIMPLE', 1);
const LOG_SIMPLE = 1;
/**
* Returns the message content
*/
define('NET_SSH1_LOG_COMPLEX', 2);
const LOG_COMPLEX = 2;
/**
* Outputs the content real-time
*/
define('NET_SSH1_LOG_REALTIME', 3);
const LOG_REALTIME = 3;
/**
* Dumps the content real-time to a file
*/
define('NET_SSH1_LOG_REALTIME_FILE', 4);
const LOG_REALTIME_FILE = 4;
/**#@-*/
/**#@+
* @access public
* @see self::read()
* @see \phpseclib\Net\SSH1::read()
*/
/**
* Returns when a string matching $expect exactly is found
*/
define('NET_SSH1_READ_SIMPLE', 1);
const READ_SIMPLE = 1;
/**
* Returns when a string matching the regular expression $expect is found
*/
define('NET_SSH1_READ_REGEX', 2);
const READ_REGEX = 2;
/**#@-*/
/**
* Pure-PHP implementation of SSHv1.
*
* @package Net_SSH1
* @author Jim Wigginton <terrafrost@php.net>
* @access public
*/
class Net_SSH1
{
/**
* The SSH identifier
*
@ -321,13 +310,13 @@ class Net_SSH1
* @access private
*/
var $supported_ciphers = array(
NET_SSH1_CIPHER_NONE => 'No encryption',
NET_SSH1_CIPHER_IDEA => 'IDEA in CFB mode',
NET_SSH1_CIPHER_DES => 'DES in CBC mode',
NET_SSH1_CIPHER_3DES => 'Triple-DES in CBC mode',
NET_SSH1_CIPHER_BROKEN_TSS => 'TRI\'s Simple Stream encryption CBC',
NET_SSH1_CIPHER_RC4 => 'RC4',
NET_SSH1_CIPHER_BLOWFISH => 'Blowfish'
self::CIPHER_NONE => 'No encryption',
self::CIPHER_IDEA => 'IDEA in CFB mode',
self::CIPHER_DES => 'DES in CBC mode',
self::CIPHER_3DES => 'Triple-DES in CBC mode',
self::CIPHER_BROKEN_TSS => 'TRI\'s Simple Stream encryption CBC',
self::CIPHER_RC4 => 'RC4',
self::CIPHER_BLOWFISH => 'Blowfish'
);
/**
@ -340,10 +329,10 @@ class Net_SSH1
* @access private
*/
var $supported_authentications = array(
NET_SSH1_AUTH_RHOSTS => '.rhosts or /etc/hosts.equiv',
NET_SSH1_AUTH_RSA => 'pure RSA authentication',
NET_SSH1_AUTH_PASSWORD => 'password authentication',
NET_SSH1_AUTH_RHOSTS_RSA => '.rhosts with RSA host authentication'
self::AUTH_RHOSTS => '.rhosts or /etc/hosts.equiv',
self::AUTH_RSA => 'pure RSA authentication',
self::AUTH_PASSWORD => 'password authentication',
self::AUTH_RHOSTS_RSA => '.rhosts with RSA host authentication'
);
/**
@ -358,7 +347,7 @@ class Net_SSH1
/**
* Protocol Flags
*
* @see self::Net_SSH1()
* @see self::__construct()
* @var array
* @access private
*/
@ -461,7 +450,7 @@ class Net_SSH1
/**
* Hostname
*
* @see self::Net_SSH1()
* @see self::__construct()
* @see self::_connect()
* @var string
* @access private
@ -471,7 +460,7 @@ class Net_SSH1
/**
* Port Number
*
* @see self::Net_SSH1()
* @see self::__construct()
* @see self::_connect()
* @var int
* @access private
@ -486,7 +475,7 @@ class Net_SSH1
* however, is non-optional. There will be a timeout, whether or not you set it. If you don't it'll be
* 10 seconds. It is used by fsockopen() in that function.
*
* @see self::Net_SSH1()
* @see self::__construct()
* @see self::_connect()
* @var int
* @access private
@ -496,7 +485,7 @@ class Net_SSH1
/**
* Default cipher
*
* @see self::Net_SSH1()
* @see self::__construct()
* @see self::_connect()
* @var int
* @access private
@ -512,24 +501,11 @@ class Net_SSH1
* @param int $port
* @param int $timeout
* @param int $cipher
* @return Net_SSH1
* @return \phpseclib\Net\SSH1
* @access public
*/
function Net_SSH1($host, $port = 22, $timeout = 10, $cipher = NET_SSH1_CIPHER_3DES)
function __construct($host, $port = 22, $timeout = 10, $cipher = self::CIPHER_3DES)
{
if (!class_exists('Math_BigInteger')) {
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 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')) {
include_once 'Crypt/Random.php';
}
$this->protocol_flags = array(
1 => 'NET_SSH1_MSG_DISCONNECT',
2 => 'NET_SSH1_SMSG_PUBLIC_KEY',
@ -590,37 +566,55 @@ class Net_SSH1
fputs($this->fsock, $this->identifier."\r\n");
$response = $this->_get_binary_packet();
if ($response[NET_SSH1_RESPONSE_TYPE] != NET_SSH1_SMSG_PUBLIC_KEY) {
if ($response[self::RESPONSE_TYPE] != NET_SSH1_SMSG_PUBLIC_KEY) {
user_error('Expected SSH_SMSG_PUBLIC_KEY');
return false;
}
$anti_spoofing_cookie = $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 8);
$anti_spoofing_cookie = $this->_string_shift($response[self::RESPONSE_DATA], 8);
$this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 4);
$this->_string_shift($response[self::RESPONSE_DATA], 4);
$temp = unpack('nlen', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 2));
$server_key_public_exponent = new Math_BigInteger($this->_string_shift($response[NET_SSH1_RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
if (strlen($response[self::RESPONSE_DATA]) < 2) {
return false;
}
$temp = unpack('nlen', $this->_string_shift($response[self::RESPONSE_DATA], 2));
$server_key_public_exponent = new BigInteger($this->_string_shift($response[self::RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
$this->server_key_public_exponent = $server_key_public_exponent;
$temp = unpack('nlen', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 2));
$server_key_public_modulus = new Math_BigInteger($this->_string_shift($response[NET_SSH1_RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
if (strlen($response[self::RESPONSE_DATA]) < 2) {
return false;
}
$temp = unpack('nlen', $this->_string_shift($response[self::RESPONSE_DATA], 2));
$server_key_public_modulus = new BigInteger($this->_string_shift($response[self::RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
$this->server_key_public_modulus = $server_key_public_modulus;
$this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 4);
$this->_string_shift($response[self::RESPONSE_DATA], 4);
$temp = unpack('nlen', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 2));
$host_key_public_exponent = new Math_BigInteger($this->_string_shift($response[NET_SSH1_RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
if (strlen($response[self::RESPONSE_DATA]) < 2) {
return false;
}
$temp = unpack('nlen', $this->_string_shift($response[self::RESPONSE_DATA], 2));
$host_key_public_exponent = new BigInteger($this->_string_shift($response[self::RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
$this->host_key_public_exponent = $host_key_public_exponent;
$temp = unpack('nlen', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 2));
$host_key_public_modulus = new Math_BigInteger($this->_string_shift($response[NET_SSH1_RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
if (strlen($response[self::RESPONSE_DATA]) < 2) {
return false;
}
$temp = unpack('nlen', $this->_string_shift($response[self::RESPONSE_DATA], 2));
$host_key_public_modulus = new BigInteger($this->_string_shift($response[self::RESPONSE_DATA], ceil($temp['len'] / 8)), 256);
$this->host_key_public_modulus = $host_key_public_modulus;
$this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 4);
$this->_string_shift($response[self::RESPONSE_DATA], 4);
// get a list of the supported ciphers
extract(unpack('Nsupported_ciphers_mask', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 4)));
if (strlen($response[self::RESPONSE_DATA]) < 4) {
return false;
}
extract(unpack('Nsupported_ciphers_mask', $this->_string_shift($response[self::RESPONSE_DATA], 4)));
foreach ($this->supported_ciphers as $mask => $name) {
if (($supported_ciphers_mask & (1 << $mask)) == 0) {
unset($this->supported_ciphers[$mask]);
@ -628,7 +622,10 @@ class Net_SSH1
}
// get a list of the supported authentications
extract(unpack('Nsupported_authentications_mask', $this->_string_shift($response[NET_SSH1_RESPONSE_DATA], 4)));
if (strlen($response[self::RESPONSE_DATA]) < 4) {
return false;
}
extract(unpack('Nsupported_authentications_mask', $this->_string_shift($response[self::RESPONSE_DATA], 4)));
foreach ($this->supported_authentications as $mask => $name) {
if (($supported_authentications_mask & (1 << $mask)) == 0) {
unset($this->supported_authentications[$mask]);
@ -637,7 +634,7 @@ class Net_SSH1
$session_id = pack('H*', md5($host_key_public_modulus->toBytes() . $server_key_public_modulus->toBytes() . $anti_spoofing_cookie));
$session_key = crypt_random_string(32);
$session_key = Random::string(32);
$double_encrypted_session_key = $session_key ^ str_pad($session_id, 32, chr(0));
if ($server_key_public_modulus->compare($host_key_public_modulus) < 0) {
@ -672,7 +669,7 @@ class Net_SSH1
);
}
$cipher = isset($this->supported_ciphers[$this->cipher]) ? $this->cipher : NET_SSH1_CIPHER_3DES;
$cipher = isset($this->supported_ciphers[$this->cipher]) ? $this->cipher : self::CIPHER_3DES;
$data = pack('C2a*na*N', NET_SSH1_CMSG_SESSION_KEY, $cipher, $anti_spoofing_cookie, 8 * strlen($double_encrypted_session_key), $double_encrypted_session_key, 0);
if (!$this->_send_binary_packet($data)) {
@ -681,32 +678,23 @@ class Net_SSH1
}
switch ($cipher) {
//case NET_SSH1_CIPHER_NONE:
// $this->crypto = new Crypt_Null();
//case self::CIPHER_NONE:
// $this->crypto = new \phpseclib\Crypt\Null();
// break;
case NET_SSH1_CIPHER_DES:
if (!class_exists('Crypt_DES')) {
include_once 'Crypt/DES.php';
}
$this->crypto = new Crypt_DES();
case self::CIPHER_DES:
$this->crypto = new DES();
$this->crypto->disablePadding();
$this->crypto->enableContinuousBuffer();
$this->crypto->setKey(substr($session_key, 0, 8));
break;
case NET_SSH1_CIPHER_3DES:
if (!class_exists('Crypt_TripleDES')) {
include_once 'Crypt/TripleDES.php';
}
$this->crypto = new Crypt_TripleDES(CRYPT_DES_MODE_3CBC);
case self::CIPHER_3DES:
$this->crypto = new TripleDES(TripleDES::MODE_3CBC);
$this->crypto->disablePadding();
$this->crypto->enableContinuousBuffer();
$this->crypto->setKey(substr($session_key, 0, 24));
break;
//case NET_SSH1_CIPHER_RC4:
// if (!class_exists('Crypt_RC4')) {
// include_once 'Crypt/RC4.php';
// }
// $this->crypto = new Crypt_RC4();
//case self::CIPHER_RC4:
// $this->crypto = new RC4();
// $this->crypto->enableContinuousBuffer();
// $this->crypto->setKey(substr($session_key, 0, 16));
// break;
@ -714,12 +702,12 @@ class Net_SSH1
$response = $this->_get_binary_packet();
if ($response[NET_SSH1_RESPONSE_TYPE] != NET_SSH1_SMSG_SUCCESS) {
if ($response[self::RESPONSE_TYPE] != NET_SSH1_SMSG_SUCCESS) {
user_error('Expected SSH_SMSG_SUCCESS');
return false;
}
$this->bitmap = NET_SSH1_MASK_CONNECTED;
$this->bitmap = self::MASK_CONNECTED;
return true;
}
@ -734,14 +722,14 @@ class Net_SSH1
*/
function login($username, $password = '')
{
if (!($this->bitmap & NET_SSH1_MASK_CONSTRUCTOR)) {
$this->bitmap |= NET_SSH1_MASK_CONSTRUCTOR;
if (!($this->bitmap & self::MASK_CONSTRUCTOR)) {
$this->bitmap |= self::MASK_CONSTRUCTOR;
if (!$this->_connect()) {
return false;
}
}
if (!($this->bitmap & NET_SSH1_MASK_CONNECTED)) {
if (!($this->bitmap & self::MASK_CONNECTED)) {
return false;
}
@ -757,10 +745,10 @@ class Net_SSH1
if ($response === true) {
return false;
}
if ($response[NET_SSH1_RESPONSE_TYPE] == NET_SSH1_SMSG_SUCCESS) {
$this->bitmap |= NET_SSH1_MASK_LOGIN;
if ($response[self::RESPONSE_TYPE] == NET_SSH1_SMSG_SUCCESS) {
$this->bitmap |= self::MASK_LOGIN;
return true;
} elseif ($response[NET_SSH1_RESPONSE_TYPE] != NET_SSH1_SMSG_FAILURE) {
} elseif ($response[self::RESPONSE_TYPE] != NET_SSH1_SMSG_FAILURE) {
user_error('Expected SSH_SMSG_SUCCESS or SSH_SMSG_FAILURE');
return false;
}
@ -773,7 +761,7 @@ class Net_SSH1
}
// remove the username and password from the last logged packet
if (defined('NET_SSH1_LOGGING') && NET_SSH1_LOGGING == NET_SSH1_LOG_COMPLEX) {
if (defined('NET_SSH1_LOGGING') && NET_SSH1_LOGGING == self::LOG_COMPLEX) {
$data = pack('CNa*', NET_SSH1_CMSG_AUTH_PASSWORD, strlen('password'), 'password');
$this->message_log[count($this->message_log) - 1] = $data;
}
@ -783,10 +771,10 @@ class Net_SSH1
if ($response === true) {
return false;
}
if ($response[NET_SSH1_RESPONSE_TYPE] == NET_SSH1_SMSG_SUCCESS) {
$this->bitmap |= NET_SSH1_MASK_LOGIN;
if ($response[self::RESPONSE_TYPE] == NET_SSH1_SMSG_SUCCESS) {
$this->bitmap |= self::MASK_LOGIN;
return true;
} elseif ($response[NET_SSH1_RESPONSE_TYPE] == NET_SSH1_SMSG_FAILURE) {
} elseif ($response[self::RESPONSE_TYPE] == NET_SSH1_SMSG_FAILURE) {
return false;
} else {
user_error('Expected SSH_SMSG_SUCCESS or SSH_SMSG_FAILURE');
@ -817,7 +805,7 @@ class Net_SSH1
* {@link http://www.faqs.org/docs/bashman/bashref_65.html http://www.faqs.org/docs/bashman/bashref_65.html}
* {@link http://www.faqs.org/docs/bashman/bashref_62.html http://www.faqs.org/docs/bashman/bashref_62.html}
*
* To execute further commands, a new Net_SSH1 object will need to be created.
* To execute further commands, a new \phpseclib\Net\SSH1 object will need to be created.
*
* Returns false on failure and the output, otherwise.
*
@ -829,7 +817,7 @@ class Net_SSH1
*/
function exec($cmd, $block = true)
{
if (!($this->bitmap & NET_SSH1_MASK_LOGIN)) {
if (!($this->bitmap & self::MASK_LOGIN)) {
user_error('Operation disallowed prior to login()');
return false;
}
@ -850,9 +838,9 @@ class Net_SSH1
if ($response !== false) {
do {
$output.= substr($response[NET_SSH1_RESPONSE_DATA], 4);
$output.= substr($response[self::RESPONSE_DATA], 4);
$response = $this->_get_binary_packet();
} while (is_array($response) && $response[NET_SSH1_RESPONSE_TYPE] != NET_SSH1_SMSG_EXITSTATUS);
} while (is_array($response) && $response[self::RESPONSE_TYPE] != NET_SSH1_SMSG_EXITSTATUS);
}
$data = pack('C', NET_SSH1_CMSG_EXIT_CONFIRMATION);
@ -862,7 +850,7 @@ class Net_SSH1
fclose($this->fsock);
// reset the execution bitmap - a new Net_SSH1 object needs to be created.
// reset the execution bitmap - a new \phpseclib\Net\SSH1 object needs to be created.
$this->bitmap = 0;
return $output;
@ -881,7 +869,7 @@ class Net_SSH1
// connect using the sample parameters in protocol-1.5.txt.
// according to wikipedia.org's entry on text terminals, "the fundamental type of application running on a text
// terminal is a command line interpreter or shell". thus, opening a terminal session to run the shell.
$data = pack('CNa*N4C', NET_SSH1_CMSG_REQUEST_PTY, strlen('vt100'), 'vt100', 24, 80, 0, 0, NET_SSH1_TTY_OP_END);
$data = pack('CNa*N4C', NET_SSH1_CMSG_REQUEST_PTY, strlen('vt100'), 'vt100', 24, 80, 0, 0, self::TTY_OP_END);
if (!$this->_send_binary_packet($data)) {
user_error('Error sending SSH_CMSG_REQUEST_PTY');
@ -893,7 +881,7 @@ class Net_SSH1
if ($response === true) {
return false;
}
if ($response[NET_SSH1_RESPONSE_TYPE] != NET_SSH1_SMSG_SUCCESS) {
if ($response[self::RESPONSE_TYPE] != NET_SSH1_SMSG_SUCCESS) {
user_error('Expected SSH_SMSG_SUCCESS');
return false;
}
@ -905,7 +893,7 @@ class Net_SSH1
return false;
}
$this->bitmap |= NET_SSH1_MASK_SHELL;
$this->bitmap |= self::MASK_SHELL;
//stream_set_blocking($this->fsock, 0);
@ -928,7 +916,7 @@ class Net_SSH1
/**
* Returns the output of an interactive shell when there's a match for $expect
*
* $expect can take the form of a string literal or, if $mode == NET_SSH1_READ_REGEX,
* $expect can take the form of a string literal or, if $mode == self::READ__REGEX,
* a regular expression.
*
* @see self::write()
@ -937,21 +925,21 @@ class Net_SSH1
* @return bool
* @access public
*/
function read($expect, $mode = NET_SSH1_READ_SIMPLE)
function read($expect, $mode = self::READ__SIMPLE)
{
if (!($this->bitmap & NET_SSH1_MASK_LOGIN)) {
if (!($this->bitmap & self::MASK_LOGIN)) {
user_error('Operation disallowed prior to login()');
return false;
}
if (!($this->bitmap & NET_SSH1_MASK_SHELL) && !$this->_initShell()) {
if (!($this->bitmap & self::MASK_SHELL) && !$this->_initShell()) {
user_error('Unable to initiate an interactive shell session');
return false;
}
$match = $expect;
while (true) {
if ($mode == NET_SSH1_READ_REGEX) {
if ($mode == self::READ__REGEX) {
preg_match($expect, $this->interactiveBuffer, $matches);
$match = isset($matches[0]) ? $matches[0] : '';
}
@ -964,7 +952,7 @@ class Net_SSH1
if ($response === true) {
return $this->_string_shift($this->interactiveBuffer, strlen($this->interactiveBuffer));
}
$this->interactiveBuffer.= substr($response[NET_SSH1_RESPONSE_DATA], 4);
$this->interactiveBuffer.= substr($response[self::RESPONSE_DATA], 4);
}
}
@ -978,12 +966,12 @@ class Net_SSH1
*/
function interactiveWrite($cmd)
{
if (!($this->bitmap & NET_SSH1_MASK_LOGIN)) {
if (!($this->bitmap & self::MASK_LOGIN)) {
user_error('Operation disallowed prior to login()');
return false;
}
if (!($this->bitmap & NET_SSH1_MASK_SHELL) && !$this->_initShell()) {
if (!($this->bitmap & self::MASK_SHELL) && !$this->_initShell()) {
user_error('Unable to initiate an interactive shell session');
return false;
}
@ -1013,12 +1001,12 @@ class Net_SSH1
*/
function interactiveRead()
{
if (!($this->bitmap & NET_SSH1_MASK_LOGIN)) {
if (!($this->bitmap & self::MASK_LOGIN)) {
user_error('Operation disallowed prior to login()');
return false;
}
if (!($this->bitmap & NET_SSH1_MASK_SHELL) && !$this->_initShell()) {
if (!($this->bitmap & self::MASK_SHELL) && !$this->_initShell()) {
user_error('Unable to initiate an interactive shell session');
return false;
}
@ -1027,7 +1015,7 @@ class Net_SSH1
$write = $except = null;
if (stream_select($read, $write, $except, 0)) {
$response = $this->_get_binary_packet();
return substr($response[NET_SSH1_RESPONSE_DATA], 4);
return substr($response[self::RESPONSE_DATA], 4);
} else {
return '';
}
@ -1070,9 +1058,9 @@ class Net_SSH1
/*
$response = $this->_get_binary_packet();
if ($response === true) {
$response = array(NET_SSH1_RESPONSE_TYPE => -1);
$response = array(self::RESPONSE_TYPE => -1);
}
switch ($response[NET_SSH1_RESPONSE_TYPE]) {
switch ($response[self::RESPONSE_TYPE]) {
case NET_SSH1_SMSG_EXITSTATUS:
$data = pack('C', NET_SSH1_CMSG_EXIT_CONFIRMATION);
break;
@ -1124,7 +1112,11 @@ class Net_SSH1
}
$start = strtok(microtime(), ' ') + strtok(''); // http://php.net/microtime#61838
$temp = unpack('Nlength', fread($this->fsock, 4));
$data = fread($this->fsock, 4);
if (strlen($data) < 4) {
return false;
}
$temp = unpack('Nlength', $data);
$padding_length = 8 - ($temp['length'] & 7);
$length = $temp['length'] + $padding_length;
@ -1145,6 +1137,9 @@ class Net_SSH1
$type = $raw[$padding_length];
$data = substr($raw, $padding_length + 1, -4);
if (strlen($raw) < 4) {
return false;
}
$temp = unpack('Ncrc', substr($raw, -4));
//if ( $temp['crc'] != $this->_crc($padding . $type . $data) ) {
@ -1162,8 +1157,8 @@ class Net_SSH1
}
return array(
NET_SSH1_RESPONSE_TYPE => $type,
NET_SSH1_RESPONSE_DATA => $data
self::RESPONSE_TYPE => $type,
self::RESPONSE_DATA => $data
);
}
@ -1186,7 +1181,7 @@ class Net_SSH1
$length = strlen($data) + 4;
$padding = crypt_random_string(8 - ($length & 7));
$padding = Random::string(8 - ($length & 7));
$orig = $data;
$data = $padding . $data;
@ -1336,22 +1331,18 @@ class Net_SSH1
* should be a number with the property that gcd($e, ($p - 1) * ($q - 1)) == 1. Could just make anything that
* calls this call modexp, instead, but I think this makes things clearer, maybe...
*
* @see self::Net_SSH1()
* @param Math_BigInteger $m
* @see self::__construct()
* @param BigInteger $m
* @param array $key
* @return Math_BigInteger
* @return BigInteger
* @access private
*/
function _rsa_crypt($m, $key)
{
/*
if (!class_exists('Crypt_RSA')) {
include_once 'Crypt/RSA.php';
}
$rsa = new Crypt_RSA();
$rsa->loadKey($key, CRYPT_RSA_PUBLIC_FORMAT_RAW);
$rsa->setEncryptionMode(CRYPT_RSA_ENCRYPTION_PKCS1);
$rsa = new RSA();
$rsa->loadKey($key, RSA::PUBLIC_FORMAT_RAW);
$rsa->setEncryptionMode(RSA::ENCRYPTION_PKCS1);
return $rsa->encrypt($m);
*/
@ -1372,13 +1363,13 @@ class Net_SSH1
$length = strlen($modulus) - strlen($m) - 3;
$random = '';
while (strlen($random) != $length) {
$block = crypt_random_string($length - strlen($random));
$block = Random::string($length - strlen($random));
$block = str_replace("\x00", '', $block);
$random.= $block;
}
$temp = chr(0) . chr(2) . $random . chr(0) . $m;
$m = new Math_BigInteger($temp, 256);
$m = new BigInteger($temp, 256);
$m = $m->modPow($key[0], $key[1]);
return $m->toBytes();
@ -1411,7 +1402,7 @@ class Net_SSH1
/**
* Returns a log of the packets that have been sent and received.
*
* 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')
* Returns a string if NET_SSH1_LOGGING == self::LOG_COMPLEX, an array if NET_SSH1_LOGGING == self::LOG_SIMPLE and false if !defined('NET_SSH1_LOGGING')
*
* @access public
* @return array|false|string
@ -1423,10 +1414,10 @@ class Net_SSH1
}
switch (NET_SSH1_LOGGING) {
case NET_SSH1_LOG_SIMPLE:
case self::LOG_SIMPLE:
return $this->message_number_log;
break;
case NET_SSH1_LOG_COMPLEX:
case self::LOG_COMPLEX:
return $this->_format_log($this->message_log, $this->protocol_flags_log);
break;
default:
@ -1547,7 +1538,7 @@ class Net_SSH1
*
* Just because a cipher is supported by an SSH1 server doesn't mean it's supported by this library. If $raw_output
* is set to true, returns, instead, an array of constants. ie. instead of array('Triple-DES in CBC mode'), you'll
* get array(NET_SSH1_CIPHER_3DES).
* get array(self::CIPHER_3DES).
*
* @param bool $raw_output
* @return array
@ -1563,7 +1554,7 @@ class Net_SSH1
*
* Just because a cipher is supported by an SSH1 server doesn't mean it's supported by this library. If $raw_output
* is set to true, returns, instead, an array of constants. ie. instead of array('password authentication'), you'll
* get array(NET_SSH1_AUTH_PASSWORD).
* get array(self::AUTH_PASSWORD).
*
* @param bool $raw_output
* @return array
@ -1597,16 +1588,16 @@ class Net_SSH1
{
switch (NET_SSH1_LOGGING) {
// useful for benchmarks
case NET_SSH1_LOG_SIMPLE:
case self::LOG_SIMPLE:
$this->protocol_flags_log[] = $protocol_flags;
break;
// the most useful log for SSH1
case NET_SSH1_LOG_COMPLEX:
case self::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) {
while ($this->log_size > self::LOG_MAX_SIZE) {
$this->log_size-= strlen(array_shift($this->message_log));
array_shift($this->protocol_flags_log);
}
@ -1614,19 +1605,19 @@ class Net_SSH1
// 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:
case self::LOG_REALTIME:
echo "<pre>\r\n" . $this->_format_log(array($message), array($protocol_flags)) . "\r\n</pre>\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.
// basically the same thing as self::LOG_REALTIME with the caveat that self::LOG_REALTIME_FILE
// needs to be defined and that the resultant log file will be capped out at self::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:
case self::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;
$filename = self::LOG_REALTIME_FILE;
$fp = fopen($filename, 'w');
$this->realtime_log_file = $fp;
}
@ -1640,7 +1631,7 @@ class Net_SSH1
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) {
if ($this->realtime_log_size > self::LOG_MAX_SIZE) {
fseek($this->realtime_log_file, 0);
$this->realtime_log_size = strlen($entry);
$this->realtime_log_wrap = true;

File diff suppressed because it is too large Load Diff

View File

@ -3,17 +3,16 @@
/**
* Pure-PHP ssh-agent client.
*
* PHP versions 4 and 5
* PHP version 5
*
* Here are some examples of how to use this library:
* <code>
* <?php
* include 'System/SSH/Agent.php';
* include 'Net/SSH2.php';
* include 'vendor/autoload.php';
*
* $agent = new System_SSH_Agent();
* $agent = new \phpseclib\System\SSH\Agent();
*
* $ssh = new Net_SSH2('www.domain.tld');
* $ssh = new \phpseclib\Net\SSH2('www.domain.tld');
* if (!$ssh->login('username', $agent)) {
* exit('Login Failed');
* }
@ -23,26 +22,8 @@
* ?>
* </code>
*
* 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
* @package SSH\Agent
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2014 Jim Wigginton
* @license http://www.opensource.org/licenses/mit-license.html MIT License
@ -50,21 +31,36 @@
* @internal See http://api.libssh.org/rfc/PROTOCOL.agent
*/
namespace phpseclib\System\SSH;
use phpseclib\Crypt\RSA;
use phpseclib\System\SSH\Agent\Identity;
/**
* Pure-PHP ssh-agent client identity factory
*
* requestIdentities() method pumps out \phpseclib\System\SSH\Agent\Identity objects
*
* @package SSH\Agent
* @author Jim Wigginton <terrafrost@php.net>
* @access internal
*/
class 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);
const 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);
const SSH_AGENT_IDENTITIES_ANSWER = 12;
// the SSH1 request is SSH_AGENTC_RSA_CHALLENGE (3)
define('SYSTEM_SSH_AGENTC_SIGN_REQUEST', 13);
const SSH_AGENTC_SIGN_REQUEST = 13;
// the SSH1 response is SSH_AGENT_RSA_RESPONSE (4)
define('SYSTEM_SSH_AGENT_SIGN_RESPONSE', 14);
const SSH_AGENT_SIGN_RESPONSE = 14;
/**#@-*/
/**@+
* Agent forwarding status
@ -72,166 +68,18 @@ define('SYSTEM_SSH_AGENT_SIGN_RESPONSE', 14);
* @access private
*/
// no forwarding requested and not active
define('SYSTEM_SSH_AGENT_FORWARD_NONE', 0);
const FORWARD_NONE = 0;
// request agent forwarding when opportune
define('SYSTEM_SSH_AGENT_FORWARD_REQUEST', 1);
const FORWARD_REQUEST = 1;
// forwarding has been request and is active
define('SYSTEM_SSH_AGENT_FORWARD_ACTIVE', 2);
const FORWARD_ACTIVE = 2;
/**#@-*/
/**
* 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 <terrafrost@php.net>
* @access internal
* Unused
*/
class System_SSH_Agent_Identity
{
/**
* Key Object
*
* @var Crypt_RSA
* @access private
* @see self::getPublicKey()
*/
var $key;
const SSH_AGENT_FAILURE = 5;
/**
* Key Blob
*
* @var string
* @access private
* @see self::sign()
*/
var $key_blob;
/**
* Socket Resource
*
* @var resource
* @access private
* @see self::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 int $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 int $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 <terrafrost@php.net>
* @access internal
*/
class System_SSH_Agent
{
/**
* Socket Resource
*
@ -245,7 +93,7 @@ class System_SSH_Agent
*
* @access private
*/
var $forward_status = SYSTEM_SSH_AGENT_FORWARD_NONE;
var $forward_status = self::FORWARD_NONE;
/**
* Buffer for accumulating forwarded authentication
@ -266,10 +114,10 @@ class System_SSH_Agent
/**
* Default Constructor
*
* @return System_SSH_Agent
* @return \phpseclib\System\SSH\Agent
* @access public
*/
function System_SSH_Agent()
function __construct()
{
switch (true) {
case isset($_SERVER['SSH_AUTH_SOCK']):
@ -293,7 +141,7 @@ class System_SSH_Agent
* 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
* Returns an array containing zero or more \phpseclib\System\SSH\Agent\Identity objects
*
* @return array
* @access public
@ -304,14 +152,14 @@ class System_SSH_Agent
return array();
}
$packet = pack('NC', 1, SYSTEM_SSH_AGENTC_REQUEST_IDENTITIES);
$packet = pack('NC', 1, self::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) {
if ($type != self::SSH_AGENT_IDENTITIES_ANSWER) {
user_error('Unable to request identities');
}
@ -329,10 +177,7 @@ class System_SSH_Agent
$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 = new RSA();
$key->loadKey($key_str);
break;
case 'ssh-dss':
@ -341,7 +186,7 @@ class System_SSH_Agent
}
// resources are passed by reference by default
if (isset($key)) {
$identity = new System_SSH_Agent_Identity($this->fsock);
$identity = new Identity($this->fsock);
$identity->setPublicKey($key);
$identity->setPublicKeyBlob($key_blob);
$identities[] = $identity;
@ -362,8 +207,8 @@ class System_SSH_Agent
*/
function startSSHForwarding($ssh)
{
if ($this->forward_status == SYSTEM_SSH_AGENT_FORWARD_NONE) {
$this->forward_status = SYSTEM_SSH_AGENT_FORWARD_REQUEST;
if ($this->forward_status == self::FORWARD_NONE) {
$this->forward_status = self::FORWARD_REQUEST;
}
}
@ -402,7 +247,7 @@ class System_SSH_Agent
}
$ssh->channel_status[$request_channel] = NET_SSH2_MSG_CHANNEL_OPEN;
$this->forward_status = SYSTEM_SSH_AGENT_FORWARD_ACTIVE;
$this->forward_status = self::FORWARD_ACTIVE;
return true;
}
@ -419,7 +264,7 @@ class System_SSH_Agent
*/
function _on_channel_open($ssh)
{
if ($this->forward_status == SYSTEM_SSH_AGENT_FORWARD_REQUEST) {
if ($this->forward_status == self::FORWARD_REQUEST) {
$this->_request_forwarding($ssh);
}
}

View File

@ -0,0 +1,158 @@
<?php
/**
* Pure-PHP ssh-agent client.
*
* PHP version 5
*
* @category System
* @package SSH\Agent
* @author Jim Wigginton <terrafrost@php.net>
* @copyright 2009 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
*/
namespace phpseclib\System\SSH\Agent;
use phpseclib\System\SSH\Agent;
/**
* Pure-PHP ssh-agent client identity object
*
* Instantiation should only be performed by \phpseclib\System\SSH\Agent class.
* This could be thought of as implementing an interface that phpseclib\Crypt\RSA
* implements. ie. maybe a Net_SSH_Auth_PublicKey interface or something.
* The methods in this interface would be getPublicKey and sign since those are the
* methods phpseclib looks for to perform public key authentication.
*
* @package SSH\Agent
* @author Jim Wigginton <terrafrost@php.net>
* @access internal
*/
class Identity
{
/**
* Key Object
*
* @var \phpseclib\Crypt\RSA
* @access private
* @see self::getPublicKey()
*/
var $key;
/**
* Key Blob
*
* @var string
* @access private
* @see self::sign()
*/
var $key_blob;
/**
* Socket Resource
*
* @var resource
* @access private
* @see self::sign()
*/
var $fsock;
/**
* Default Constructor.
*
* @param resource $fsock
* @return \phpseclib\System\SSH\Agent\Identity
* @access private
*/
function __construct($fsock)
{
$this->fsock = $fsock;
}
/**
* Set Public Key
*
* Called by \phpseclib\System\SSH\Agent::requestIdentities()
*
* @param \phpseclib\Crypt\RSA $key
* @access private
*/
function setPublicKey($key)
{
$this->key = $key;
$this->key->setPublicKey();
}
/**
* Set Public Key
*
* Called by \phpseclib\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 int $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 \phpseclib\Crypt\RSA::SIGNATURE_PKCS1
*
* @param int $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', Agent::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 != Agent::SSH_AGENT_SIGN_RESPONSE) {
user_error('Unable to retrieve 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);
}
}

View File

@ -1,39 +0,0 @@
<?php
/**
* Pure-PHP ssh-agent client wrapper
*
* PHP versions 4 and 5
*
* Originally System_SSH_Agent was accessed as System/SSH_Agent.php instead of
* System/SSH/Agent.php. The problem with this is that PSR0 compatible autoloaders
* don't support that kind of directory layout hence the package being moved and
* this "alias" being created to maintain backwards compatibility.
*
* 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 <terrafrost@php.net>
* @copyright 2014 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
*/
require_once 'SSH/Agent.php';

View File

@ -460,10 +460,6 @@ function get_preg($argument, $regexp) {
$language = $_SESSION['language'];
$language2 = explode ('.', $language);
setlocale(LC_ALL, $language2[0]);
// workaround for buggy PHP with Turkish
if (($language == 'tr_TR.utf8') && (version_compare(phpversion(), '5.5') < 0)) {
setlocale(LC_CTYPE, 'en_GB');
}
// First we check "positive" cases
$pregexpr = '';
switch ($regexp) {
@ -592,10 +588,6 @@ function get_preg($argument, $regexp) {
if (preg_match($pregexpr, $argument)) {
/* Bug in php preg_match doesn't work correct with utf8 */
setlocale(LC_ALL, $language);
// workaround for buggy PHP with Turkish
if (($language == 'tr_TR.utf8') && (version_compare(phpversion(), '5.5') < 0)) {
setlocale(LC_CTYPE, 'en_GB');
}
return true;
}
// Now we check "negative" cases, characters which are not allowed
@ -615,18 +607,10 @@ function get_preg($argument, $regexp) {
if (!preg_match($pregexpr, $argument)) {
/* Bug in php preg_match doesn't work correct with utf8 */
setlocale(LC_ALL, $language);
// workaround for buggy PHP with Turkish
if (($language == 'tr_TR.utf8') && (version_compare(phpversion(), '5.5') < 0)) {
setlocale(LC_CTYPE, 'en_GB');
}
return true;
}
/* Bug in php preg_match doesn't work correct with utf8 */
setlocale(LC_ALL, $language);
// workaround for buggy PHP with Turkish
if (($language == 'tr_TR.utf8') && (version_compare(phpversion(), '5.5') < 0)) {
setlocale(LC_CTYPE, 'en_GB');
}
return false;
}

View File

@ -36,8 +36,8 @@ include_once("../lib/status.inc");
/** config */
include_once("../lib/config.inc");
// check if PHP >= 5.4.0
if (version_compare(phpversion(), '5.4.0') < 0) {
// check if PHP >= 5.6.0
if (version_compare(phpversion(), '5.6.0') < 0) {
echo "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\n\n";
echo "<html>\n<head>\n";
echo "<meta http-equiv=\"content-type\" content=\"text/html; charset=UTF-8\">\n";
@ -47,7 +47,7 @@ if (version_compare(phpversion(), '5.4.0') < 0) {
echo "<link rel=\"icon\" href=\"../graphics/logo136.png\">\n";
echo "<title>LDAP Account Manager</title>\n";
echo "</head><body>\n";
StatusMessage("ERROR", "LAM needs a PHP 5 version which is greater or equal than 5.4.0.", "Please upgrade your PHP installation. The found version is " . phpversion());
StatusMessage("ERROR", "LAM needs a PHP 5 version which is greater or equal than 5.6.0.", "Please upgrade your PHP installation. The found version is " . phpversion());
echo "<br><br>";
echo "</body></html>";
exit();

View File

@ -73,10 +73,6 @@ function setlanguage() {
}
putenv("LANG=" . $code); // e.g. LANG=de_DE
setlocale(LC_ALL, $code); // set LC_ALL
// workaround for buggy PHP with Turkish
if (($code == 'tr_TR.utf8') && (version_compare(phpversion(), '5.5') < 0)) {
setlocale(LC_CTYPE, 'en_GB');
}
$locdir = substr(__FILE__, 0, strlen(__FILE__) - 15) . "/locale"; // set path to translations
bindtextdomain("messages", $locdir);
bind_textdomain_codeset("messages", $encoding);

View File

@ -1,129 +0,0 @@
<?php
/*
$Id$
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
Copyright (C) 2004 - 2016 Roland Gruber
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
/**
* This file includes functions to control lamdaemon.
*
* @author Tilo Lutz
* @author Roland Gruber
* @author Thomas Manninger
*
* @package modules
*/
/**
* Sends commands to lamdaemon script.
*
* @param array $command command to execute
* @param string $server remote server
* @return array Output of lamdaemon
*
*/
function lamdaemon($command, $server) {
if ($server == '') {
return array();
}
// add phpseclib to include path
set_include_path(get_include_path() . PATH_SEPARATOR . dirname(__FILE__) . '/3rdParty/phpseclib');
include_once('Net/SSH2.php');
try {
$handle = lamConnectSSH($server);
}
catch (Exception $e) {
return array("ERROR," . $e->getMessage() . "," . $server);
}
$output = $handle->exec("sudo " . $_SESSION['config']->get_scriptPath() . ' ' . escapeshellarg($command));
return array($output);
}
/**
* Connects to the given SSH server.
*
* @param String $server server name (e.g. localhost or localhost,1234)
* @return object handle
*/
function lamConnectSSH($server) {
// add phpseclib to include path
set_include_path(get_include_path() . PATH_SEPARATOR . dirname(__FILE__) . '/3rdParty/phpseclib');
include_once('Net/SSH2.php');
include_once('Crypt/RSA.php');
$serverNameParts = explode(",", $server);
$handle = false;
if (sizeof($serverNameParts) > 1) {
$handle = @new Net_SSH2($serverNameParts[0], $serverNameParts[1]);
}
else {
$handle = @new Net_SSH2($server);
}
if (!$handle) {
throw new Exception(_("Unable to connect to remote server!"));
}
lamLoginSSH($handle);
return $handle;
}
/**
* Performs a login to the provided SSH handle.
*
* @param handle $handle SSH handle
* @throws Exception login failed
*/
function lamLoginSSH($handle) {
$username = $_SESSION['config']->getScriptUserName();
$credentials = $_SESSION['ldap']->decrypt_login();
if (empty($username)) {
// get user name from current LAM user
$sr = @ldap_read($_SESSION['ldap']->server(), $credentials[0], "objectClass=posixAccount", array('uid'), 0, 0, 0, LDAP_DEREF_NEVER);
if ($sr) {
$entry = @ldap_get_entries($_SESSION['ldap']->server(), $sr);
$username = $entry[0]['uid'][0];
}
if (empty($username)) {
throw new Exception(sprintf(_("Your LAM admin user (%s) must be a valid Unix account to work with lamdaemon!"), getAbstractDN($credentials[0])));
}
}
$password = $credentials[1];
$keyPath = $_SESSION['config']->getScriptSSHKey();
if (!empty($keyPath)) {
// use key authentication
if (!file_exists($keyPath) || !is_readable($keyPath)) {
throw new Exception(sprintf(_("Unable to read %s."), htmlspecialchars($keyPath)));
}
$key = file_get_contents($keyPath);
$rsa = new Crypt_RSA();
$keyPassword = $_SESSION['config']->getScriptSSHKeyPassword();
if (!empty($keyPassword)) {
$rsa->setPassword($keyPassword);
}
if (!$rsa->loadKey($key)) {
throw new Exception(sprintf(_("Unable to load key %s."), htmlspecialchars($keyPath)));
}
$password = $rsa;
}
$login = @$handle->login($username, $password);
if (!$login) {
throw new Exception(_("Unable to login to remote server!"));
}
}
?>

View File

@ -45,8 +45,8 @@ include_once("account.inc");
include_once("baseModule.inc");
/** access to LDAP server */
include_once("ldap.inc");
/** lamdaemon functions */
include_once("lamdaemon.inc");
/** remote functions */
include_once("remote.inc");
/** security functions */
include_once("security.inc");
/** meta HTML classes */
@ -532,10 +532,12 @@ function buildUploadAccounts($type, $data, $ids, $selectedModules) {
}
}
if (sizeof($errors) > 0) {
for ($i = 0; (($i < sizeof($errors)) || ($i > 49)); $i++) call_user_func_array("StatusMessage", $errors[$i]);
for ($i = 0; (($i < sizeof($errors)) || ($i > 49)); $i++) {
call_user_func_array("StatusMessage", $errors[$i]);
}
return false;
}
else return $partialAccounts;
return $partialAccounts;
}
/**

View File

@ -475,7 +475,7 @@ class courierMailAccount extends baseModule {
'description' => _('Home directory'),
'help' => 'homeDirectory',
'example' => _('/home/smiller'),
'required' => 'true'
'required' => true
);
}
return $return;

View File

@ -248,7 +248,7 @@ By default, the nodes are configured as H-Nodes which fits for small networks. I
'help' => 'subnet',
'example' => '192.168.10.0',
'required' => true,
'unique' => 'true'
'unique' => true
),
array(
'name' => 'dhcp_settings_domainName',

View File

@ -161,7 +161,7 @@ class eduPerson extends baseModule {
'description' => _('Principal name'),
'help' => 'eduPersonPrincipalName',
'example' => _('user@company.com'),
'unique' => 'true'
'unique' => true
),
array(
'name' => 'eduPerson_primaryAffiliation',

View File

@ -32,7 +32,7 @@ $Id$
*
* @package modules
*/
class kolabSharedFolder extends baseModule { // TODO folder type
class kolabSharedFolder extends baseModule {
/** cache for mailHost values */
private $mailHostCache = null;
@ -49,7 +49,6 @@ class kolabSharedFolder extends baseModule { // TODO folder type
// call parent constructor
parent::__construct($scope);
$this->folderTypes = array(
// TODO reactivate types when stable 3.1 is released
/*_('Shared address book') => 'addressbook',
_('Shared calendar') => 'calendar',
_('Shared journal') => 'journal',

View File

@ -186,10 +186,8 @@ class posixAccount extends baseModule implements passwordService {
$loginShellsHelp = new htmlHelpLink('loginShells', get_class($this));
$loginShellsHelp->alignment = htmlElement::ALIGN_TOP;
$selfServiceContainer->addElement($loginShellsHelp, true);
if (version_compare(phpversion(), '5.4.26') >= 0) {
$selfServiceContainer->addElement(new htmlTableExtendedInputCheckbox('posixAccount_useOldPwd', false, _('Password change with old password')));
$selfServiceContainer->addElement(new htmlHelpLink('useOldPwd', get_class($this)), true);
}
$return['selfServiceSettings'] = $selfServiceContainer;
}
// profile checks
@ -734,7 +732,9 @@ class posixAccount extends baseModule implements passwordService {
elseif (!in_array($temp[0], $this->lamdaemonServers)) {
continue;
}
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -745,11 +745,11 @@ class posixAccount extends baseModule implements passwordService {
"0".$_SESSION['config']->get_scriptRights(),
$this->attributes['uidNumber'][0],
$this->attributes['gidNumber'][0])
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
$singleresult = explode(",", $result[0]);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'INFO') || ($singleresult[0] == 'WARN')) {
$messages[] = $singleresult;
}
@ -769,7 +769,9 @@ class posixAccount extends baseModule implements passwordService {
}
$temp = explode(":", $lamdaemonServers[$i]);
$server = $temp[0];
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -779,11 +781,11 @@ class posixAccount extends baseModule implements passwordService {
$this->orig[$homeDirAttr][0],
$this->attributes['uidNumber'][0],
$this->attributes[$homeDirAttr][0])
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
$singleresult = explode(",", $result[0]);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'INFO') || ($singleresult[0] == 'WARN')) {
$messages[] = $singleresult;
}
@ -800,7 +802,9 @@ class posixAccount extends baseModule implements passwordService {
}
$temp = explode(":", $lamdaemonServers[$i]);
$server = $temp[0];
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -810,11 +814,11 @@ class posixAccount extends baseModule implements passwordService {
$this->orig[$homeDirAttr][0],
$this->attributes['uidNumber'][0],
$this->attributes['gidNumber'][0])
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
$singleresult = explode(",", $result[0]);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'INFO') || ($singleresult[0] == 'WARN')) {
$messages[] = $singleresult;
}
@ -937,7 +941,9 @@ class posixAccount extends baseModule implements passwordService {
}
// try to delete directory on all servers
for ($i = 0; $i < sizeof($lamdaemonServers); $i++) {
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($lamdaemonServers[$i]);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -947,12 +953,11 @@ class posixAccount extends baseModule implements passwordService {
$this->attributes[$homeDirAttr][0],
$this->attributes['uidNumber'][0]
)
),
$lamdaemonServers[$i]);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
foreach ($result as $singleresult) {
$singleresult = explode(",", $singleresult);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (is_array($singleresult)) {
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'WARN') || ($singleresult[0] == 'INFO')) {
$return[] = $singleresult;
@ -961,7 +966,6 @@ class posixAccount extends baseModule implements passwordService {
}
}
}
}
// delete sudo rights
if (isset($_POST['deleteSudoers']) && ($_POST['deleteSudoers'] == 'on')) {
$result = searchLDAPByAttribute('sudoUser', $this->attributes['uid'][0], 'sudoRole', array('dn'), array('sudo'));
@ -1272,7 +1276,9 @@ class posixAccount extends baseModule implements passwordService {
$temp = explode(":", $lamdaemonServers[$i]);
$server = $temp[0];
if (isset($_POST['form_subpage_' . get_class($this) . '_homedir_create_' . $i])) {
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1283,12 +1289,11 @@ class posixAccount extends baseModule implements passwordService {
"0".$_SESSION['config']->get_scriptRights(),
$this->attributes['uidNumber'][0],
$this->attributes['gidNumber'][0])
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
foreach ($result as $singleresult) {
$singleresult = explode(",", $singleresult);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (is_array($singleresult)) {
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'WARN') || ($singleresult[0] == 'INFO')) {
$return[] = $singleresult;
@ -1296,9 +1301,10 @@ class posixAccount extends baseModule implements passwordService {
}
}
}
}
elseif (isset($_POST['form_subpage_' . get_class($this) . '_homedir_delete_' . $i])) {
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1308,12 +1314,11 @@ class posixAccount extends baseModule implements passwordService {
$this->attributes[$homeDirAttr][0],
$this->attributes['uidNumber'][0]
)
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
foreach ($result as $singleresult) {
$singleresult = explode(",", $singleresult);
if (!empty($result)) {
$singleresult = explode(",", $result);
if (is_array($singleresult)) {
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'WARN') || ($singleresult[0] == 'INFO')) {
$return[] = $singleresult;
@ -1322,7 +1327,6 @@ class posixAccount extends baseModule implements passwordService {
}
}
}
}
return $return;
}
@ -1662,7 +1666,9 @@ class posixAccount extends baseModule implements passwordService {
if (isset($temp[1])) {
$label = $temp[1];
}
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1670,11 +1676,11 @@ class posixAccount extends baseModule implements passwordService {
"home",
"check",
$this->attributes[$homeDirAttr][0])
),
$server);
));
$remote->disconnect();
// lamdaemon results
if (is_array($result)) {
$returnValue = trim($result[0]);
if (!empty($result)) {
$returnValue = trim($result);
if ($returnValue == 'ok') {
$homeServerContainer->addElement(new htmlOutputText($label));
$homeServerContainer->addElement(new htmlSpacer('5px', null));
@ -2533,7 +2539,9 @@ class posixAccount extends baseModule implements passwordService {
// create home directories
elseif ($temp['counter'] < (sizeof($temp['groups']) + sizeof($temp['createHomes']))) {
$pos = $temp['createHomes'][$temp['counter'] - sizeof($temp['groups'])];
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($data[$pos][$ids['posixAccount_createHomeDir']]);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -2545,11 +2553,11 @@ class posixAccount extends baseModule implements passwordService {
$accounts[$pos]['uidNumber'],
$accounts[$pos]['gidNumber'],
)
),
$data[$pos][$ids['posixAccount_createHomeDir']]);
));
$remote->disconnect();
$errors = array();
if (($result != false) && (sizeof($result) == 1)) {
$parts = explode(",", $result[0]);
if (!empty($result)) {
$parts = explode(",", $result);
if (in_array($parts[0], array('ERROR', 'WARN'))) {
$errors[] = $parts;
}

View File

@ -186,11 +186,14 @@ class quota extends baseModule {
$temp = explode(":", $lamdaemonServers[$s]);
$server = $temp[0];
// get quotas
$quotas = lamdaemon(implode(quota::$SPLIT_DELIMITER, array($userName, "quota", "get", $this->get_scope())), $server);
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$quotas = $remote->execute(implode(quota::$SPLIT_DELIMITER, array($userName, "quota", "get", $this->get_scope())));
$remote->disconnect();
if (sizeof($quotas) == 0) {
continue;
}
$allQuotas = explode(":", $quotas[0]);
$allQuotas = explode(":", $quotas);
array_pop($allQuotas); // remove empty element at the end
for ($i = 0; $i < sizeof($allQuotas); $i++) {
if (strpos($allQuotas[$i], quota::$QUOTA_PREFIX) !== 0) continue;
@ -280,7 +283,10 @@ class quota extends baseModule {
$quotastring = $quotastring . $this->quota[$server][$i][0] . ',' . $this->quota[$server][$i][2] . ',' . $this->quota[$server][$i][3]
. ',' . $this->quota[$server][$i][6] . ',' . $this->quota[$server][$i][7] . ':';
}
lamdaemon(implode(quota::$SPLIT_DELIMITER, array($id, "quota", "set", $this->get_scope(), "$quotastring\n")), $server);
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$remote->execute(implode(quota::$SPLIT_DELIMITER, array($id, "quota", "set", $this->get_scope(), "$quotastring\n")));
$remote->disconnect();
}
return $messages;
}
@ -319,7 +325,10 @@ class quota extends baseModule {
$quotastring = $quotastring . $this->quota[$server][$i][0] . ',0,0,0,0:';
$i++;
}
lamdaemon(implode(quota::$SPLIT_DELIMITER, array($id, "quota", "set", $this->get_scope(), "$quotastring\n")), $server);
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$remote->execute(implode(quota::$SPLIT_DELIMITER, array($id, "quota", "set", $this->get_scope(), "$quotastring\n")));
$remote->disconnect();
}
return array();
}
@ -483,11 +492,14 @@ class quota extends baseModule {
$description = $temp[1] . ' (' . $temp[0] . ')';
}
// Get quotas
$quotas = lamdaemon(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())), $server);
if (sizeof($quotas) == 0) {
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$quotas = $remote->execute(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())));
$remote->disconnect();
if (empty($quotas)) {
continue;
}
$dirs = explode(":", $quotas[0]);
$dirs = explode(":", $quotas);
array_pop($dirs); // remove empty element at the end
for ($i = 0; $i < sizeof($dirs); $i++) {
if (strpos($dirs[$i], quota::$QUOTA_PREFIX) !== 0) {
@ -556,8 +568,11 @@ class quota extends baseModule {
$server = $temp[0];
$id = $this->replaceSpecialChars($server);
// Get quotas
$quotas = lamdaemon(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())), $server);
$dirs = explode(":", $quotas[0]);
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$quotas = $remote->execute(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())));
$remote->disconnect();
$dirs = explode(":", $quotas);
array_pop($dirs); // remove empty element at the end
for ($i = 0; $i < sizeof($dirs); $i++) {
if (strpos($dirs[$i], quota::$QUOTA_PREFIX) !== 0) {
@ -669,8 +684,11 @@ class quota extends baseModule {
$temp = explode(":", $lamdaemonServers[$s]);
$server = $temp[0];
// Get quotas
$quotas = lamdaemon(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())), $server);
$dirs = explode(":", $quotas[0]);
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$quotas = $remote->execute(implode(quota::$SPLIT_DELIMITER, array("+", "quota", "get", $this->get_scope())));
$remote->disconnect();
$dirs = explode(":", $quotas);
array_pop($dirs); // remove empty element at the end
for ($i = 0; $i < sizeof($dirs); $i++) {
if (strpos($dirs[$i], quota::$QUOTA_PREFIX) !== 0) {
@ -786,16 +804,17 @@ class quota extends baseModule {
$dir = $mpParts[1];
$quotaString = implode(quota::$SPLIT_DELIMITER, array($name, "quota", "set", $this->get_scope(), $dir . ',' .
implode(',', $temp['accounts'][$name][$mountPoints[$m]]) . "\n"));
$result = lamdaemon($quotaString, $server);
if (is_array($result)) {
for ($i = 0; $i < sizeof($result); $i++) {
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute($quotaString);
$remote->disconnect();
if (!empty($result)) {
$parts = explode(",", $result);
if ($parts[0] == 'ERROR') {
$errors[] = array('ERROR', $parts[1], $parts[2]);
}
}
}
}
// set counters to next account/mount point
$temp['counter']++;
return array(

View File

@ -1,4 +1,5 @@
<?php
/*
$Id$
@ -64,7 +65,7 @@ class sambaSamAccount extends baseModule implements passwordService {
private $cachedGroupSIDList = null;
/** cache for domain list */
private $cachedDomainList = null;
/** delimiter for lamdaemon commands */
/** delimiter for remote commands */
private static $SPLIT_DELIMITER = "###x##y##x###";
@ -1541,16 +1542,18 @@ class sambaSamAccount extends baseModule implements passwordService {
$return->addElement(new htmlSpacer(null, '10px'), true);
$homeServerContainer = new htmlTable();
$homeServerContainer->colspan = 5;
// get list of lamdaemon servers
$lamdaemonServers = explode(";", $_SESSION['config']->get_scriptServers());
for ($i = 0; $i < sizeof($lamdaemonServers); $i++) {
$temp = explode(":", $lamdaemonServers[$i]);
// get list of remote servers
$remoteServers = explode(";", $_SESSION['config']->get_scriptServers());
for ($i = 0; $i < sizeof($remoteServers); $i++) {
$temp = explode(":", $remoteServers[$i]);
$server = $temp[0];
$label = $temp[0];
if (isset($temp[1])) {
$label = $temp[1];
}
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1558,11 +1561,11 @@ class sambaSamAccount extends baseModule implements passwordService {
"home",
"check",
$this->attributes['sambaProfilePath'][0])
),
$server);
// lamdaemon results
if (is_array($result)) {
$returnValue = trim($result[0]);
));
$remote->disconnect();
// remote command results
if (!empty($result)) {
$returnValue = trim($result);
if ($returnValue == 'ok') {
$homeServerContainer->addElement(new htmlOutputText($label));
$homeServerContainer->addElement(new htmlSpacer('5px', null));
@ -1614,13 +1617,15 @@ class sambaSamAccount extends baseModule implements passwordService {
if (empty($uidNumber) || empty($gidNumber)) {
return;
}
// get list of lamdaemon servers
$lamdaemonServers = explode(";", $_SESSION['config']->get_scriptServers());
for ($i = 0; $i < sizeof($lamdaemonServers); $i++) {
$temp = explode(":", $lamdaemonServers[$i]);
// get list of remote servers
$remoteServers = explode(";", $_SESSION['config']->get_scriptServers());
for ($i = 0; $i < sizeof($remoteServers); $i++) {
$temp = explode(":", $remoteServers[$i]);
$server = $temp[0];
if (isset($_POST['form_subpage_' . get_class($this) . '_homedir_create_' . $i])) {
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1631,12 +1636,11 @@ class sambaSamAccount extends baseModule implements passwordService {
"0".$_SESSION['config']->get_scriptRights(),
$uidNumber,
$gidNumber)
),
$server);
// lamdaemon results
if (is_array($result)) {
foreach ($result as $singleresult) {
$singleresult = explode(",", $singleresult);
));
$remote->disconnect();
// remote command results
if (!empty($result)) {
$singleresult = explode(",", $result);
if (is_array($singleresult)) {
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'WARN') || ($singleresult[0] == 'INFO')) {
$return[] = $singleresult;
@ -1644,9 +1648,10 @@ class sambaSamAccount extends baseModule implements passwordService {
}
}
}
}
elseif (isset($_POST['form_subpage_' . get_class($this) . '_homedir_delete_' . $i])) {
$result = lamdaemon(
$remote = new \LAM\REMOTE\Remote();
$remote->connect($server);
$result = $remote->execute(
implode(
self::$SPLIT_DELIMITER,
array(
@ -1656,12 +1661,11 @@ class sambaSamAccount extends baseModule implements passwordService {
$this->attributes['sambaProfilePath'][0],
$uidNumber
)
),
$server);
// lamdaemon results
if (is_array($result)) {
foreach ($result as $singleresult) {
$singleresult = explode(",", $singleresult);
));
$remote->disconnect();
// remote command results
if (!empty($result)) {
$singleresult = explode(",", $result);
if (is_array($singleresult)) {
if (($singleresult[0] == 'ERROR') || ($singleresult[0] == 'WARN') || ($singleresult[0] == 'INFO')) {
$return[] = $singleresult;
@ -1670,7 +1674,6 @@ class sambaSamAccount extends baseModule implements passwordService {
}
}
}
}
return $return;
}

164
lam/lib/remote.inc Normal file
View File

@ -0,0 +1,164 @@
<?php
namespace LAM\REMOTE;
use \Exception;
use \phpseclib\Net\SSH2;
use \phpseclib\Crypt\RSA;
/*
$Id$
This code is part of LDAP Account Manager (http://www.ldap-account-manager.org/)
Copyright (C) 2017 Roland Gruber
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*/
/**
* This file includes functions to control LAM remote executions.
*
* @author Roland Gruber
*
* @package modules
*/
/**
* Runs remote commands.
*
* @author Roland Gruber
*/
class Remote {
/** SSH2 server handle */
private $server = null;
/**
* Constructor, include SSH library.
*/
public function __construct() {
$this->includeSshLibrary();
}
/**
* Sends commands to remote script.
*
* @param string $command command to execute
* @return string output of remote script
*/
public function execute($command) {
if ($this->server == null) {
return array();
}
return $this->server->exec("sudo " . $_SESSION['config']->get_scriptPath() . ' ' . escapeshellarg($command));
}
/**
* Connects to the given SSH server.
*
* @param String $server server name (e.g. localhost or localhost,1234)
*/
public function connect($server) {
$serverNameParts = explode(",", $server);
$handle = false;
if (sizeof($serverNameParts) > 1) {
$handle = @new SSH2($serverNameParts[0], $serverNameParts[1]);
}
else {
$handle = @new SSH2($server);
}
if (!$handle) {
throw new Exception(_("Unable to connect to remote server!"));
}
$this->loginSSH($handle);
$this->server = $handle;
}
/**
* Closes the connection.
*/
public function disconnect() {
if ($this->server == null) {
return;
}
$this->server->disconnect();
}
/**
* Performs a login to the provided SSH handle.
*
* @param SSH2 $handle SSH handle
* @throws Exception login failed
*/
private function loginSSH($handle) {
$username = $_SESSION['config']->getScriptUserName();
$credentials = $_SESSION['ldap']->decrypt_login();
if (empty($username)) {
// get user name from current LAM user
$sr = @ldap_read($_SESSION['ldap']->server(), $credentials[0], "objectClass=posixAccount", array('uid'), 0, 0, 0, LDAP_DEREF_NEVER);
if ($sr) {
$entry = @ldap_get_entries($_SESSION['ldap']->server(), $sr);
$username = $entry[0]['uid'][0];
}
if (empty($username)) {
throw new Exception(sprintf(_("Your LAM admin user (%s) must be a valid Unix account to work with lamdaemon!"), getAbstractDN($credentials[0])));
}
}
$password = $credentials[1];
$keyPath = $_SESSION['config']->getScriptSSHKey();
if (!empty($keyPath)) {
// use key authentication
if (!file_exists($keyPath) || !is_readable($keyPath)) {
throw new Exception(sprintf(_("Unable to read %s."), htmlspecialchars($keyPath)));
}
$key = file_get_contents($keyPath);
$rsa = new RSA();
$keyPassword = $_SESSION['config']->getScriptSSHKeyPassword();
if (!empty($keyPassword)) {
$rsa->setPassword($keyPassword);
}
if (!$rsa->loadKey($key)) {
throw new Exception(sprintf(_("Unable to load key %s."), htmlspecialchars($keyPath)));
}
$password = $rsa;
}
$login = @$handle->login($username, $password);
if (!$login) {
throw new Exception(_("Unable to login to remote server!"));
}
}
/**
* Include the SSH files.
*/
private function includeSshLibrary() {
$prefix = dirname(__FILE__) . '/3rdParty/phpseclib/';
require_once($prefix . 'Crypt/Base.php');
require_once($prefix . 'Crypt/Blowfish.php');
require_once($prefix . 'Crypt/Hash.php');
require_once($prefix . 'Crypt/Random.php');
require_once($prefix . 'Crypt/RC4.php');
require_once($prefix . 'Crypt/Rijndael.php');
require_once($prefix . 'Crypt/AES.php');
require_once($prefix . 'Crypt/RSA.php');
require_once($prefix . 'Crypt/DES.php');
require_once($prefix . 'Crypt/TripleDES.php');
require_once($prefix . 'Crypt/Twofish.php');
require_once($prefix . 'Math/BigInteger.php');
require_once($prefix . 'System/SSH/Agent.php');
require_once($prefix . 'Net/SSH2.php');
}
}
?>

View File

@ -85,8 +85,8 @@ if (isset($_GET['DN'])) {
$result = $_SESSION['account']->load_account($DN);
if (sizeof($result) > 0) {
include '../main_header.php';
for ($i=0; $i<sizeof($result); $i++) {
call_user_func_array("StatusMessage", $result[$i]);
foreach ($result as $message) {
call_user_func_array("StatusMessage", $message);
}
include '../main_footer.php';
die();
@ -107,14 +107,6 @@ else if (count($_POST)==0) {
$_SESSION['account']->new_account();
}
// remove double slashes if magic quotes are on
if (get_magic_quotes_gpc() == 1) {
$postKeys = array_keys($_POST);
for ($i = 0; $i < sizeof($postKeys); $i++) {
if (is_string($_POST[$postKeys[$i]])) $_POST[$postKeys[$i]] = stripslashes($_POST[$postKeys[$i]]);
}
}
// show account page
$_SESSION['account']->continue_main();

View File

@ -625,13 +625,6 @@ function checkInput() {
$conf = &$_SESSION['conf_config'];
$types = $conf->get_ActiveTypes();
// remove double slashes if magic quotes are on
if (get_magic_quotes_gpc() == 1) {
$postKeys = array_keys($_POST);
for ($i = 0; $i < sizeof($postKeys); $i++) {
if (is_string($_POST[$postKeys[$i]])) $_POST[$postKeys[$i]] = stripslashes($_POST[$postKeys[$i]]);
}
}
// check new preferences
$errors = array();
if (!$conf->set_ServerURL($_POST['serverurl'])) {

View File

@ -90,13 +90,6 @@ $errors = array();
$messages = array();
// check if submit button was pressed
if (isset($_POST['submitFormData'])) {
// remove double slashes if magic quotes are on
if (get_magic_quotes_gpc() == 1) {
$postKeys = array_keys($_POST);
for ($i = 0; $i < sizeof($postKeys); $i++) {
if (is_string($_POST[$postKeys[$i]])) $_POST[$postKeys[$i]] = stripslashes($_POST[$postKeys[$i]]);
}
}
// set master password
if (isset($_POST['masterpassword']) && ($_POST['masterpassword'] != "")) {
if ($_POST['masterpassword'] && $_POST['masterpassword2'] && ($_POST['masterpassword'] == $_POST['masterpassword2'])) {

View File

@ -42,8 +42,8 @@ include_once('../lib/config.inc');
include_once('../lib/status.inc');
/** LDAP connection */
include_once('../lib/ldap.inc');
/** lamdaemon interface */
include_once('../lib/lamdaemon.inc');
/** remote interface */
include_once('../lib/remote.inc');
/** module interface */
include_once('../lib/modules.inc');
@ -105,7 +105,8 @@ if (isset($_GET['type']) && isset($_SESSION['delete_dn'])) {
echo "<b>" . _("Do you really want to remove the following accounts?") . "</b>";
echo "<br><br>\n";
echo "<table border=0>\n";
for ($i=0; $i<count($users); $i++) {
$userCount = sizeof($users);
for ($i = 0; $i < $userCount; $i++) {
echo "<tr>\n";
echo "<td><b>" . _("Account name:") . "</b> " . htmlspecialchars($users[$i]) . "</td>\n";
echo "<td>&nbsp;&nbsp;<b>" . _('DN') . ":</b> " . htmlspecialchars($_SESSION['delete_dn'][$i]) . "</td>\n";
@ -173,11 +174,11 @@ if (isset($_POST['delete'])) {
// Delete dns
$allOk = true;
$allErrors = array();
for ($m=0; $m<count($_SESSION['delete_dn']); $m++) {
foreach ($_SESSION['delete_dn'] as $deleteDN) {
// Set to true if an real error has happened
$stopprocessing = false;
// First load DN.
$_SESSION['account']->load_account($_SESSION['delete_dn'][$m]);
$_SESSION['account']->load_account($deleteDN);
// get commands and changes of each attribute
$moduleNames = array_keys($_SESSION['account']->getAccountModules());
$modules = $_SESSION['account']->getAccountModules();
@ -188,13 +189,13 @@ if (isset($_POST['delete'])) {
foreach ($moduleNames as $singlemodule) {
$success = true;
$messages = $modules[$singlemodule]->preDeleteActions();
for ($i = 0; $i < sizeof($messages); $i++) {
$errors[] = $messages[$i];
if ($messages[$i][0] == 'ERROR') {
foreach ($messages as $message) {
$errors[] = $message;
if ($message[0] == 'ERROR') {
$success = false;
$allOk = false;
}
elseif ($messages[$i][0] == 'WARN') {
elseif ($message[0] == 'WARN') {
$allOk = false;
}
}
@ -213,20 +214,21 @@ if (isset($_POST['delete'])) {
// merge changes
$DNs = array_keys($temp);
$attributes = array_merge_recursive($temp, $attributes);
for ($i=0; $i<count($DNs); $i++) {
$ops = array_keys($temp[$DNs[$i]]);
for ($j=0; $j<count($ops); $j++) {
$attrs = array_keys($temp[$DNs[$i]][$ops[$j]]);
for ($k=0; $k<count($attrs); $k++)
$attributes[$DNs[$i]][$ops[$j]][$attrs[$k]] = array_unique($attributes[$DNs[$i]][$ops[$j]][$attrs[$k]]);
foreach ($DNs as $dn) {
$ops = array_keys($temp[$dn]);
foreach ($ops as $op) {
$attrs = array_keys($temp[$dn][$op]);
foreach ($attrs as $attribute) {
$attributes[$dn][$op][$attribute] = array_unique($attributes[$dn][$op][$attribute]);
}
}
}
}
}
$DNs = array_keys($attributes);
for ($i=0; $i<count($DNs); $i++) {
if (isset($attributes[$DNs[$i]]['errors'])) {
foreach ($attributes[$DNs[$i]]['errors'] as $singleerror) {
foreach ($DNs as $dn) {
if (isset($attributes[$dn]['errors'])) {
foreach ($attributes[$dn]['errors'] as $singleerror) {
$errors[] = $singleerror;
if ($singleerror[0] == 'ERROR') {
$stopprocessing = true;
@ -236,28 +238,28 @@ if (isset($_POST['delete'])) {
}
if (!$stopprocessing) {
// modify attributes
if (isset($attributes[$DNs[$i]]['modify']) && !$stopprocessing) {
$success = @ldap_mod_replace($_SESSION['ldap']->server(), $DNs[$i], $attributes[$DNs[$i]]['modify']);
if (isset($attributes[$dn]['modify']) && !$stopprocessing) {
$success = @ldap_mod_replace($_SESSION['ldap']->server(), $dn, $attributes[$dn]['modify']);
if (!$success) {
$errors[] = array ('ERROR', sprintf(_('Was unable to modify attributes from DN: %s.'), $DNs[$i]), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$errors[] = array ('ERROR', sprintf(_('Was unable to modify attributes from DN: %s.'), $dn), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$stopprocessing = true;
$allOk = false;
}
}
// add attributes
if (isset($attributes[$DNs[$i]]['add']) && !$stopprocessing) {
$success = @ldap_mod_add($_SESSION['ldap']->server(), $DNs[$i], $attributes[$DNs[$i]]['add']);
if (isset($attributes[$dn]['add']) && !$stopprocessing) {
$success = @ldap_mod_add($_SESSION['ldap']->server(), $dn, $attributes[$dn]['add']);
if (!$success) {
$errors[] = array ('ERROR', sprintf(_('Was unable to add attributes to DN: %s.'), $DNs[$i]), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$errors[] = array ('ERROR', sprintf(_('Was unable to add attributes to DN: %s.'), $dn), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$stopprocessing = true;
$allOk = false;
}
}
// remove attributes
if (isset($attributes[$DNs[$i]]['remove']) && !$stopprocessing) {
$success = @ldap_mod_del($_SESSION['ldap']->server(), $DNs[$i], $attributes[$DNs[$i]]['remove']);
if (isset($attributes[$dn]['remove']) && !$stopprocessing) {
$success = @ldap_mod_del($_SESSION['ldap']->server(), $dn, $attributes[$dn]['remove']);
if (!$success) {
$errors[] = array ('ERROR', sprintf(_('Was unable to remove attributes from DN: %s.'), $DNs[$i]), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$errors[] = array ('ERROR', sprintf(_('Was unable to remove attributes from DN: %s.'), $dn), getDefaultLDAPErrorString($_SESSION['ldap']->server()));
$stopprocessing = true;
$allOk = false;
}
@ -267,7 +269,7 @@ if (isset($_POST['delete'])) {
}
if (!$stopprocessing) {
$recursive = !$_SESSION['account']->hasOnlyVirtualChildren();
$messages = deleteDN($_SESSION['delete_dn'][$m], $recursive);
$messages = deleteDN($deleteDN, $recursive);
$errors = array_merge($errors, $messages);
if (sizeof($errors) > 0) {
$stopprocessing = true;
@ -278,16 +280,16 @@ if (isset($_POST['delete'])) {
if (!$stopprocessing) {
foreach ($moduleNames as $singlemodule) {
$messages = $modules[$singlemodule]->postDeleteActions();
for ($i = 0; $i < sizeof($messages); $i++) {
$errors[] = $messages[$i];
if (($messages[$i][0] == 'ERROR') || ($messages[$i][0] == 'WARN')) {
foreach ($messages as $message) {
$errors[] = $message;
if (($message[0] == 'ERROR') || ($message[0] == 'WARN')) {
$allOk = false;
}
}
}
}
if (!$stopprocessing) {
echo sprintf(_('Deleted DN: %s'), $_SESSION['delete_dn'][$m]) . "<br>\n";
echo sprintf(_('Deleted DN: %s'), $deleteDN) . "<br>\n";
foreach ($errors as $error) {
call_user_func_array('StatusMessage', $error);
}
@ -295,7 +297,7 @@ if (isset($_POST['delete'])) {
flush();
}
else {
echo sprintf(_('Error while deleting DN: %s'), $_SESSION['delete_dn'][$m]) . "<br>\n";
echo sprintf(_('Error while deleting DN: %s'), $deleteDN) . "<br>\n";
foreach ($errors as $error) {
call_user_func_array('StatusMessage', $error);
}

View File

@ -54,19 +54,19 @@ if (!empty($_POST)) {
// check if user already pressed button
if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
if (isset($_POST['add_suff'])) {
$fail = array();
$errors = array();
$new_suff = $_POST['new_suff'];
$new_suff = str_replace("\\", "", $new_suff);
$new_suff = str_replace("'", "", $new_suff);
$new_suff = explode(";", $new_suff);
$failedDNs = array();
$error = array();
$newSuffixes = $_POST['new_suff'];
$newSuffixes = str_replace("\\", "", $newSuffixes);
$newSuffixes = str_replace("'", "", $newSuffixes);
$newSuffixes = explode(";", $newSuffixes);
// add entries
for ($i = 0; $i < sizeof($new_suff); $i++) {
foreach ($newSuffixes as $newSuffix) {
// check if entry is already present
$info = @ldap_read($_SESSION['ldap']->server(), escapeDN($new_suff[$i]), "objectclass=*", array('dn'), 0, 0, 0, LDAP_DEREF_NEVER);
$info = @ldap_read($_SESSION['ldap']->server(), escapeDN($newSuffix), "objectclass=*", array('dn'), 0, 0, 0, LDAP_DEREF_NEVER);
$res = @ldap_get_entries($_SESSION['ldap']->server(), $info);
if ($res) continue;
$suff = $new_suff[$i];
$suff = $newSuffix;
// generate DN and attributes
$tmp = explode(",", $suff);
$name = explode("=", $tmp[0]);
@ -78,7 +78,7 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
$attr['objectClass'] = 'organization';
$dn = $suff;
if (!@ldap_add($_SESSION['ldap']->server(), $dn, $attr)) {
$fail[] = $suff;
$failedDNs[] = $suff;
$error[] = ldap_error($_SESSION['ldap']->server());
continue;
}
@ -117,7 +117,7 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
$attr['ou'] = $headarray[1];
$dn = $subsuffs[$k];
if (!@ldap_add($_SESSION['ldap']->server(), $dn, $attr)) {
$fail[] = $suff;
$failedDNs[] = $suff;
$error[] = ldap_error($_SESSION['ldap']->server());
break;
}
@ -132,7 +132,7 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
}
$dn = $subsuffs[$k];
if (!@ldap_add($_SESSION['ldap']->server(), $dn, $attr)) {
$fail[] = $suff;
$failedDNs[] = $suff;
$error[] = ldap_error($_SESSION['ldap']->server());
break;
}
@ -141,7 +141,7 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
}
}
else {
$fail[] = $suff;
$failedDNs[] = $suff;
$error[] = ldap_error($_SESSION['ldap']->server());
}
}
@ -151,10 +151,10 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
include 'main_header.php';
// print error/success messages
if (isset($_POST['add_suff'])) {
if (sizeof($fail) > 0) {
if (sizeof($failedDNs) > 0) {
// print error messages
for ($i = 0; $i < sizeof($fail); $i++) {
StatusMessage("ERROR", _("Failed to create entry!") . "<br>" . htmlspecialchars($error[$i]), htmlspecialchars($fail[$i]));
for ($i = 0; $i < sizeof($failedDNs); $i++) {
StatusMessage("ERROR", _("Failed to create entry!") . "<br>" . htmlspecialchars($error[$i]), htmlspecialchars($failedDNs[$i]));
}
include 'main_footer.php';
}
@ -173,10 +173,10 @@ if (isset($_POST['add_suff']) || isset($_POST['cancel'])) {
}
// first show of page
$new_suff = $_GET['suffs'];
$new_suff = str_replace("\\", "", $new_suff);
$new_suff = str_replace("'", "", $new_suff);
$new_suff = explode(";", $new_suff);
$newSuffixes = $_GET['suffs'];
$newSuffixes = str_replace("\\", "", $newSuffixes);
$newSuffixes = str_replace("'", "", $newSuffixes);
$newSuffixes = explode(";", $newSuffixes);
include 'main_header.php';
echo '<div class="user-bright smallPaddingContent">';
@ -186,15 +186,15 @@ include 'main_header.php';
$container->addElement(new htmlOutputText(_("You can setup the LDAP suffixes for all account types in your LAM server profile on tab \"Account types\".")), true);
$container->addElement(new htmlSpacer(null, '10px'), true);
// print missing suffixes
for ($i = 0; $i < sizeof($new_suff); $i++) {
$container->addElement(new htmlOutputText($new_suff[$i]), true);
foreach ($newSuffixes as $newSuffix) {
$container->addElement(new htmlOutputText($newSuffix), true);
}
$container->addElement(new htmlSpacer(null, '10px'), true);
$buttonContainer = new htmlTable();
$buttonContainer->addElement(new htmlButton('add_suff', _("Create")));
$buttonContainer->addElement(new htmlButton('cancel', _("Cancel")));
$buttonContainer->addElement(new htmlHiddenInput('new_suff', implode(";", $new_suff)));
$buttonContainer->addElement(new htmlHiddenInput('new_suff', implode(";", $newSuffixes)));
$container->addElement($buttonContainer);
addSecurityTokenToMetaHTML($container);

View File

@ -177,7 +177,7 @@ $_SESSION['header'] .= "<meta http-equiv=\"pragma\" content=\"no-cache\">\n <me
* @param \LAM\ENV\LAMLicenseValidator $licenseValidator license validator
* @param string $error_message error message to display
*/
function display_LoginPage($config_object, $cfgMain, $licenseValidator, $error_message) {
function display_LoginPage(LAMConfig $config_object, LAMCfgMain $cfgMain, $licenseValidator, $error_message) {
logNewMessage(LOG_DEBUG, "Display login page");
// generate 256 bit key and initialization vector for user/passwd-encryption
if(function_exists('openssl_random_pseudo_bytes') && ($cfgMain->encryptSession == 'true')) {
@ -582,9 +582,6 @@ if(!empty($_POST['checklogin'])) {
display_LoginPage($_SESSION['config'], $_SESSION["cfgMain"], $licenseValidator, $error_message); // Empty password submitted. Return to login page.
exit();
}
if (get_magic_quotes_gpc() == 1) {
$_POST['passwd'] = stripslashes($_POST['passwd']);
}
$username = $_POST['username'];
$password = $_POST['passwd'];
}
@ -594,7 +591,7 @@ if(!empty($_POST['checklogin'])) {
$searchFilter = str_replace('%USER%', $username ,$searchFilter);
$searchDN = '';
$searchPassword = '';
if (($_SESSION['config']->getLoginSearchDN() != null) && ($_SESSION['config']->getLoginSearchDN() != '')) {
if (!empty($_SESSION['config']->getLoginSearchDN())) {
$searchDN = $_SESSION['config']->getLoginSearchDN();
$searchPassword = $_SESSION['config']->getLoginSearchPassword();
}

View File

@ -1,4 +1,5 @@
<?php
namespace LAM\AJAX;
/*
$Id$
@ -47,18 +48,19 @@ if (startSecureSession(false, true) === false) {
setlanguage();
lamAjax::handleRequest();
$ajax = new Ajax();
$ajax->handleRequest();
/**
* Manages all AJAX requests.
*/
class lamAjax {
class Ajax {
/**
* Manages an AJAX request.
*/
public static function handleRequest() {
lamAjax::setHeader();
public function handleRequest() {
$this->setHeader();
// check token
validateSecurityToken(false);
@ -84,16 +86,16 @@ class lamAjax {
$jsonInput = $_POST['jsonInput'];
if ($function == 'passwordStrengthCheck') {
lamAjax::checkPasswordStrength($jsonInput);
$this->checkPasswordStrength($jsonInput);
}
enforceUserIsLoggedIn();
if ($function == 'passwordChange') {
lamAjax::managePasswordChange($jsonInput);
$this->managePasswordChange($jsonInput);
}
elseif ($function == 'upload') {
include_once('../../lib/upload.inc');
$typeManager = new \LAM\TYPES\TypeManager();
$uploader = new LAM\UPLOAD\Uploader($typeManager->getConfiguredType($_GET['typeId']));
$uploader = new \LAM\UPLOAD\Uploader($typeManager->getConfiguredType($_GET['typeId']));
ob_start();
$jsonOut = $uploader->doUpload();
ob_end_clean();
@ -115,7 +117,7 @@ class lamAjax {
*
* @param array $input input parameters
*/
public static function managePasswordChange($input) {
private static function managePasswordChange($input) {
$return = $_SESSION['account']->setNewPassword($input);
echo json_encode($return);
}
@ -125,7 +127,7 @@ class lamAjax {
*
* @param array $input input parameters
*/
public static function checkPasswordStrength($input) {
private function checkPasswordStrength($input) {
$password = $input['password'];
$result = checkPasswordStrength($password, null, null);
echo json_encode(array("result" => $result));

View File

@ -81,7 +81,7 @@ if (isset($_POST['createOU']) || isset($_POST['deleteOU'])) {
// check if ou already exists
$new_dn = "ou=" . $_POST['newOU'] . "," . $_POST['parentOU'];
$found = ldapGetDN($new_dn);
if ($found == null) {
if ($found === null) {
// add new ou
$ou = array();
$ou['objectClass'] = "organizationalunit";

View File

@ -15,6 +15,7 @@ use \htmlInputFileUpload;
use \htmlHelpLink;
use \htmlInputField;
use \htmlHiddenInput;
use \LAM\TYPES\TypeManager;
/*
$Id$
@ -89,7 +90,7 @@ if(isset($_POST['createNewTemplate'])) {
exit();
}
$typeManager = new \LAM\TYPES\TypeManager();
$typeManager = new TypeManager();
$types = $typeManager->getConfiguredTypes();
$sortedTypes = array();
foreach ($types as $type) {
@ -141,7 +142,7 @@ if (!empty($_POST['import'])) {
}
$errMessage = importStructures($_POST['typeId'], $options, $serverProfiles, $typeManager);
}
if ($errMessage != null) {
if ($errMessage !== null) {
$errMessage->colspan = 10;
$container->addElement($errMessage, true);
}
@ -166,7 +167,7 @@ if (!empty($_POST['export'])) {
$name = $_POST['name_' . $typeId];
$errMessage = exportStructures($typeId, $name, $options, $serverProfiles, $typeManager);
}
if ($errMessage != null) {
if ($errMessage !== null) {
$errMessage->colspan = 10;
$container->addElement($errMessage, true);
}
@ -195,23 +196,18 @@ foreach ($sortedTypes as $typeId => $title) {
'scope' => $type->getScope(),
'title' => $title,
'icon' => $type->getIcon(),
'templates' => "");
'templates' => \LAM\PDF\getPDFStructures($type->getId()));
$availableTypes[$title] = $type->getId();
}
// get list of templates for each account type
for ($i = 0; $i < sizeof($templateClasses); $i++) {
$templateClasses[$i]['templates'] = \LAM\PDF\getPDFStructures($templateClasses[$i]['typeId']);
}
// check if a template should be edited
for ($i = 0; $i < sizeof($templateClasses); $i++) {
if (isset($_POST['editTemplate_' . $templateClasses[$i]['typeId']]) || isset($_POST['editTemplate_' . $templateClasses[$i]['typeId'] . '_x'])) {
metaRefresh('pdfpage.php?type=' . htmlspecialchars($templateClasses[$i]['typeId']) . '&edit=' . htmlspecialchars($_POST['template_' . $templateClasses[$i]['typeId']]));
foreach ($templateClasses as $templateClass) {
if (isset($_POST['editTemplate_' . $templateClass['typeId']]) || isset($_POST['editTemplate_' . $templateClass['typeId'] . '_x'])) {
metaRefresh('pdfpage.php?type=' . htmlspecialchars($templateClass['typeId']) . '&edit=' . htmlspecialchars($_POST['template_' . $templateClass['typeId']]));
exit;
}
}
include '../main_header.php';
?>
<div class="user-bright smallPaddingContent">
<form enctype="multipart/form-data" action="pdfmain.php" method="post" name="pdfmainForm" >
@ -246,38 +242,38 @@ include '../main_header.php';
// existing templates
$container->addElement(new htmlSubTitle(_("Manage existing PDF structures")), true);
$existingContainer = new htmlTable();
for ($i = 0; $i < sizeof($templateClasses); $i++) {
foreach ($templateClasses as $templateClass) {
if ($i > 0) {
$existingContainer->addElement(new htmlSpacer(null, '10px'), true);
}
$existingContainer->addElement(new htmlImage('../../graphics/' . $templateClasses[$i]['icon']));
$existingContainer->addElement(new htmlImage('../../graphics/' . $templateClass['icon']));
$existingContainer->addElement(new htmlSpacer('3px', null));
$existingContainer->addElement(new htmlOutputText($templateClasses[$i]['title']));
$existingContainer->addElement(new htmlOutputText($templateClass['title']));
$existingContainer->addElement(new htmlSpacer('3px', null));
$select = new htmlSelect('template_' . $templateClasses[$i]['typeId'], $templateClasses[$i]['templates']);
$select = new htmlSelect('template_' . $templateClass['typeId'], $templateClass['templates']);
$select->setWidth('15em');
$existingContainer->addElement($select);
$existingContainer->addElement(new htmlSpacer('3px', null));
$exEditButton = new htmlButton('editTemplate_' . $templateClasses[$i]['typeId'], 'edit.png', true);
$exEditButton = new htmlButton('editTemplate_' . $templateClass['typeId'], 'edit.png', true);
$exEditButton->setTitle(_('Edit'));
$existingContainer->addElement($exEditButton);
$deleteLink = new htmlLink(null, '#', '../../graphics/delete.png');
$deleteLink->setTitle(_('Delete'));
$deleteLink->setOnClick("profileShowDeleteDialog('" . _('Delete') . "', '" . _('Ok') . "', '" . _('Cancel') . "', '" . $templateClasses[$i]['typeId'] . "', '" . 'template_' . $templateClasses[$i]['typeId'] . "');");
$deleteLink->setOnClick("profileShowDeleteDialog('" . _('Delete') . "', '" . _('Ok') . "', '" . _('Cancel') . "', '" . $templateClass['typeId'] . "', '" . 'template_' . $templateClass['typeId'] . "');");
$existingContainer->addElement($deleteLink);
if (count($configProfiles) > 1) {
$importLink = new htmlLink(null, '#', '../../graphics/import.png');
$importLink->setTitle(_('Import PDF structures'));
$importLink->setOnClick("showDistributionDialog('" . _("Import PDF structures") . "', '" .
_('Ok') . "', '" . _('Cancel') . "', '" . $templateClasses[$i]['typeId'] . "', 'import');");
_('Ok') . "', '" . _('Cancel') . "', '" . $templateClass['typeId'] . "', 'import');");
$existingContainer->addElement($importLink);
}
$exportLink = new htmlLink(null, '#', '../../graphics/export.png');
$exportLink->setTitle(_('Export PDF structure'));
$exportLink->setOnClick("showDistributionDialog('" . _("Export PDF structure") . "', '" .
_('Ok') . "', '" . _('Cancel') . "', '" . $templateClasses[$i]['typeId'] . "', 'export', '" . 'template_' . $templateClasses[$i]['typeId'] . "', '" . $_SESSION['config']->getName() . "');");
_('Ok') . "', '" . _('Cancel') . "', '" . $templateClass['typeId'] . "', 'export', '" . 'template_' . $templateClass['typeId'] . "', '" . $_SESSION['config']->getName() . "');");
$existingContainer->addElement($exportLink);
$existingContainer->addNewLine();
}
@ -314,12 +310,12 @@ include '../main_header.php';
echo "</form>\n";
echo "</div>\n";
for ($i = 0; $i < sizeof($templateClasses); $i++) {
$typeId = $templateClasses[$i]['typeId'];
$scope = $templateClasses[$i]['scope'];
foreach ($templateClasses as $templateClass) {
$typeId = $templateClass['typeId'];
$scope = $templateClass['scope'];
$importOptions = array();
foreach ($configProfiles as $profile) {
$typeManagerImport = new \LAM\TYPES\TypeManager($serverProfiles[$profile]);
$typeManagerImport = new TypeManager($serverProfiles[$profile]);
$typesImport = $typeManagerImport->getConfiguredTypesForScope($scope);
foreach ($typesImport as $typeImport) {
if (($profile != $_SESSION['config']->getName()) || ($typeImport->getId() != $typeId)) {
@ -374,7 +370,7 @@ include '../main_header.php';
$container->addElement(new htmlOutputText(_("Target server profile")), true);
$exportOptions = array();
foreach ($configProfiles as $profile) {
$typeManagerExport = new \LAM\TYPES\TypeManager($serverProfiles[$profile]);
$typeManagerExport = new TypeManager($serverProfiles[$profile]);
$typesExport = $typeManagerExport->getConfiguredTypesForScope($scope);
foreach ($typesExport as $typeExport) {
if (($profile != $_SESSION['config']->getName()) || ($typeExport->getId() != $typeId)) {
@ -430,18 +426,18 @@ include '../main_footer.php';
* @param string $typeId type id
* @param array $options options
* @param \LAMConfig[] $serverProfiles server profiles (name => profile object)
* @param \LAM\TYPES\TypeManager $typeManager type manager
* @param TypeManager $typeManager type manager
* @return \htmlStatusMessage message or null
*/
function importStructures($typeId, $options, &$serverProfiles, &$typeManager) {
function importStructures($typeId, $options, &$serverProfiles, TypeManager &$typeManager) {
foreach ($options as $option) {
$sourceConfName = $option['conf'];
$sourceTypeId = $option['typeId'];
$sourceName = $option['name'];
$sourceTypeManager = new \LAM\TYPES\TypeManager($serverProfiles[$sourceConfName]);
$sourceTypeManager = new TypeManager($serverProfiles[$sourceConfName]);
$sourceType = $sourceTypeManager->getConfiguredType($sourceTypeId);
$targetType = $typeManager->getConfiguredType($typeId);
if (($sourceType != null) && ($targetType != null)) {
if (($sourceType !== null) && ($targetType !== null)) {
try {
\LAM\PDF\copyStructure($sourceType, $sourceName, $targetType);
}
@ -460,12 +456,12 @@ function importStructures($typeId, $options, &$serverProfiles, &$typeManager) {
* @param string $name profile name
* @param array $options options
* @param \LAMConfig[] $serverProfiles server profiles (name => profile object)
* @param \LAM\TYPES\TypeManager $typeManager type manager
* @param TypeManager $typeManager type manager
* @return \htmlStatusMessage message or null
*/
function exportStructures($typeId, $name, $options, &$serverProfiles, &$typeManager) {
function exportStructures($typeId, $name, $options, &$serverProfiles, TypeManager &$typeManager) {
$sourceType = $typeManager->getConfiguredType($typeId);
if ($sourceType == null) {
if ($sourceType === null) {
return null;
}
foreach ($options as $option) {
@ -480,9 +476,9 @@ function exportStructures($typeId, $name, $options, &$serverProfiles, &$typeMana
}
else {
$targetTypeId = $option['typeId'];
$targetTypeManager = new \LAM\TYPES\TypeManager($serverProfiles[$targetConfName]);
$targetTypeManager = new TypeManager($serverProfiles[$targetConfName]);
$targetType = $targetTypeManager->getConfiguredType($targetTypeId);
if ($targetType != null) {
if ($targetType !== null) {
try {
\LAM\PDF\copyStructure($sourceType, $name, $targetType);
}

View File

@ -496,7 +496,7 @@ function translateFieldIDToName($id, $scope, $availablePDFFields) {
*
* @param PDFStructure $structure
*/
function updateBasicSettings(&$structure) {
function updateBasicSettings(PDFStructure &$structure) {
// set headline
if (isset($_POST['headline'])) {
$structure->setTitle(str_replace('<', '', str_replace('>', '', $_POST['headline'])));
@ -516,7 +516,7 @@ function updateBasicSettings(&$structure) {
*
* @param PDFStructure $structure
*/
function updateSectionTitles(&$structure) {
function updateSectionTitles(PDFStructure &$structure) {
$sections = $structure->getSections();
foreach ($_POST as $key => $value) {
if (strpos($key, 'section_') === 0) {
@ -531,7 +531,7 @@ function updateSectionTitles(&$structure) {
*
* @param PDFStructure $structure
*/
function addSection(&$structure) {
function addSection(PDFStructure &$structure) {
$sections = $structure->getSections();
// add a new text field
if(isset($_POST['add_text'])) {
@ -570,7 +570,7 @@ function addSection(&$structure) {
*
* @param PDFStructure $structure
*/
function addSectionEntry(&$structure) {
function addSectionEntry(PDFStructure &$structure) {
if(isset($_POST['add_new_field'])) {
$field = new PDFSectionEntry($_POST['new_field']);
$sections = $structure->getSections();
@ -587,7 +587,7 @@ function addSectionEntry(&$structure) {
*
* @param PDFStructure $structure
*/
function removeItem(&$structure) {
function removeItem(PDFStructure &$structure) {
$sections = $structure->getSections();
foreach ($_POST as $key => $value) {
// remove section
@ -617,7 +617,7 @@ function removeItem(&$structure) {
*
* @param PDFStructure $structure
*/
function moveUp(&$structure) {
function moveUp(PDFStructure &$structure) {
$sections = $structure->getSections();
foreach ($_POST as $key => $value) {
// move section
@ -649,7 +649,7 @@ function moveUp(&$structure) {
*
* @param PDFStructure $structure
*/
function moveDown(&$structure) {
function moveDown(PDFStructure &$structure) {
$sections = $structure->getSections();
foreach ($_POST as $key => $value) {
// move section

View File

@ -14,6 +14,7 @@ use \htmlOutputText;
use \htmlHelpLink;
use \htmlHiddenInput;
use \htmlInputField;
use \LAM\TYPES\TypeManager;
/*
$Id$
@ -67,7 +68,7 @@ if (!empty($_POST)) {
validateSecurityToken();
}
$typeManager = new \LAM\TYPES\TypeManager();
$typeManager = new TypeManager();
$types = $typeManager->getConfiguredTypes();
$profileClasses = array();
$profileClassesTemp = array();
@ -158,7 +159,7 @@ if (!empty($_POST['import'])) {
}
$errMessage = importProfiles($_POST['typeId'], $options, $serverProfiles, $typeManager);
}
if ($errMessage != null) {
if ($errMessage !== null) {
$errMessage->colspan = 10;
$container->addElement($errMessage, true);
}
@ -181,7 +182,7 @@ if (!empty($_POST['export'])) {
$name = $_POST['name_' . $typeId];
$errMessage = exportProfiles($typeId, $name, $options, $serverProfiles, $typeManager);
}
if ($errMessage != null) {
if ($errMessage !== null) {
$errMessage->colspan = 10;
$container->addElement($errMessage, true);
}
@ -274,7 +275,7 @@ for ($i = 0; $i < sizeof($profileClasses); $i++) {
$scope = $profileClasses[$i]['scope'];
$importOptions = array();
foreach ($configProfiles as $profile) {
$typeManagerImport = new \LAM\TYPES\TypeManager($serverProfiles[$profile]);
$typeManagerImport = new TypeManager($serverProfiles[$profile]);
$typesImport = $typeManagerImport->getConfiguredTypesForScope($scope);
foreach ($typesImport as $typeImport) {
if (($profile != $_SESSION['config']->getName()) || ($typeImport->getId() != $typeId)) {
@ -329,7 +330,7 @@ for ($i = 0; $i < sizeof($profileClasses); $i++) {
$container->addElement(new htmlOutputText(_("Target server profile")), true);
$exportOptions = array();
foreach ($configProfiles as $profile) {
$typeManagerExport = new \LAM\TYPES\TypeManager($serverProfiles[$profile]);
$typeManagerExport = new TypeManager($serverProfiles[$profile]);
$typesExport = $typeManagerExport->getConfiguredTypesForScope($scope);
foreach ($typesExport as $typeExport) {
if (($profile != $_SESSION['config']->getName()) || ($typeExport->getId() != $typeId)) {
@ -385,18 +386,18 @@ include '../main_footer.php';
* @param string $typeId type id
* @param array $options options
* @param \LAMConfig[] $serverProfiles server profiles (name => profile object)
* @param \LAM\TYPES\TypeManager $typeManager type manager
* @param TypeManager $typeManager type manager
* @return \htmlStatusMessage message or null
*/
function importProfiles($typeId, $options, &$serverProfiles, &$typeManager) {
function importProfiles($typeId, $options, &$serverProfiles, TypeManager &$typeManager) {
foreach ($options as $option) {
$sourceConfName = $option['conf'];
$sourceTypeId = $option['typeId'];
$sourceName = $option['name'];
$sourceTypeManager = new \LAM\TYPES\TypeManager($serverProfiles[$sourceConfName]);
$sourceTypeManager = new TypeManager($serverProfiles[$sourceConfName]);
$sourceType = $sourceTypeManager->getConfiguredType($sourceTypeId);
$targetType = $typeManager->getConfiguredType($typeId);
if (($sourceType != null) && ($targetType != null)) {
if (($sourceType !== null) && ($targetType !== null)) {
try {
\LAM\PROFILES\copyAccountProfile($sourceType, $sourceName, $targetType);
}
@ -415,12 +416,12 @@ function importProfiles($typeId, $options, &$serverProfiles, &$typeManager) {
* @param string $name profile name
* @param array $options options
* @param \LAMConfig[] $serverProfiles server profiles (name => profile object)
* @param \LAM\TYPES\TypeManager $typeManager type manager
* @param TypeManager $typeManager type manager
* @return \htmlStatusMessage message or null
*/
function exportProfiles($typeId, $name, $options, &$serverProfiles, &$typeManager) {
function exportProfiles($typeId, $name, $options, &$serverProfiles, TypeManager &$typeManager) {
$sourceType = $typeManager->getConfiguredType($typeId);
if ($sourceType == null) {
if ($sourceType === null) {
return null;
}
foreach ($options as $option) {
@ -435,9 +436,9 @@ function exportProfiles($typeId, $name, $options, &$serverProfiles, &$typeManage
}
else {
$targetTypeId = $option['typeId'];
$targetTypeManager = new \LAM\TYPES\TypeManager($serverProfiles[$targetConfName]);
$targetTypeManager = new TypeManager($serverProfiles[$targetConfName]);
$targetType = $targetTypeManager->getConfiguredType($targetTypeId);
if ($targetType != null) {
if ($targetType !== null) {
try {
\LAM\PROFILES\copyAccountProfile($sourceType, $name, $targetType);
}

View File

@ -125,13 +125,6 @@ if (isset($_POST['save'])) {
}
}
// remove double slashes if magic quotes are on
if (get_magic_quotes_gpc() == 1) {
foreach ($opt_keys as $element) {
if (isset($options[$element][0]) && is_string($options[$element][0])) $options[$element][0] = stripslashes($options[$element][0]);
}
}
// check options
$errors = checkProfileOptions($_POST['accounttype'], $options);
if (sizeof($errors) == 0) { // input data is valid, save profile
@ -169,13 +162,8 @@ if (isset($_POST['save'])) {
$postKeys = array_keys($_POST);
for ($i = 0; $i < sizeof($postKeys); $i++) {
if (!is_array($_POST[$postKeys[$i]])) {
if (get_magic_quotes_gpc() == 1) {
$old_options[$postKeys[$i]] = array(stripslashes($_POST[$postKeys[$i]]));
}
else {
$old_options[$postKeys[$i]] = array($_POST[$postKeys[$i]]);
}
}
else {
$old_options[$postKeys[$i]] = $_POST[$postKeys[$i]];
}
@ -241,7 +229,7 @@ for ($m = 0; $m < sizeof($modules); $m++) {
if (sizeof($options[$modules[$m]]) < 1) continue;
$module = new $modules[$m]($type->getScope());
$icon = $module->getIcon();
if (($icon != null) && !(strpos($icon, 'http') === 0) && !(strpos($icon, '/') === 0)) {
if (!empty($icon) && !(strpos($icon, 'http') === 0) && !(strpos($icon, '/') === 0)) {
$icon = '../../graphics/' . $icon;
}
$container = new htmlTable();

View File

@ -1,4 +1,18 @@
<?php
namespace LAM\TOOLS\TESTS;
use \LAM\REMOTE\Remote;
use \htmlTable;
use \htmlTitle;
use \htmlOutputText;
use \htmlSelect;
use \htmlInputCheckbox;
use \htmlSpacer;
use \htmlButton;
use \htmlStatusMessage;
use \htmlImage;
use \htmlSubTitle;
use \Exception;
/*
$Id$
@ -22,7 +36,7 @@ $Id$
*/
/**
* Tests the lamdaemon script.
* Tests the remote script.
*
* @author Roland Gruber
* @author Thomas Manninger
@ -67,7 +81,7 @@ for ($i = 0; $i < sizeof($servers); $i++) {
}
if (isset($_POST['runTest'])) {
lamRunLamdaemonTestSuite($_POST['server'], $serverTitles[$_POST['server']] , isset($_POST['checkQuotas']), $container);
lamRunTestSuite($_POST['server'], $serverTitles[$_POST['server']] , isset($_POST['checkQuotas']), $container);
}
else if ((sizeof($servers) > 0) && isset($servers[0]) && ($servers[0] != '')) {
$container->addElement(new htmlOutputText(_("Server")));
@ -111,22 +125,22 @@ include '../main_footer.php';
*
* @param string $command test command
* @param boolean $stopTest specifies if test should be run
* @param connection $handle SSH connection
* @param Remote $remote SSH connection
* @param string $testText describing text
* @param htmlTable $container container for HTML output
* @return boolean true, if errors occured
*/
function lamTestLamdaemon($command, $stopTest, $handle, $testText, $container) {
function testRemoteCommand($command, $stopTest, $remote, $testText, $container) {
$okImage = "../../graphics/pass.png";
$failImage = "../../graphics/fail.png";
$spacer = new htmlSpacer('10px', null);
// run lamdaemon and get user quotas
// run remote command
if (!$stopTest) {
$container->addElement(new htmlOutputText($testText));
$container->addElement($spacer);
flush();
$lamdaemonOk = false;
$output = $handle->exec("sudo " . $_SESSION['config']->get_scriptPath() . ' ' . escapeshellarg($command));
$output = $remote->execute($command);
if ((stripos(strtolower($output), "error") === false) && ((strpos($output, 'INFO,') === 0) || (strpos($output, 'QUOTA_ENTRY') === 0))) {
$lamdaemonOk = true;
}
@ -170,7 +184,7 @@ function lamTestLamdaemon($command, $stopTest, $handle, $testText, $container) {
* @param boolean $testQuota true, if Quotas should be checked
* @param htmlTable $container container for HTML output
*/
function lamRunLamdaemonTestSuite($serverName, $serverTitle, $testQuota, $container) {
function lamRunTestSuite($serverName, $serverTitle, $testQuota, $container) {
$SPLIT_DELIMITER = "###x##y##x###";
$LAMDAEMON_PROTOCOL_VERSION = '5';
$okImage = "../../graphics/pass.png";
@ -246,13 +260,14 @@ function lamRunLamdaemonTestSuite($serverName, $serverTitle, $testQuota, $contai
flush();
// check SSH login
$remote = new Remote();
if (!$stopTest) {
$container->addElement(new htmlOutputText(_("SSH connection")));
$container->addElement($spacer);
flush();
$sshOk = false;
try {
$handle = lamConnectSSH($serverName);
$remote->connect($serverName);
$container->addElement(new htmlImage($okImage));
$container->addElement($spacer);
$container->addElement(new htmlOutputText(_("SSH connection established.")), true);
@ -268,23 +283,21 @@ function lamRunLamdaemonTestSuite($serverName, $serverTitle, $testQuota, $contai
flush();
if (!$stopTest) {
$stopTest = lamTestLamdaemon("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "basic", $stopTest, $handle, _("Execute lamdaemon"), $container);
$stopTest = testRemoteCommand("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "basic", $stopTest, $remote, _("Execute lamdaemon"), $container);
}
if (!$stopTest) {
$stopTest = lamTestLamdaemon("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "version" . $SPLIT_DELIMITER . $LAMDAEMON_PROTOCOL_VERSION, $stopTest, $handle, _("Lamdaemon version"), $container);
$stopTest = testRemoteCommand("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "version" . $SPLIT_DELIMITER . $LAMDAEMON_PROTOCOL_VERSION, $stopTest, $remote, _("Lamdaemon version"), $container);
}
if (!$stopTest) {
$handle = lamConnectSSH($serverName);
$stopTest = lamTestLamdaemon("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "nss" . $SPLIT_DELIMITER . "$userName", $stopTest, $handle, _("Lamdaemon: check NSS LDAP"), $container);
$stopTest = testRemoteCommand("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "nss" . $SPLIT_DELIMITER . "$userName", $stopTest, $remote, _("Lamdaemon: check NSS LDAP"), $container);
if (!$stopTest && $testQuota) {
$handle = lamConnectSSH($serverName);
$stopTest = lamTestLamdaemon("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "quota", $stopTest, $handle, _("Lamdaemon: Quota module installed"), $container);
$handle = lamConnectSSH($serverName);
$stopTest = lamTestLamdaemon("+" . $SPLIT_DELIMITER . "quota" . $SPLIT_DELIMITER . "get" . $SPLIT_DELIMITER . "user", $stopTest, $handle, _("Lamdaemon: read quotas"), $container);
$stopTest = testRemoteCommand("+" . $SPLIT_DELIMITER . "test" . $SPLIT_DELIMITER . "quota", $stopTest, $remote, _("Lamdaemon: Quota module installed"), $container);
$stopTest = testRemoteCommand("+" . $SPLIT_DELIMITER . "quota" . $SPLIT_DELIMITER . "get" . $SPLIT_DELIMITER . "user", $stopTest, $remote, _("Lamdaemon: read quotas"), $container);
}
}
$remote->disconnect();
$container->addElement(new htmlSpacer(null, '10px'), true);
$endMessage = new htmlOutputText(_("Lamdaemon test finished."));

View File

@ -140,7 +140,7 @@ if ($_FILES['inputfile'] && ($_FILES['inputfile']['size'] > 0)) {
$checkcolumns = array();
$columns = call_user_func_array('array_merge', $columns);
for ($i = 0; $i < sizeof($columns); $i++) {
if (isset($columns[$i]['required']) && ($columns[$i]['required'] == true)) {
if (isset($columns[$i]['required']) && ($columns[$i]['required'] === true)) {
if (isset($ids[$columns[$i]['name']])) $checkcolumns[] = $ids[$columns[$i]['name']];
else $errors[] = array(_("A required column is missing in your CSV file."), $columns[$i]['name']);
}
@ -201,7 +201,7 @@ if ($_FILES['inputfile'] && ($_FILES['inputfile']['size'] > 0)) {
// let modules build accounts
else {
$accounts = buildUploadAccounts($type, $data, $ids, $selectedModules);
if ($accounts != false) {
if ($accounts !== false) {
$rdnList = getRDNAttributes($type->getId(), $selectedModules);
$suffix = $type->getSuffix();
// set DN
@ -282,7 +282,7 @@ include '../main_footer.php';
* @param array $selectedModules selected modules for upload
* @param htmlTable $container table container
*/
function massPrintBackButton($typeId, $selectedModules, &$container) {
function massPrintBackButton($typeId, $selectedModules, htmlTable &$container) {
$backButton = new htmlButton('submit', _('Back'));
$backButton->setIconClass('backButton');
$container->addElement($backButton);

View File

@ -256,7 +256,7 @@ include '../main_footer.php';
* @param \LAM\TYPES\ConfiguredType $type account type
* @param array $selectedModules list of selected account modules
*/
function showMainPage($type, $selectedModules) {
function showMainPage(\LAM\TYPES\ConfiguredType $type, $selectedModules) {
$scope = $type->getScope();
echo '<div class="' . $scope . '-bright smallPaddingContent">';
// get input fields from modules
@ -382,7 +382,7 @@ function showMainPage($type, $selectedModules) {
$columnContainer->addElement(new htmlSpacer(null, '10px'), true);
$module = moduleCache::getModule($modules[$m], $scope);
$icon = $module->getIcon();
if (($icon != null) && !(strpos($icon, 'http') === 0) && !(strpos($icon, '/') === 0)) {
if (!empty($icon) && !(strpos($icon, 'http') === 0) && !(strpos($icon, '/') === 0)) {
$icon = '../../graphics/' . $icon;
}
$moduleTitle = new htmlSubTitle(getModuleAlias($modules[$m], $scope), $icon);
@ -413,7 +413,7 @@ function showMainPage($type, $selectedModules) {
$odd = true;
for ($i = 0; $i < sizeof($columns[$modules[$m]]); $i++) {
$required = false;
if (isset($columns[$modules[$m]][$i]['required']) && ($columns[$modules[$m]][$i]['required'] == true)) {
if (isset($columns[$modules[$m]][$i]['required']) && ($columns[$modules[$m]][$i]['required'] === true)) {
$required = true;
}
$rowCells = array();