]> git.mxchange.org Git - quix0rs-gnu-social.git/blob - plugins/OStatus/extlib/Crypt/RSA/Key.php
generate keypairs for users, and put them in the XRD for discovery
[quix0rs-gnu-social.git] / plugins / OStatus / extlib / Crypt / RSA / Key.php
1 <?php
2 /**
3  * Crypt_RSA allows to do following operations:
4  *     - key pair generation
5  *     - encryption and decryption
6  *     - signing and sign validation
7  *
8  * PHP versions 4 and 5
9  *
10  * LICENSE: This source file is subject to version 3.0 of the PHP license
11  * that is available through the world-wide-web at the following URI:
12  * http://www.php.net/license/3_0.txt.  If you did not receive a copy of
13  * the PHP License and are unable to obtain it through the web, please
14  * send a note to license@php.net so we can mail you a copy immediately.
15  *
16  * @category  Encryption
17  * @package   Crypt_RSA
18  * @author    Alexander Valyalkin <valyala@gmail.com>
19  * @copyright 2005 Alexander Valyalkin
20  * @license   http://www.php.net/license/3_0.txt  PHP License 3.0
21  * @version   CVS: $Id: Key.php,v 1.6 2009/01/05 08:30:29 clockwerx Exp $
22  * @link      http://pear.php.net/package/Crypt_RSA
23  */
24
25 /**
26  * RSA error handling facilities
27  */
28 require_once 'Crypt/RSA/ErrorHandler.php';
29
30 /**
31  * loader for RSA math wrappers
32  */
33 require_once 'Crypt/RSA/MathLoader.php';
34
35 /**
36  * Crypt_RSA_Key class, derived from Crypt_RSA_ErrorHandler
37  *
38  * Provides the following functions:
39  *  - getKeyLength() - returns bit key length
40  *  - getExponent() - returns key exponent as binary string
41  *  - getModulus() - returns key modulus as binary string
42  *  - getKeyType() - returns type of the key (public or private)
43  *  - toString() - returns serialized key as string
44  *  - fromString($key_str) - static function; returns key, unserialized from string
45  *  - isValid($key) - static function for validating of $key
46  *
47  * Example usage:
48  *    // create new 1024-bit key pair
49  *    $key_pair = new Crypt_RSA_KeyPair(1024);
50  * 
51  *    // get public key (its class is Crypt_RSA_Key)
52  *    $key = $key_pair->getPublicKey();
53  *
54  *    // get key length
55  *    $len = $key->getKeyLength();
56  *
57  *    // get modulus as string
58  *    $modulus = $key->getModulus();
59  *
60  *    // get exponent as string
61  *    $exponent = $key->getExponent();
62  *
63  *    // get string represenation of key (use it instead of serialization of Crypt_RSA_Key object)
64  *    $key_in_str = $key->toString();
65  *
66  *    // restore key object from string using 'BigInt' math wrapper
67  *    $key = Crypt_RSA_Key::fromString($key_in_str, 'BigInt');
68  *
69  *    // error check
70  *    if ($key->isError()) {
71  *        echo "error while unserializing key object:\n";
72  *        $erorr = $key->getLastError();
73  *        echo $error->getMessage(), "\n";
74  *    }
75  *
76  *    // validate key
77  *    if (Crypt_RSA_Key::isValid($key)) echo 'valid key';
78  *    else echo 'invalid key';
79  *
80  *    // using factory() method instead of constructor (it returns PEAR_Error object on failure)
81  *    $rsa_obj = &Crypt_RSA_Key::factory($modulus, $exp, $key_type);
82  *    if (PEAR::isError($rsa_obj)) {
83  *        echo "error: ", $rsa_obj->getMessage(), "\n";
84  *    }
85  *
86  * @category  Encryption
87  * @package   Crypt_RSA
88  * @author    Alexander Valyalkin <valyala@gmail.com>
89  * @copyright 2005 Alexander Valyalkin
90  * @license   http://www.php.net/license/3_0.txt  PHP License 3.0
91  * @version   Release: @package_version@
92  * @link      http://pear.php.net/package/Crypt_RSA
93  * @access    public
94  */
95 class Crypt_RSA_Key extends Crypt_RSA_ErrorHandler
96 {
97     /**
98      * Reference to math wrapper object, which is used to
99      * manipulate large integers in RSA algorithm.
100      *
101      * @var object of Crypt_RSA_Math_* class
102      * @access private
103      */
104     var $_math_obj;
105
106     /**
107      * shared modulus
108      *
109      * @var string
110      * @access private
111      */
112     var $_modulus;
113
114     /**
115      * exponent
116      *
117      * @var string
118      * @access private
119      */
120     var $_exp;
121
122     /**
123      * key type (private or public)
124      *
125      * @var string
126      * @access private
127      */
128     var $_key_type;
129
130     /**
131      * key length in bits
132      *
133      * @var int
134      * @access private
135      */
136     var $_key_len;
137
138     /**
139      * Crypt_RSA_Key constructor.
140      *
141      * You should pass in the name of math wrapper, which will be used to
142      *        perform different operations with big integers.
143      *        See contents of Crypt/RSA/Math folder for examples of wrappers.
144      *        Read docs/Crypt_RSA/docs/math_wrappers.txt for details.
145      *
146      * @param string $modulus       key modulus
147      * @param string $exp           key exponent
148      * @param string $key_type      type of the key (public or private)
149      * @param string $wrapper_name  wrapper to use
150      * @param string $error_handler name of error handler function
151      *
152      * @access public
153      */
154     function Crypt_RSA_Key($modulus, $exp, $key_type, $wrapper_name = 'default', $error_handler = '')
155     {
156         // set error handler
157         $this->setErrorHandler($error_handler);
158         // try to load math wrapper $wrapper_name
159         $obj = &Crypt_RSA_MathLoader::loadWrapper($wrapper_name);
160         if ($this->isError($obj)) {
161             // error during loading of math wrapper
162             $this->pushError($obj); // push error object into error list
163             return;
164         }
165         $this->_math_obj = &$obj;
166
167         $this->_modulus = $modulus;
168         $this->_exp = $exp;
169
170         if (!in_array($key_type, array('private', 'public'))) {
171             $this->pushError('invalid key type. It must be private or public', CRYPT_RSA_ERROR_WRONG_KEY_TYPE);
172             return;
173         }
174         $this->_key_type = $key_type;
175
176         /* check length of modulus & exponent ( abs(modulus) > abs(exp) ) */
177         $mod_num = $this->_math_obj->bin2int($this->_modulus);
178         $exp_num = $this->_math_obj->bin2int($this->_exp);
179
180         if ($this->_math_obj->cmpAbs($mod_num, $exp_num) <= 0) {
181             $this->pushError('modulus must be greater than exponent', CRYPT_RSA_ERROR_EXP_GE_MOD);
182             return;
183         }
184
185         // determine key length
186         $this->_key_len = $this->_math_obj->bitLen($mod_num);
187     }
188
189     /**
190      * Crypt_RSA_Key factory.
191      *
192      * @param string $modulus       key modulus
193      * @param string $exp           key exponent
194      * @param string $key_type      type of the key (public or private)
195      * @param string $wrapper_name  wrapper to use
196      * @param string $error_handler name of error handler function
197      *
198      * @return object   new Crypt_RSA_Key object on success or PEAR_Error object on failure
199      * @access public
200      */
201     function factory($modulus, $exp, $key_type, $wrapper_name = 'default', $error_handler = '')
202     {
203         $obj = new Crypt_RSA_Key($modulus, $exp, $key_type, $wrapper_name, $error_handler);
204         if ($obj->isError()) {
205             // error during creating a new object. Retrurn PEAR_Error object
206             return $obj->getLastError();
207         }
208         // object created successfully. Return it
209         return $obj;
210     }
211
212     /**
213      * Calculates bit length of the key
214      *
215      * @return int    bit length of key
216      * @access public
217      */
218     function getKeyLength()
219     {
220         return $this->_key_len;
221     }
222
223     /**
224      * Returns modulus part of the key as binary string,
225      * which can be used to construct new Crypt_RSA_Key object.
226      *
227      * @return string  modulus as binary string
228      * @access public
229      */
230     function getModulus()
231     {
232         return $this->_modulus;
233     }
234
235     /**
236      * Returns exponent part of the key as binary string,
237      * which can be used to construct new Crypt_RSA_Key object.
238      *
239      * @return string  exponent as binary string
240      * @access public
241      */
242     function getExponent()
243     {
244         return $this->_exp;
245     }
246
247     /**
248      * Returns key type (public, private)
249      *
250      * @return string  key type (public, private)
251      * @access public
252      */
253     function getKeyType()
254     {
255         return $this->_key_type;
256     }
257
258     /**
259      * Returns string representation of key
260      *
261      * @return string  key, serialized to string
262      * @access public
263      */
264     function toString()
265     {
266         return base64_encode(
267             serialize(
268                 array($this->_modulus, $this->_exp, $this->_key_type)
269             )
270         );
271     }
272
273     /**
274      * Returns Crypt_RSA_Key object, unserialized from
275      * string representation of key.
276      *
277      * optional parameter $wrapper_name - is the name of math wrapper,
278      * which will be used during unserialization of this object.
279      *
280      * This function can be called statically:
281      *     $key = Crypt_RSA_Key::fromString($key_in_string, 'BigInt');
282      *
283      * @param string $key_str      RSA key, serialized into string
284      * @param string $wrapper_name optional math wrapper name
285      *
286      * @return object        key as Crypt_RSA_Key object
287      * @access public
288      * @static
289      */
290     function fromString($key_str, $wrapper_name = 'default')
291     {
292         list($modulus, $exponent, $key_type) = unserialize(base64_decode($key_str));
293         $obj = new Crypt_RSA_Key($modulus, $exponent, $key_type, $wrapper_name);
294         return $obj;
295     }
296
297     /**
298      * Validates key
299      * This function can be called statically:
300      *    $is_valid = Crypt_RSA_Key::isValid($key)
301      *
302      * Returns true, if $key is valid Crypt_RSA key, else returns false
303      *
304      * @param object $key Crypt_RSA_Key object for validating
305      *
306      * @return bool        true if $key is valid, else false
307      * @access public
308      */
309     function isValid($key)
310     {
311         return (is_object($key) && strtolower(get_class($key)) === strtolower(__CLASS__));
312     }
313 }
314
315 ?>