New experimental plugin 'secure mail'
authorfabrixxm <fabrix.xm@gmail.com>
Mon, 29 Dec 2014 17:10:32 +0000 (18:10 +0100)
committerfabrixxm <fabrix.xm@gmail.com>
Mon, 29 Dec 2014 17:10:32 +0000 (18:10 +0100)
14 files changed:
securemail/README.md [new file with mode: 0644]
securemail/php-gpg/.gitignore [new file with mode: 0644]
securemail/php-gpg/README.md [new file with mode: 0644]
securemail/php-gpg/libs/GPG.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/AES.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/Cipher.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/Expanded_Key.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/Public_Key.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/Utility.php [new file with mode: 0644]
securemail/php-gpg/libs/GPG/globals.php [new file with mode: 0644]
securemail/php-gpg/tests/gpg/EncryptTest.php [new file with mode: 0644]
securemail/php-gpg/tests/gpg/KeyTest.php [new file with mode: 0644]
securemail/php-gpg/tests/runtests.sh [new file with mode: 0644]
securemail/securemail.php [new file with mode: 0644]

diff --git a/securemail/README.md b/securemail/README.md
new file mode 100644 (file)
index 0000000..2f24c53
--- /dev/null
@@ -0,0 +1,11 @@
+Secure Mail
+-----------
+
+Send notification mails to user encrypted with GPG.
+Each user can enable it and submit his public key under Settings-> Addon 
+-> "Secure Mail" Settings.
+
+Use 'php-gpg' library, a pure PHP implementation of GPG/PGP, released 
+under GPL. See [project repo](https://github.com/jasonhinkle/php-gpg).
+
+This plugin need Friendica version > 3.3.2 to work.
diff --git a/securemail/php-gpg/.gitignore b/securemail/php-gpg/.gitignore
new file mode 100644 (file)
index 0000000..0bd34b3
--- /dev/null
@@ -0,0 +1,3 @@
+/.buildpath
+/.settings
+.DS_Store
\ No newline at end of file
diff --git a/securemail/php-gpg/README.md b/securemail/php-gpg/README.md
new file mode 100644 (file)
index 0000000..4929115
--- /dev/null
@@ -0,0 +1,39 @@
+php-gpg
+=======
+
+php-gpg is a pure PHP implementation of GPG/PGP (currently supports encryption only).  The library does not require PGP/GPG binaries and should run on any platform that supports PHP.
+
+This library is useful for encrypting data before it is sent over an insecure protocol (for example email).  Messages encrypted with this library are compatible and can be decrypted by standard GPG/PGP clients.
+
+Features/Limitations
+--------------------
+
+ * Supports RSA, DSA public key length of 2,4,8,16,512,1024,2048 or 4096
+ * Currently supports only encrypt
+
+Hey You!  If you have a good understanding of public key encryption and want to implement signing or decryption your pull request would be welcome.
+Usage
+-----
+
+```php
+require_once 'libs/GPG.php';
+
+$gpg = new GPG();
+
+// create an instance of a GPG public key object based on ASCII key
+$pub_key = new GPG_Public_Key($public_key_ascii);
+
+// using the key, encrypt your plain text using the public key
+$encrypted = $gpg->encrypt($pub_key,$plain_text_string);
+
+echo $encrypted;
+
+```
+
+License
+-------
+
+GPL http://www.gnu.org/copyleft/gpl.html
+
+I'd like to release this under a more permissive license, but since PGP & GPG itself are GPL, I think this library is likely bound to the terms of GPL as well.
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG.php b/securemail/php-gpg/libs/GPG.php
new file mode 100644 (file)
index 0000000..053a54b
--- /dev/null
@@ -0,0 +1,186 @@
+<?php\r
+/** @package    php-gpg */\r
+\r
+/** require supporting files */\r
+require_once("GPG/Expanded_Key.php");\r
+require_once("GPG/Public_Key.php");\r
+require_once("GPG/AES.php");\r
+require_once("GPG/globals.php");\r
+\r
+/**\r
+ * Pure PHP implementation of PHP/GPG encryption.  \r
+ * Supports RSA, DSA public key length of 2,4,8,16,512,1024,2048 or 4096\r
+ * Currently supports only encrypt\r
+ *\r
+ * @package php-gpg::Encryption\r
+ * @link http://www.verysimple.com/\r
+ * @copyright 1997-2012 VerySimple, Inc.\r
+ * @license http://www.gnu.org/licenses/gpl.html  GPL\r
+ * @todo implement decryption\r
+ * @version 1.1\r
+ * \r
+ * @example \r
+ *             require_once 'libs/GPG.php';\r
+ *             $gpg = new GPG();\r
+ *             $pub_key = new GPG_Public_Key($public_key_ascii);\r
+ *             $encrypted = $gpg->encrypt($pub_key,$plain_text_string);\r
+ */\r
+class GPG \r
+{\r
+\r
+       private $width = 16;\r
+       private $el = array(3, 5, 9, 17, 513, 1025, 2049, 4097);\r
+       private $version = "1.4.7";\r
+\r
+       private function gpg_encrypt($key, $text) {\r
+\r
+               $i = 0;\r
+               $i = 0;\r
+               $len = strlen($text);\r
+               $len = strlen($text);\r
+               $iblock = array_fill(0, $this->width, 0);\r
+               $rblock = array_fill(0, $this->width, 0);\r
+               $ct = array_fill(0, $this->width + 2, 0);\r
+        \r
+               $cipher = "";\r
+\r
+               if($len % $this->width) {\r
+                       for($i = ($len % $this->width); $i < $this->width; $i++) $text .= "\0";\r
+               }\r
+        \r
+               $ekey = new Expanded_Key($key);\r
+\r
+               for($i = 0; $i < $this->width; $i++) {\r
+                       $iblock[$i] = 0;\r
+                       $rblock[$i] = GPG_Utility::c_random();\r
+               }\r
+\r
+\r
+               $iblock = GPG_AES::encrypt($iblock, $ekey);\r
+               for($i = 0; $i < $this->width; $i++) {\r
+                       $ct[$i] = ($iblock[$i] ^= $rblock[$i]);\r
+               }\r
+\r
+               $iblock = GPG_AES::encrypt($iblock, $ekey);\r
+               $ct[$this->width]   = ($iblock[0] ^ $rblock[$this->width - 2]);\r
+               $ct[$this->width + 1] = ($iblock[1] ^ $rblock[$this->width - 1]);\r
+        \r
+               for($i = 0; $i < $this->width + 2; $i++) $cipher .= chr($ct[$i]);\r
+\r
+               $iblock = array_slice($ct, 2, $this->width + 2);\r
+\r
+               for($n = 0; $n < strlen($text); $n += $this->width) {\r
+                       $iblock = GPG_AES::encrypt($iblock, $ekey);\r
+                       for($i = 0; $i < $this->width; $i++) {\r
+                               $iblock[$i] ^= ord($text[$n + $i]);\r
+                               $cipher .= chr($iblock[$i]);\r
+                       }\r
+               }\r
+        \r
+               return substr($cipher, 0, $len + $this->width + 2);\r
+       }\r
+\r
+       private function gpg_header($tag, $len)\r
+       {\r
+               if ($len > 0xff) $tag += 1;\r
+               $h = chr($tag);\r
+               if ($len > 0xff) $h .= chr($len / 0x100);\r
+               $h .= chr($len % 0x100);\r
+\r
+               return $h;\r
+       }\r
+\r
+       private function gpg_session($key_id, $key_type, $session_key, $public_key)\r
+       { \r
+\r
+               $mod = array();\r
+               $exp = array();\r
+               $enc = "";\r
+        \r
+               $s = base64_decode($public_key);\r
+               $l = floor((ord($s[0]) * 256 + ord($s[1]) + 7) / 8);\r
+               $mod = mpi2b(substr($s, 0, $l + 2));\r
+               if($key_type) {\r
+                       $grp = array();\r
+                       $y = array();\r
+                       $B = array();\r
+                       $C = array();\r
+\r
+                       $l2 = floor((ord($s[$l + 2]) * 256 + ord($s[$l + 3]) + 7) / 8) + 2;\r
+                       $grp = mpi2b(substr($s, $l + 2, $l2));\r
+                       $y = mpi2b(substr($s, $l + 2 + $l2));\r
+                       $exp[0] = $this->el[GPG_Utility::c_random() & 7];\r
+                       $B = bmodexp($grp, $exp, $mod);\r
+                       $C = bmodexp($y, $exp, $mod);\r
+               } else {\r
+                       $exp = mpi2b(substr($s, $l + 2));\r
+               }\r
+\r
+               $c = 0;\r
+               $lsk = strlen($session_key);\r
+               for($i = 0; $i < $lsk; $i++) $c += ord($session_key[$i]);\r
+               $c &= 0xffff;\r
+\r
+               $lm = ($l - 2) * 8 + 2;\r
+               $m = chr($lm / 256) . chr($lm % 256) .\r
+                       chr(2) . GPG_Utility::s_random($l - $lsk - 6, 1) . "\0" .\r
+                       chr(7) . $session_key .\r
+                       chr($c / 256) . chr($c & 0xff);\r
+\r
+               if($key_type) {\r
+                       $enc = b2mpi($B) . b2mpi(bmod(bmul(mpi2b($m), $C), $mod));\r
+                       return $this->gpg_header(0x84,strlen($enc) + 10) .\r
+                               chr(3) . $key_id . chr(16) . $enc;\r
+               } else {\r
+                       $enc = b2mpi(bmodexp(mpi2b($m), $exp, $mod));\r
+                       return $this->gpg_header(0x84, strlen($enc) + 10) .\r
+                               chr(3) . $key_id . chr(1) . $enc;\r
+               }\r
+       }\r
+\r
+       private function gpg_literal($text)\r
+       {\r
+               if (strpos($text, "\r\n") === false)\r
+                       $text = str_replace("\n", "\r\n", $text);\r
+\r
+               return\r
+               $this->gpg_header(0xac, strlen($text) + 10) . "t" .\r
+                       chr(4) . "file\0\0\0\0" . $text;\r
+       }\r
+\r
+       private function gpg_data($key, $text)\r
+       {\r
+               $enc = $this->gpg_encrypt($key, $this->gpg_literal($text));\r
+               return $this->gpg_header(0xa4, strlen($enc)) . $enc;\r
+       }\r
+\r
+       /**\r
+        * GPG Encypts a message to the provided public key\r
+        *\r
+        * @param GPG_Public_Key $pk\r
+        * @param string $plaintext\r
+        * @return string encrypted text\r
+        */\r
+       function encrypt($pk, $plaintext)\r
+       {\r
+               // normalize the public key\r
+               $key_id = $pk->GetKeyId();\r
+               $key_type = $pk->GetKeyType();\r
+               $public_key = $pk->GetPublicKey();\r
+\r
+               $session_key = GPG_Utility::s_random($this->width, 0);\r
+               $key_id = GPG_Utility::hex2bin($key_id);\r
+               $cp = $this->gpg_session($key_id, $key_type, $session_key, $public_key) .\r
+                       $this->gpg_data($session_key, $plaintext);\r
+\r
+               $code = base64_encode($cp);\r
+               $code = wordwrap($code, 60, "\n", 1);\r
+\r
+               return\r
+                       "-----BEGIN PGP MESSAGE-----\nVersion: VerySimple PHP-GPG v".$this->version."\n\n" .\r
+                       $code . "\n=" . base64_encode(GPG_Utility::crc24($cp)) .\r
+                       "\n-----END PGP MESSAGE-----\n";\r
+       }\r
+}\r
+\r
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG/AES.php b/securemail/php-gpg/libs/GPG/AES.php
new file mode 100644 (file)
index 0000000..25e4e4a
--- /dev/null
@@ -0,0 +1,63 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** require supporting files */\r
+require_once("Cipher.php");\r
+\r
+/**\r
+ * @package    php-gpg::GPG\r
+ */\r
+class GPG_AES\r
+{\r
+       static function encrypt($block, $ctx)\r
+       {\r
+               $RCON = GPG_Cipher::$RCON;\r
+               $S = GPG_Cipher::$S;\r
+               \r
+               $T1 = GPG_Cipher::$T1;\r
+               $T2 = GPG_Cipher::$T2;\r
+               $T3 = GPG_Cipher::$T3;\r
+               $T4 = GPG_Cipher::$T4;\r
+               \r
+               $r = 0;\r
+               $t0 = 0;\r
+               $t1 = 0;\r
+               $t2 = 0;\r
+               $t3 = 0;\r
+               \r
+               $b = GPG_Utility::pack_octets($block);\r
+               $rounds = $ctx->rounds;\r
+               $b0 = $b[0];\r
+               $b1 = $b[1];\r
+               $b2 = $b[2];\r
+               $b3 = $b[3];\r
+               \r
+               for($r = 0; $r < $rounds - 1; $r++) {\r
+                       $t0 = $b0 ^ $ctx->rk[$r][0];\r
+                       $t1 = $b1 ^ $ctx->rk[$r][1];\r
+                       $t2 = $b2 ^ $ctx->rk[$r][2];\r
+                       $t3 = $b3 ^ $ctx->rk[$r][3];\r
+                       \r
+                       $b0 = $T1[$t0 & 255] ^ $T2[($t1 >> 8) & 255] ^ $T3[($t2 >> 16) & 255] ^ $T4[GPG_Utility::zshift($t3, 24)];\r
+                       $b1 = $T1[$t1 & 255] ^ $T2[($t2 >> 8) & 255] ^ $T3[($t3 >> 16) & 255] ^ $T4[GPG_Utility::zshift($t0, 24)];\r
+                       $b2 = $T1[$t2 & 255] ^ $T2[($t3 >> 8) & 255] ^ $T3[($t0 >> 16) & 255] ^ $T4[GPG_Utility::zshift($t1, 24)];\r
+                       $b3 = $T1[$t3 & 255] ^ $T2[($t0 >> 8) & 255] ^ $T3[($t1 >> 16) & 255] ^ $T4[GPG_Utility::zshift($t2, 24)];\r
+               }\r
+               \r
+               $r = $rounds - 1;\r
+               \r
+               $t0 = $b0 ^ $ctx->rk[$r][0];\r
+               $t1 = $b1 ^ $ctx->rk[$r][1];\r
+               $t2 = $b2 ^ $ctx->rk[$r][2];\r
+               $t3 = $b3 ^ $ctx->rk[$r][3];\r
+               \r
+               $b[0] = GPG_Cipher::F1($t0, $t1, $t2, $t3) ^ $ctx->rk[$rounds][0];\r
+               $b[1] = GPG_Cipher::F1($t1, $t2, $t3, $t0) ^ $ctx->rk[$rounds][1];\r
+               $b[2] = GPG_Cipher::F1($t2, $t3, $t0, $t1) ^ $ctx->rk[$rounds][2];\r
+               $b[3] = GPG_Cipher::F1($t3, $t0, $t1, $t2) ^ $ctx->rk[$rounds][3];\r
+               \r
+               return GPG_Utility::unpack_octets($b);\r
+       }\r
+}\r
+\r
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG/Cipher.php b/securemail/php-gpg/libs/GPG/Cipher.php
new file mode 100644 (file)
index 0000000..5940e14
--- /dev/null
@@ -0,0 +1,335 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** require supporting files */\r
+require_once("Utility.php");\r
+\r
+/**\r
+ * @package    php-gpg::GPG\r
+ */\r
+class GPG_Cipher\r
+{\r
+       /*\r
+       global $RCON;\r
+       global $S;\r
+       global $T1;\r
+       global $T2;\r
+       global $T3;\r
+       global $T4;\r
+\r
+       global $maxkc;\r
+       global $maxrk;\r
+       */\r
+       \r
+       static $maxkc = 8;\r
+       static $maxrk = 14;\r
+\r
+       static $RCON = array( \r
+                       0x01, 0x02, 0x04, 0x08, 0x10, 0x20,\r
+                       0x40, 0x80, 0x1b, 0x36, 0x6c, 0xd8, \r
+                       0xab, 0x4d, 0x9a, 0x2f, 0x5e, 0xbc,\r
+                       0x63, 0xc6, 0x97, 0x35, 0x6a, 0xd4, \r
+                       0xb3, 0x7d, 0xfa, 0xef, 0xc5, 0x91\r
+                       );\r
+\r
+       static $S = array(\r
+                       99, 124, 119, 123, 242, 107, 111, 197,  48,   1, 103,  43, 254, 215, 171, \r
+                       118, 202, 130, 201, 125, 250,  89,  71, 240, 173, 212, 162, 175, 156, 164, \r
+                       114, 192, 183, 253, 147,  38,  54,  63, 247, 204,  52, 165, 229, 241, 113, \r
+                       216,  49,  21,   4, 199,  35, 195,  24, 150,   5, 154,   7,  18, 128, 226, \r
+                       235,  39, 178, 117,   9, 131,  44,  26,  27, 110,  90, 160,  82,  59, 214, \r
+                       179,  41, 227,  47, 132,  83, 209,   0, 237,  32, 252, 177,  91, 106, 203, \r
+                       190,  57,  74,  76,  88, 207, 208, 239, 170, 251,  67,  77,  51, 133,  69, \r
+                       249,   2, 127,  80,  60, 159, 168,  81, 163,  64, 143, 146, 157,  56, 245, \r
+                       188, 182, 218,  33,  16, 255, 243, 210, 205,  12,  19, 236,  95, 151,  68,  \r
+                       23,  196, 167, 126,  61, 100,  93,  25, 115,  96, 129,  79, 220,  34,  42, \r
+                       144, 136,  70, 238, 184,  20, 222,  94,  11, 219, 224,  50,  58,  10,  73,\r
+                       6,  36,  92, 194, 211, 172,  98, 145, 149, 228, 121, 231, 200,  55, 109, \r
+                       141, 213,  78, 169, 108,  86, 244, 234, 101, 122, 174,   8, 186, 120,  37,  \r
+                       46,  28, 166, 180, 198, 232, 221, 116,  31,  75, 189, 139, 138, 112,  62, \r
+                       181, 102,  72,   3, 246,  14,  97,  53,  87, 185, 134, 193,  29, 158, 225,\r
+                       248, 152,  17, 105, 217, 142, 148, 155,  30, 135, 233, 206,  85,  40, 223,\r
+                       140, 161, 137,  13, 191, 230,  66, 104,  65, 153,  45,  15, 176,  84, 187,  \r
+                       22\r
+                       );\r
+\r
+       static $T1 = array(\r
+                       0xa56363c6, 0x847c7cf8, 0x997777ee, 0x8d7b7bf6,\r
+                       0x0df2f2ff, 0xbd6b6bd6, 0xb16f6fde, 0x54c5c591,\r
+                       0x50303060, 0x03010102, 0xa96767ce, 0x7d2b2b56,\r
+                       0x19fefee7, 0x62d7d7b5, 0xe6abab4d, 0x9a7676ec,\r
+                       0x45caca8f, 0x9d82821f, 0x40c9c989, 0x877d7dfa,\r
+                       0x15fafaef, 0xeb5959b2, 0xc947478e, 0x0bf0f0fb,\r
+                       0xecadad41, 0x67d4d4b3, 0xfda2a25f, 0xeaafaf45,\r
+                       0xbf9c9c23, 0xf7a4a453, 0x967272e4, 0x5bc0c09b,\r
+                       0xc2b7b775, 0x1cfdfde1, 0xae93933d, 0x6a26264c,\r
+                       0x5a36366c, 0x413f3f7e, 0x02f7f7f5, 0x4fcccc83,\r
+                       0x5c343468, 0xf4a5a551, 0x34e5e5d1, 0x08f1f1f9,\r
+                       0x937171e2, 0x73d8d8ab, 0x53313162, 0x3f15152a,\r
+                       0x0c040408, 0x52c7c795, 0x65232346, 0x5ec3c39d,\r
+                       0x28181830, 0xa1969637, 0x0f05050a, 0xb59a9a2f,\r
+                       0x0907070e, 0x36121224, 0x9b80801b, 0x3de2e2df,\r
+                       0x26ebebcd, 0x6927274e, 0xcdb2b27f, 0x9f7575ea,\r
+                       0x1b090912, 0x9e83831d, 0x742c2c58, 0x2e1a1a34,\r
+                       0x2d1b1b36, 0xb26e6edc, 0xee5a5ab4, 0xfba0a05b,\r
+                       0xf65252a4, 0x4d3b3b76, 0x61d6d6b7, 0xceb3b37d,\r
+                       0x7b292952, 0x3ee3e3dd, 0x712f2f5e, 0x97848413,\r
+                       0xf55353a6, 0x68d1d1b9, 0x00000000, 0x2cededc1,\r
+                       0x60202040, 0x1ffcfce3, 0xc8b1b179, 0xed5b5bb6,\r
+                       0xbe6a6ad4, 0x46cbcb8d, 0xd9bebe67, 0x4b393972,\r
+                       0xde4a4a94, 0xd44c4c98, 0xe85858b0, 0x4acfcf85,\r
+                       0x6bd0d0bb, 0x2aefefc5, 0xe5aaaa4f, 0x16fbfbed,\r
+                       0xc5434386, 0xd74d4d9a, 0x55333366, 0x94858511,\r
+                       0xcf45458a, 0x10f9f9e9, 0x06020204, 0x817f7ffe,\r
+                       0xf05050a0, 0x443c3c78, 0xba9f9f25, 0xe3a8a84b,\r
+                       0xf35151a2, 0xfea3a35d, 0xc0404080, 0x8a8f8f05,\r
+                       0xad92923f, 0xbc9d9d21, 0x48383870, 0x04f5f5f1,\r
+                       0xdfbcbc63, 0xc1b6b677, 0x75dadaaf, 0x63212142,\r
+                       0x30101020, 0x1affffe5, 0x0ef3f3fd, 0x6dd2d2bf,\r
+                       0x4ccdcd81, 0x140c0c18, 0x35131326, 0x2fececc3,\r
+                       0xe15f5fbe, 0xa2979735, 0xcc444488, 0x3917172e,\r
+                       0x57c4c493, 0xf2a7a755, 0x827e7efc, 0x473d3d7a,\r
+                       0xac6464c8, 0xe75d5dba, 0x2b191932, 0x957373e6,\r
+                       0xa06060c0, 0x98818119, 0xd14f4f9e, 0x7fdcdca3,\r
+                       0x66222244, 0x7e2a2a54, 0xab90903b, 0x8388880b,\r
+                       0xca46468c, 0x29eeeec7, 0xd3b8b86b, 0x3c141428,\r
+                       0x79dedea7, 0xe25e5ebc, 0x1d0b0b16, 0x76dbdbad,\r
+                       0x3be0e0db, 0x56323264, 0x4e3a3a74, 0x1e0a0a14,\r
+                       0xdb494992, 0x0a06060c, 0x6c242448, 0xe45c5cb8,\r
+                       0x5dc2c29f, 0x6ed3d3bd, 0xefacac43, 0xa66262c4,\r
+                       0xa8919139, 0xa4959531, 0x37e4e4d3, 0x8b7979f2,\r
+                       0x32e7e7d5, 0x43c8c88b, 0x5937376e, 0xb76d6dda,\r
+                       0x8c8d8d01, 0x64d5d5b1, 0xd24e4e9c, 0xe0a9a949,\r
+                       0xb46c6cd8, 0xfa5656ac, 0x07f4f4f3, 0x25eaeacf,\r
+                       0xaf6565ca, 0x8e7a7af4, 0xe9aeae47, 0x18080810,\r
+                       0xd5baba6f, 0x887878f0, 0x6f25254a, 0x722e2e5c,\r
+                       0x241c1c38, 0xf1a6a657, 0xc7b4b473, 0x51c6c697,\r
+                       0x23e8e8cb, 0x7cdddda1, 0x9c7474e8, 0x211f1f3e,\r
+                       0xdd4b4b96, 0xdcbdbd61, 0x868b8b0d, 0x858a8a0f,\r
+                       0x907070e0, 0x423e3e7c, 0xc4b5b571, 0xaa6666cc,\r
+                       0xd8484890, 0x05030306, 0x01f6f6f7, 0x120e0e1c,\r
+                       0xa36161c2, 0x5f35356a, 0xf95757ae, 0xd0b9b969,\r
+                       0x91868617, 0x58c1c199, 0x271d1d3a, 0xb99e9e27,\r
+                       0x38e1e1d9, 0x13f8f8eb, 0xb398982b, 0x33111122,\r
+                       0xbb6969d2, 0x70d9d9a9, 0x898e8e07, 0xa7949433,\r
+                       0xb69b9b2d, 0x221e1e3c, 0x92878715, 0x20e9e9c9,\r
+                       0x49cece87, 0xff5555aa, 0x78282850, 0x7adfdfa5,\r
+                       0x8f8c8c03, 0xf8a1a159, 0x80898909, 0x170d0d1a,\r
+                       0xdabfbf65, 0x31e6e6d7, 0xc6424284, 0xb86868d0,\r
+                       0xc3414182, 0xb0999929, 0x772d2d5a, 0x110f0f1e,\r
+                       0xcbb0b07b, 0xfc5454a8, 0xd6bbbb6d, 0x3a16162c\r
+                       );\r
+\r
+       static $T2 = array(\r
+                       0x6363c6a5, 0x7c7cf884, 0x7777ee99, 0x7b7bf68d,\r
+                       0xf2f2ff0d, 0x6b6bd6bd, 0x6f6fdeb1, 0xc5c59154,\r
+                       0x30306050, 0x01010203, 0x6767cea9, 0x2b2b567d,\r
+                       0xfefee719, 0xd7d7b562, 0xabab4de6, 0x7676ec9a,\r
+                       0xcaca8f45, 0x82821f9d, 0xc9c98940, 0x7d7dfa87,\r
+                       0xfafaef15, 0x5959b2eb, 0x47478ec9, 0xf0f0fb0b,\r
+                       0xadad41ec, 0xd4d4b367, 0xa2a25ffd, 0xafaf45ea,\r
+                       0x9c9c23bf, 0xa4a453f7, 0x7272e496, 0xc0c09b5b,\r
+                       0xb7b775c2, 0xfdfde11c, 0x93933dae, 0x26264c6a,\r
+                       0x36366c5a, 0x3f3f7e41, 0xf7f7f502, 0xcccc834f,\r
+                       0x3434685c, 0xa5a551f4, 0xe5e5d134, 0xf1f1f908,\r
+                       0x7171e293, 0xd8d8ab73, 0x31316253, 0x15152a3f,\r
+                       0x0404080c, 0xc7c79552, 0x23234665, 0xc3c39d5e,\r
+                       0x18183028, 0x969637a1, 0x05050a0f, 0x9a9a2fb5,\r
+                       0x07070e09, 0x12122436, 0x80801b9b, 0xe2e2df3d,\r
+                       0xebebcd26, 0x27274e69, 0xb2b27fcd, 0x7575ea9f,\r
+                       0x0909121b, 0x83831d9e, 0x2c2c5874, 0x1a1a342e,\r
+                       0x1b1b362d, 0x6e6edcb2, 0x5a5ab4ee, 0xa0a05bfb,\r
+                       0x5252a4f6, 0x3b3b764d, 0xd6d6b761, 0xb3b37dce,\r
+                       0x2929527b, 0xe3e3dd3e, 0x2f2f5e71, 0x84841397,\r
+                       0x5353a6f5, 0xd1d1b968, 0x00000000, 0xededc12c,\r
+                       0x20204060, 0xfcfce31f, 0xb1b179c8, 0x5b5bb6ed,\r
+                       0x6a6ad4be, 0xcbcb8d46, 0xbebe67d9, 0x3939724b,\r
+                       0x4a4a94de, 0x4c4c98d4, 0x5858b0e8, 0xcfcf854a,\r
+                       0xd0d0bb6b, 0xefefc52a, 0xaaaa4fe5, 0xfbfbed16,\r
+                       0x434386c5, 0x4d4d9ad7, 0x33336655, 0x85851194,\r
+                       0x45458acf, 0xf9f9e910, 0x02020406, 0x7f7ffe81,\r
+                       0x5050a0f0, 0x3c3c7844, 0x9f9f25ba, 0xa8a84be3,\r
+                       0x5151a2f3, 0xa3a35dfe, 0x404080c0, 0x8f8f058a,\r
+                       0x92923fad, 0x9d9d21bc, 0x38387048, 0xf5f5f104,\r
+                       0xbcbc63df, 0xb6b677c1, 0xdadaaf75, 0x21214263,\r
+                       0x10102030, 0xffffe51a, 0xf3f3fd0e, 0xd2d2bf6d,\r
+                       0xcdcd814c, 0x0c0c1814, 0x13132635, 0xececc32f,\r
+                       0x5f5fbee1, 0x979735a2, 0x444488cc, 0x17172e39,\r
+                       0xc4c49357, 0xa7a755f2, 0x7e7efc82, 0x3d3d7a47,\r
+                       0x6464c8ac, 0x5d5dbae7, 0x1919322b, 0x7373e695,\r
+                       0x6060c0a0, 0x81811998, 0x4f4f9ed1, 0xdcdca37f,\r
+                       0x22224466, 0x2a2a547e, 0x90903bab, 0x88880b83,\r
+                       0x46468cca, 0xeeeec729, 0xb8b86bd3, 0x1414283c,\r
+                       0xdedea779, 0x5e5ebce2, 0x0b0b161d, 0xdbdbad76,\r
+                       0xe0e0db3b, 0x32326456, 0x3a3a744e, 0x0a0a141e,\r
+                       0x494992db, 0x06060c0a, 0x2424486c, 0x5c5cb8e4,\r
+                       0xc2c29f5d, 0xd3d3bd6e, 0xacac43ef, 0x6262c4a6,\r
+                       0x919139a8, 0x959531a4, 0xe4e4d337, 0x7979f28b,\r
+                       0xe7e7d532, 0xc8c88b43, 0x37376e59, 0x6d6ddab7,\r
+                       0x8d8d018c, 0xd5d5b164, 0x4e4e9cd2, 0xa9a949e0,\r
+                       0x6c6cd8b4, 0x5656acfa, 0xf4f4f307, 0xeaeacf25,\r
+                       0x6565caaf, 0x7a7af48e, 0xaeae47e9, 0x08081018,\r
+                       0xbaba6fd5, 0x7878f088, 0x25254a6f, 0x2e2e5c72,\r
+                       0x1c1c3824, 0xa6a657f1, 0xb4b473c7, 0xc6c69751,\r
+                       0xe8e8cb23, 0xdddda17c, 0x7474e89c, 0x1f1f3e21,\r
+                       0x4b4b96dd, 0xbdbd61dc, 0x8b8b0d86, 0x8a8a0f85,\r
+                       0x7070e090, 0x3e3e7c42, 0xb5b571c4, 0x6666ccaa,\r
+                       0x484890d8, 0x03030605, 0xf6f6f701, 0x0e0e1c12,\r
+                       0x6161c2a3, 0x35356a5f, 0x5757aef9, 0xb9b969d0,\r
+                       0x86861791, 0xc1c19958, 0x1d1d3a27, 0x9e9e27b9,\r
+                       0xe1e1d938, 0xf8f8eb13, 0x98982bb3, 0x11112233,\r
+                       0x6969d2bb, 0xd9d9a970, 0x8e8e0789, 0x949433a7,\r
+                       0x9b9b2db6, 0x1e1e3c22, 0x87871592, 0xe9e9c920,\r
+                       0xcece8749, 0x5555aaff, 0x28285078, 0xdfdfa57a,\r
+                       0x8c8c038f, 0xa1a159f8, 0x89890980, 0x0d0d1a17,\r
+                       0xbfbf65da, 0xe6e6d731, 0x424284c6, 0x6868d0b8,\r
+                       0x414182c3, 0x999929b0, 0x2d2d5a77, 0x0f0f1e11,\r
+                       0xb0b07bcb, 0x5454a8fc, 0xbbbb6dd6, 0x16162c3a\r
+                       );\r
+\r
+       static $T3 = array(\r
+                       0x63c6a563, 0x7cf8847c, 0x77ee9977, 0x7bf68d7b,\r
+                       0xf2ff0df2, 0x6bd6bd6b, 0x6fdeb16f, 0xc59154c5,\r
+                       0x30605030, 0x01020301, 0x67cea967, 0x2b567d2b,\r
+                       0xfee719fe, 0xd7b562d7, 0xab4de6ab, 0x76ec9a76,\r
+                       0xca8f45ca, 0x821f9d82, 0xc98940c9, 0x7dfa877d,\r
+                       0xfaef15fa, 0x59b2eb59, 0x478ec947, 0xf0fb0bf0,\r
+                       0xad41ecad, 0xd4b367d4, 0xa25ffda2, 0xaf45eaaf,\r
+                       0x9c23bf9c, 0xa453f7a4, 0x72e49672, 0xc09b5bc0,\r
+                       0xb775c2b7, 0xfde11cfd, 0x933dae93, 0x264c6a26,\r
+                       0x366c5a36, 0x3f7e413f, 0xf7f502f7, 0xcc834fcc,\r
+                       0x34685c34, 0xa551f4a5, 0xe5d134e5, 0xf1f908f1,\r
+                       0x71e29371, 0xd8ab73d8, 0x31625331, 0x152a3f15,\r
+                       0x04080c04, 0xc79552c7, 0x23466523, 0xc39d5ec3,\r
+                       0x18302818, 0x9637a196, 0x050a0f05, 0x9a2fb59a,\r
+                       0x070e0907, 0x12243612, 0x801b9b80, 0xe2df3de2,\r
+                       0xebcd26eb, 0x274e6927, 0xb27fcdb2, 0x75ea9f75,\r
+                       0x09121b09, 0x831d9e83, 0x2c58742c, 0x1a342e1a,\r
+                       0x1b362d1b, 0x6edcb26e, 0x5ab4ee5a, 0xa05bfba0,\r
+                       0x52a4f652, 0x3b764d3b, 0xd6b761d6, 0xb37dceb3,\r
+                       0x29527b29, 0xe3dd3ee3, 0x2f5e712f, 0x84139784,\r
+                       0x53a6f553, 0xd1b968d1, 0x00000000, 0xedc12ced,\r
+                       0x20406020, 0xfce31ffc, 0xb179c8b1, 0x5bb6ed5b,\r
+                       0x6ad4be6a, 0xcb8d46cb, 0xbe67d9be, 0x39724b39,\r
+                       0x4a94de4a, 0x4c98d44c, 0x58b0e858, 0xcf854acf,\r
+                       0xd0bb6bd0, 0xefc52aef, 0xaa4fe5aa, 0xfbed16fb,\r
+                       0x4386c543, 0x4d9ad74d, 0x33665533, 0x85119485,\r
+                       0x458acf45, 0xf9e910f9, 0x02040602, 0x7ffe817f,\r
+                       0x50a0f050, 0x3c78443c, 0x9f25ba9f, 0xa84be3a8,\r
+                       0x51a2f351, 0xa35dfea3, 0x4080c040, 0x8f058a8f,\r
+                       0x923fad92, 0x9d21bc9d, 0x38704838, 0xf5f104f5,\r
+                       0xbc63dfbc, 0xb677c1b6, 0xdaaf75da, 0x21426321,\r
+                       0x10203010, 0xffe51aff, 0xf3fd0ef3, 0xd2bf6dd2,\r
+                       0xcd814ccd, 0x0c18140c, 0x13263513, 0xecc32fec,\r
+                       0x5fbee15f, 0x9735a297, 0x4488cc44, 0x172e3917,\r
+                       0xc49357c4, 0xa755f2a7, 0x7efc827e, 0x3d7a473d,\r
+                       0x64c8ac64, 0x5dbae75d, 0x19322b19, 0x73e69573,\r
+                       0x60c0a060, 0x81199881, 0x4f9ed14f, 0xdca37fdc,\r
+                       0x22446622, 0x2a547e2a, 0x903bab90, 0x880b8388,\r
+                       0x468cca46, 0xeec729ee, 0xb86bd3b8, 0x14283c14,\r
+                       0xdea779de, 0x5ebce25e, 0x0b161d0b, 0xdbad76db,\r
+                       0xe0db3be0, 0x32645632, 0x3a744e3a, 0x0a141e0a,\r
+                       0x4992db49, 0x060c0a06, 0x24486c24, 0x5cb8e45c,\r
+                       0xc29f5dc2, 0xd3bd6ed3, 0xac43efac, 0x62c4a662,\r
+                       0x9139a891, 0x9531a495, 0xe4d337e4, 0x79f28b79,\r
+                       0xe7d532e7, 0xc88b43c8, 0x376e5937, 0x6ddab76d,\r
+                       0x8d018c8d, 0xd5b164d5, 0x4e9cd24e, 0xa949e0a9,\r
+                       0x6cd8b46c, 0x56acfa56, 0xf4f307f4, 0xeacf25ea,\r
+                       0x65caaf65, 0x7af48e7a, 0xae47e9ae, 0x08101808,\r
+                       0xba6fd5ba, 0x78f08878, 0x254a6f25, 0x2e5c722e,\r
+                       0x1c38241c, 0xa657f1a6, 0xb473c7b4, 0xc69751c6,\r
+                       0xe8cb23e8, 0xdda17cdd, 0x74e89c74, 0x1f3e211f,\r
+                       0x4b96dd4b, 0xbd61dcbd, 0x8b0d868b, 0x8a0f858a,\r
+                       0x70e09070, 0x3e7c423e, 0xb571c4b5, 0x66ccaa66,\r
+                       0x4890d848, 0x03060503, 0xf6f701f6, 0x0e1c120e,\r
+                       0x61c2a361, 0x356a5f35, 0x57aef957, 0xb969d0b9,\r
+                       0x86179186, 0xc19958c1, 0x1d3a271d, 0x9e27b99e,\r
+                       0xe1d938e1, 0xf8eb13f8, 0x982bb398, 0x11223311,\r
+                       0x69d2bb69, 0xd9a970d9, 0x8e07898e, 0x9433a794,\r
+                       0x9b2db69b, 0x1e3c221e, 0x87159287, 0xe9c920e9,\r
+                       0xce8749ce, 0x55aaff55, 0x28507828, 0xdfa57adf,\r
+                       0x8c038f8c, 0xa159f8a1, 0x89098089, 0x0d1a170d,\r
+                       0xbf65dabf, 0xe6d731e6, 0x4284c642, 0x68d0b868,\r
+                       0x4182c341, 0x9929b099, 0x2d5a772d, 0x0f1e110f,\r
+                       0xb07bcbb0, 0x54a8fc54, 0xbb6dd6bb, 0x162c3a16\r
+                       );\r
+\r
+       static $T4 = array(\r
+                       0xc6a56363, 0xf8847c7c, 0xee997777, 0xf68d7b7b,\r
+                       0xff0df2f2, 0xd6bd6b6b, 0xdeb16f6f, 0x9154c5c5,\r
+                       0x60503030, 0x02030101, 0xcea96767, 0x567d2b2b,\r
+                       0xe719fefe, 0xb562d7d7, 0x4de6abab, 0xec9a7676,\r
+                       0x8f45caca, 0x1f9d8282, 0x8940c9c9, 0xfa877d7d,\r
+                       0xef15fafa, 0xb2eb5959, 0x8ec94747, 0xfb0bf0f0,\r
+                       0x41ecadad, 0xb367d4d4, 0x5ffda2a2, 0x45eaafaf,\r
+                       0x23bf9c9c, 0x53f7a4a4, 0xe4967272, 0x9b5bc0c0,\r
+                       0x75c2b7b7, 0xe11cfdfd, 0x3dae9393, 0x4c6a2626,\r
+                       0x6c5a3636, 0x7e413f3f, 0xf502f7f7, 0x834fcccc,\r
+                       0x685c3434, 0x51f4a5a5, 0xd134e5e5, 0xf908f1f1,\r
+                       0xe2937171, 0xab73d8d8, 0x62533131, 0x2a3f1515,\r
+                       0x080c0404, 0x9552c7c7, 0x46652323, 0x9d5ec3c3,\r
+                       0x30281818, 0x37a19696, 0x0a0f0505, 0x2fb59a9a,\r
+                       0x0e090707, 0x24361212, 0x1b9b8080, 0xdf3de2e2,\r
+                       0xcd26ebeb, 0x4e692727, 0x7fcdb2b2, 0xea9f7575,\r
+                       0x121b0909, 0x1d9e8383, 0x58742c2c, 0x342e1a1a,\r
+                       0x362d1b1b, 0xdcb26e6e, 0xb4ee5a5a, 0x5bfba0a0,\r
+                       0xa4f65252, 0x764d3b3b, 0xb761d6d6, 0x7dceb3b3,\r
+                       0x527b2929, 0xdd3ee3e3, 0x5e712f2f, 0x13978484,\r
+                       0xa6f55353, 0xb968d1d1, 0x00000000, 0xc12ceded,\r
+                       0x40602020, 0xe31ffcfc, 0x79c8b1b1, 0xb6ed5b5b,\r
+                       0xd4be6a6a, 0x8d46cbcb, 0x67d9bebe, 0x724b3939,\r
+                       0x94de4a4a, 0x98d44c4c, 0xb0e85858, 0x854acfcf,\r
+                       0xbb6bd0d0, 0xc52aefef, 0x4fe5aaaa, 0xed16fbfb,\r
+                       0x86c54343, 0x9ad74d4d, 0x66553333, 0x11948585,\r
+                       0x8acf4545, 0xe910f9f9, 0x04060202, 0xfe817f7f,\r
+                       0xa0f05050, 0x78443c3c, 0x25ba9f9f, 0x4be3a8a8,\r
+                       0xa2f35151, 0x5dfea3a3, 0x80c04040, 0x058a8f8f,\r
+                       0x3fad9292, 0x21bc9d9d, 0x70483838, 0xf104f5f5,\r
+                       0x63dfbcbc, 0x77c1b6b6, 0xaf75dada, 0x42632121,\r
+                       0x20301010, 0xe51affff, 0xfd0ef3f3, 0xbf6dd2d2,\r
+                       0x814ccdcd, 0x18140c0c, 0x26351313, 0xc32fecec,\r
+                       0xbee15f5f, 0x35a29797, 0x88cc4444, 0x2e391717,\r
+                       0x9357c4c4, 0x55f2a7a7, 0xfc827e7e, 0x7a473d3d,\r
+                       0xc8ac6464, 0xbae75d5d, 0x322b1919, 0xe6957373,\r
+                       0xc0a06060, 0x19988181, 0x9ed14f4f, 0xa37fdcdc,\r
+                       0x44662222, 0x547e2a2a, 0x3bab9090, 0x0b838888,\r
+                       0x8cca4646, 0xc729eeee, 0x6bd3b8b8, 0x283c1414,\r
+                       0xa779dede, 0xbce25e5e, 0x161d0b0b, 0xad76dbdb,\r
+                       0xdb3be0e0, 0x64563232, 0x744e3a3a, 0x141e0a0a,\r
+                       0x92db4949, 0x0c0a0606, 0x486c2424, 0xb8e45c5c,\r
+                       0x9f5dc2c2, 0xbd6ed3d3, 0x43efacac, 0xc4a66262,\r
+                       0x39a89191, 0x31a49595, 0xd337e4e4, 0xf28b7979,\r
+                       0xd532e7e7, 0x8b43c8c8, 0x6e593737, 0xdab76d6d,\r
+                       0x018c8d8d, 0xb164d5d5, 0x9cd24e4e, 0x49e0a9a9,\r
+                       0xd8b46c6c, 0xacfa5656, 0xf307f4f4, 0xcf25eaea,\r
+                       0xcaaf6565, 0xf48e7a7a, 0x47e9aeae, 0x10180808,\r
+                       0x6fd5baba, 0xf0887878, 0x4a6f2525, 0x5c722e2e,\r
+                       0x38241c1c, 0x57f1a6a6, 0x73c7b4b4, 0x9751c6c6,\r
+                       0xcb23e8e8, 0xa17cdddd, 0xe89c7474, 0x3e211f1f,\r
+                       0x96dd4b4b, 0x61dcbdbd, 0x0d868b8b, 0x0f858a8a,\r
+                       0xe0907070, 0x7c423e3e, 0x71c4b5b5, 0xccaa6666,\r
+                       0x90d84848, 0x06050303, 0xf701f6f6, 0x1c120e0e,\r
+                       0xc2a36161, 0x6a5f3535, 0xaef95757, 0x69d0b9b9,\r
+                       0x17918686, 0x9958c1c1, 0x3a271d1d, 0x27b99e9e,\r
+                       0xd938e1e1, 0xeb13f8f8, 0x2bb39898, 0x22331111,\r
+                       0xd2bb6969, 0xa970d9d9, 0x07898e8e, 0x33a79494,\r
+                       0x2db69b9b, 0x3c221e1e, 0x15928787, 0xc920e9e9,\r
+                       0x8749cece, 0xaaff5555, 0x50782828, 0xa57adfdf,\r
+                       0x038f8c8c, 0x59f8a1a1, 0x09808989, 0x1a170d0d,\r
+                       0x65dabfbf, 0xd731e6e6, 0x84c64242, 0xd0b86868,\r
+                       0x82c34141, 0x29b09999, 0x5a772d2d, 0x1e110f0f,\r
+                       0x7bcbb0b0, 0xa8fc5454, 0x6dd6bbbb, 0x2c3a1616\r
+                       );\r
+\r
+       static function F1($x0, $x1, $x2, $x3)\r
+       {\r
+               $T1 = GPG_Cipher::$T1;\r
+               \r
+               return\r
+               GPG_Utility::B1($T1[$x0 & 0xff]) | (GPG_Utility::B1($T1[($x1 >> 0x8) & 0xff]) << 0x8) |\r
+                       (GPG_Utility::B1($T1[($x2 >> 0x10) & 0xff]) << 0x10) | (GPG_Utility::B1($T1[GPG_Utility::zshift($x3, 0x18)]) << 0x18);\r
+       }\r
+\r
+\r
+}\r
+?>\r
diff --git a/securemail/php-gpg/libs/GPG/Expanded_Key.php b/securemail/php-gpg/libs/GPG/Expanded_Key.php
new file mode 100644 (file)
index 0000000..fdc69b2
--- /dev/null
@@ -0,0 +1,105 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** require supporting files */\r
+require_once("Cipher.php");\r
+\r
+/**\r
+ * @package    php-gpg::GPG\r
+ */\r
+class Expanded_Key {\r
+    var $rounds;\r
+    var $rk;\r
+\r
+       function Expanded_Key($key) {\r
+        $RCON = GPG_Cipher::$RCON;\r
+        $S = GPG_Cipher::$S;\r
+\r
+               $maxkc = GPG_Cipher::$maxkc;\r
+               $maxrk = GPG_Cipher::$maxrk;\r
+\r
+        $kc = 0;\r
+        $i = 0;\r
+        $j = 0;\r
+        $r = 0;\r
+        $t = 0;\r
+        $rounds = 0;\r
+        $keySched = array_fill(0, $maxrk + 1, 0);\r
+        $keylen = strlen($key);\r
+        $k = array_fill(0, $maxkc, 0);\r
+        $tk = array_fill(0, $maxkc, 0);\r
+        $rconpointer = 0;\r
+\r
+        if ($keylen == 16) {\r
+            $rounds = 10;\r
+            $kc = 4;\r
+        } else if ($keylen == 24) {\r
+            $rounds = 12;\r
+            $kc = 6;\r
+        } else if ($keylen == 32) {\r
+            $rounds = 14;\r
+            $kc = 8;\r
+        } else {\r
+            return;\r
+        }\r
+\r
+        for($i = 0; $i < $maxrk + 1; $i++) $keySched[$i] = array_fill(0, 4, 0);\r
+        for($i = 0, $j = 0; $j < $keylen; $j++, $i += 4) {\r
+                if ($i < $keylen) {\r
+                    $k[$j] = ord($key[$i]) | (ord($key[$i + 1]) << 0x8) |\r
+                        (ord($key[$i + 2]) << 0x10) | (ord($key[$i + 3]) << 0x18);\r
+                } else {\r
+                    $k[$j] = 0;\r
+                }\r
+        }\r
+        for($j = $kc - 1; $j >= 0; $j--) $tk[$j] = $k[$j];\r
+\r
+        $r = 0;\r
+        $t = 0;\r
+        for($j = 0; ($j < $kc) && ($r < $rounds + 1); ) {\r
+            for(; ($j < $kc) && ($t < 4); $j++, $t++) {\r
+                $keySched[$r][$t] = $tk[$j];\r
+            }\r
+            if($t == 4) {\r
+                $r++;\r
+                $t = 0;\r
+            }\r
+        }\r
+\r
+        while($r < $rounds + 1) {\r
+            $temp = $tk[$kc - 1];\r
+\r
+                       $tk[0] ^= $S[GPG_Utility::B1($temp)] | ($S[GPG_Utility::B2($temp)] << 0x8) |\r
+                               ($S[GPG_Utility::B3($temp)] << 0x10) | ($S[GPG_Utility::B0($temp)] << 0x18);\r
+            $tk[0] ^= $RCON[$rconpointer++];\r
+\r
+            if ($kc != 8) {\r
+                for($j = 1; $j < $kc; $j++) $tk[$j] ^= $tk[$j - 1];\r
+            } else {\r
+                for($j = 1; $j < $kc / 2; $j++) $tk[$j] ^= $tk[$j - 1];\r
\r
+                $temp = $tk[$kc / 2 - 1];\r
+                               $tk[$kc / 2] ^= $S[GPG_Utility::B0($temp)] | ($S[GPG_Utility::B1($temp)] << 0x8) |\r
+                                       ($S[GPG_Utility::B2($temp)] << 0x10) | ($S[GPG_Utility::B3($temp)] << 0x18);\r
+\r
+                for($j = $kc / 2 + 1; $j < $kc; $j++) $tk[$j] ^= $tk[$j - 1];\r
+            }\r
+\r
+            for($j = 0; ($j < $kc) && ($r < $rounds + 1); ) {\r
+                for(; ($j < $kc) && ($t < 4); $j++, $t++) {\r
+                    $keySched[$r][$t] = $tk[$j];\r
+                }\r
+                if($t == 4) {\r
+                    $r++;\r
+                    $t = 0;\r
+                }\r
+            }\r
+        }\r
+    \r
+        $this->rounds = $rounds;\r
+        $this->rk = $keySched;\r
+        return $this;\r
+    }\r
+}\r
+\r
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG/Public_Key.php b/securemail/php-gpg/libs/GPG/Public_Key.php
new file mode 100644 (file)
index 0000000..7b81307
--- /dev/null
@@ -0,0 +1,217 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** require supporting files */\r
+require_once("Expanded_Key.php");\r
+\r
+define("PK_TYPE_ELGAMAL", 1);\r
+define("PK_TYPE_RSA", 0);\r
+define("PK_TYPE_UNKNOWN", -1);\r
+\r
+/**\r
+ * Pure PHP implementation of PHP/GPG public key\r
+ *\r
+ * @package php-gpg::GPG\r
+ * @link http://www.verysimple.com/\r
+ * @copyright  1997-2011 VerySimple, Inc.\r
+ * @license    http://www.gnu.org/licenses/lgpl.html  LGPL\r
+ * @todo implement decryption\r
+ * @version 1.0\r
+ */\r
+class GPG_Public_Key {\r
+    var $version;\r
+       var $fp;\r
+       var $key_id;\r
+       var $user;\r
+       var $public_key;\r
+       var $type;\r
+       \r
+       function IsValid()\r
+       {\r
+               return $this->version != -1 && $this->GetKeyType() != PK_TYPE_UNKNOWN;\r
+       }\r
+       \r
+       function GetKeyType()\r
+       {\r
+               if (!strcmp($this->type, "ELGAMAL")) return PK_TYPE_ELGAMAL;\r
+               if (!strcmp($this->type, "RSA")) return PK_TYPE_RSA;\r
+               return PK_TYPE_UNKNOWN;\r
+       }\r
+\r
+       function GetFingerprint()\r
+       {\r
+               return strtoupper( trim(chunk_split($this->fp, 4, ' ')) );\r
+       }\r
+       \r
+       function GetKeyId()\r
+       {\r
+               return (strlen($this->key_id) == 16) ? strtoupper($this->key_id) : '0000000000000000';\r
+       }\r
+       \r
+       function GetPublicKey()\r
+       {\r
+               return str_replace("\n", "", $this->public_key);\r
+       }\r
+       \r
+       function GPG_Public_Key($asc) {\r
+               $found = 0;\r
+               \r
+               // normalize line breaks\r
+               $asc = str_replace("\r\n", "\n", $asc);\r
+               \r
+               if (strpos($asc, "-----BEGIN PGP PUBLIC KEY BLOCK-----\n") === false)\r
+                       throw new Exception("Missing header block in Public Key");\r
+\r
+               if (strpos($asc, "\n\n") === false)\r
+                       throw new Exception("Missing body delimiter in Public Key");\r
+               \r
+               if (strpos($asc, "\n-----END PGP PUBLIC KEY BLOCK-----") === false)\r
+                       throw new Exception("Missing footer block in Public Key");\r
+               \r
+               // get rid of everything except the base64 encoded key\r
+               $headerbody = explode("\n\n", str_replace("\n-----END PGP PUBLIC KEY BLOCK-----", "", $asc), 2);\r
+               $asc = trim($headerbody[1]);\r
+               \r
+               \r
+               $len = 0;\r
+               $s =  base64_decode($asc);\r
+               $sa = str_split($s);\r
+               \r
+               for($i = 0; $i < strlen($s);) {\r
+                       $tag = ord($sa[$i++]);\r
+                       \r
+                       // echo 'TAG=' . $tag . '/';\r
+                       \r
+                       if(($tag & 128) == 0) break;\r
+                       \r
+                       if($tag & 64) {\r
+                               $tag &= 63;\r
+                               $len = ord($sa[$i++]);\r
+                               if ($len > 191 && $len < 224) $len = (($len - 192) << 8) + ord($sa[$i++]);\r
+                               else if ($len == 255) $len = (ord($sa[$i++]) << 24) + (ord($sa[$i++]) << 16) + (ord($sa[$i++]) << 8) + ord($sa[$i++]);\r
+                                       else if ($len > 223 && len < 255) $len = (1 << ($len & 0x1f));\r
+                       } else {\r
+                               $len = $tag & 3;\r
+                               $tag = ($tag >> 2) & 15;\r
+                               if ($len == 0) $len = ord($sa[$i++]);\r
+                               else if($len == 1) $len = (ord($sa[$i++]) << 8) + ord($sa[$i++]);\r
+                                       else if($len == 2) $len = (ord($sa[$i++]) << 24) + (ord($sa[$i++]) << 16) + (ord($sa[$i++]) << 8) + ord($sa[$i++]);\r
+                                               else $len = strlen($s) - 1;\r
+                       }\r
+                       \r
+                       // echo $tag . ' ';\r
+                       \r
+                       if ($tag == 6 || $tag == 14) {\r
+                               $k = $i;\r
+                               $version = ord($sa[$i++]);\r
+                               $found = 1;\r
+                               $this->version = $version;\r
+                               \r
+                               $time = (ord($sa[$i++]) << 24) + (ord($sa[$i++]) << 16) + (ord($sa[$i++]) << 8) + ord($sa[$i++]);\r
+                               \r
+                               if($version == 2 || $version == 3) $valid = ord($sa[$i++]) << 8 + ord($sa[$i++]);\r
+                               \r
+                               $algo = ord($sa[$i++]);\r
+                               \r
+                               if($algo == 1 || $algo == 2) {\r
+                                       $m = $i;\r
+                                       $lm = floor((ord($sa[$i]) * 256 + ord($sa[$i + 1]) + 7) / 8);\r
+                                       $i += $lm + 2;\r
+                                       \r
+                                       $mod = substr($s, $m, $lm + 2);\r
+                                       $le = floor((ord($sa[$i]) * 256 + ord($sa[$i+1]) + 7) / 8);\r
+                                       $i += $le + 2;\r
+                                       \r
+                                       $this->public_key = base64_encode(substr($s, $m, $lm + $le + 4));\r
+                                       $this->type = "RSA";\r
+                                       \r
+                                       if ($version == 3) {\r
+                                               $this->fp = '';\r
+                                               $this->key_id = bin2hex(substr($mod, strlen($mod) - 8, 8));\r
+                                       } else if($version == 4) {\r
+                                               \r
+                                               // https://tools.ietf.org/html/rfc4880#section-12\r
+                                               $headerPos = strpos($s, chr(0x04));  // TODO: is this always the correct starting point for the pulic key packet 'version' field?\r
+                                               $delim = chr(0x01) . chr(0x00);  // TODO: is this the correct delimiter for the end of the public key packet? \r
+                                               $delimPos = strpos($s, $delim) + (3-$headerPos);\r
+                                               \r
+                                               // echo "POSITION: $delimPos\n";\r
+                                               \r
+                                               $pkt = chr(0x99) . chr($delimPos >> 8) . chr($delimPos & 255) . substr($s, $headerPos, $delimPos);\r
+                                               \r
+                                               // this is the original signing string which seems to have only worked for key lengths of 1024 or less\r
+                                               //$pkt = chr(0x99) . chr($len >> 8) . chr($len & 255) . substr($s, $k, $len);\r
+                                               \r
+                                               $fp = sha1($pkt);\r
+                                               $this->fp = $fp;\r
+                                               $this->key_id = substr($fp, strlen($fp) - 16, 16);\r
+                                               \r
+                                               // uncomment to debug the start point for the signing string\r
+//                                             for ($ii = 5; $ii > -1; $ii--) {\r
+//                                                     $pkt = chr(0x99) . chr($ii >> 8) . chr($ii & 255) . substr($s, $headerPos, $ii);\r
+//                                                     $fp = sha1($pkt);\r
+//                                                     echo "LENGTH=" . $headerPos . '->' . $ii . " CHR(" . ord(substr($s,$ii, 1)) . ") = " . substr($fp, strlen($fp) - 16, 16) . "\n";\r
+//                                             }\r
+//                                             echo "\n";\r
+                                               \r
+                                               // uncomment to debug the end point for the signing string\r
+//                                             for ($ii = strlen($s); $ii > 1; $ii--) {\r
+//                                                     $pkt = chr(0x99) . chr($ii >> 8) . chr($ii & 255) . substr($s, $headerPos, $ii);\r
+//                                                     $fp = sha1($pkt);\r
+//                                                     echo "LENGTH=" . $headerPos . '->' . $ii . " CHR(" . ord(substr($s,$ii, 1)) . ") = " . substr($fp, strlen($fp) - 16, 16) . "\n";\r
+//                                             }\r
+                                       } else {\r
+                                               throw new Exception('GPG Key Version ' . $version . ' is not supported');\r
+                                       }\r
+                                       $found = 2;\r
+                               } else if(($algo == 16 || $algo == 20) && $version == 4) {\r
+                                               $m = $i;\r
+                                               \r
+                                               $lp = floor((ord($sa[$i]) * 256 + ord($sa[$i +1]) + 7) / 8);\r
+                                               $i += $lp + 2;\r
+                                               \r
+                                               $lg = floor((ord($sa[$i]) * 256 + ord($sa[$i + 1]) + 7) / 8);\r
+                                               $i += $lg + 2;\r
+                                               \r
+                                               $ly = floor((ord($sa[$i]) * 256 + ord($sa[$i + 1]) + 7)/8);\r
+                                               $i += $ly + 2;\r
+                                               \r
+                                               $this->public_key = base64_encode(substr($s, $m, $lp + $lg + $ly + 6));\r
+                                               \r
+                                               // TODO: should this be adjusted as it was for RSA (above)..?\r
+                                               \r
+                                               $pkt = chr(0x99) . chr($len >> 8) . chr($len & 255) . substr($s, $k, $len);\r
+                                               $fp = sha1($pkt);\r
+                                               $this->fp = $fp;\r
+                                               $this->key_id = substr($fp, strlen($fp) - 16, 16);\r
+                                               $this->type = "ELGAMAL";\r
+                                               $found = 3;\r
+                                       } else {\r
+                                               $i = $k + $len;\r
+                                       }\r
+                       } else if ($tag == 13) {\r
+                                       $this->user = substr($s, $i, $len);\r
+                                       $i += $len;\r
+                               } else {\r
+                                       $i += $len;\r
+                               }\r
+               }\r
+               \r
+               if($found < 2) {  \r
+                       \r
+                       throw new Exception("Unable to parse Public Key");\r
+//                     $this->version = "";\r
+//                     $this->fp = "";\r
+//                     $this->key_id = "";\r
+//                     $this->user = ""; \r
+//                     $this->public_key = "";\r
+               }\r
+       }\r
+       \r
+       function GetExpandedKey()\r
+       {\r
+               $ek = new Expanded_Key($this->public_key);\r
+       }\r
+}\r
+\r
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG/Utility.php b/securemail/php-gpg/libs/GPG/Utility.php
new file mode 100644 (file)
index 0000000..ac3ac6b
--- /dev/null
@@ -0,0 +1,131 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** seed rand */\r
+list($gpg_usec, $gpg_sec) = explode(' ', microtime());\r
+srand((float) $gpg_sec + ((float) $gpg_usec * 100000));\r
+\r
+/**\r
+ * @package    php-gpg::GPG\r
+ */\r
+class GPG_Utility\r
+{\r
+       \r
+       static function starts_with($haystack, $needle)\r
+       {\r
+               return $needle === "" || strpos($haystack, $needle) === 0;\r
+       }\r
+       \r
+       static function B0($x) {\r
+               return ($x & 0xff);\r
+       }\r
+       \r
+       static function B1($x) {\r
+               return (($x >> 0x8) & 0xff);\r
+       }\r
+       \r
+       static function B2($x) {\r
+               return (($x >> 0x10) & 0xff);\r
+       }\r
+       \r
+       static function B3($x) {\r
+               return (($x >> 0x18) & 0xff);\r
+       }\r
+       \r
+       static function zshift($x, $s) {\r
+               $res = $x >> $s;\r
+               \r
+               $pad = 0;\r
+               for ($i = 0; $i < 32 - $s; $i++) $pad += (1 << $i);\r
+               \r
+               return $res & $pad;\r
+       }\r
+       \r
+       static function pack_octets($octets)\r
+       {\r
+               $i = 0;\r
+               $j = 0;\r
+               $len = count($octets);\r
+               $b = array_fill(0, $len / 4, 0);\r
+               \r
+               if (!$octets || $len % 4) return;\r
+               \r
+               for ($i = 0, $j = 0; $j < $len; $j += 4) {\r
+                       $b[$i++] = $octets[$j] | ($octets[$j + 1] << 0x8) | ($octets[$j + 2] << 0x10) | ($octets[$j + 3] << 0x18);\r
+                       \r
+               }\r
+               \r
+               return $b;  \r
+       }\r
+       \r
+       static function unpack_octets($packed)\r
+       {\r
+               $j = 0;\r
+               $i = 0;\r
+               $l = count($packed);\r
+               $r = array_fill(0, $l * 4, 0);\r
+               \r
+               for ($j = 0; $j < $l; $j++) {\r
+                       $r[$i++] = GPG_Utility::B0($packed[$j]);\r
+                       $r[$i++] = GPG_Utility::B1($packed[$j]);\r
+                       $r[$i++] = GPG_Utility::B2($packed[$j]);\r
+                       $r[$i++] = GPG_Utility::B3($packed[$j]);\r
+               }\r
+               \r
+               return $r;\r
+       }\r
+\r
+\r
+\r
+\r
+       static function hex2bin($h)\r
+       {\r
+               if(strlen($h) % 2) $h += "0";\r
+\r
+               $r = "";\r
+               for($i = 0; $i < strlen($h); $i += 2) {\r
+                       $r .= chr(intval($h[$i], 16) * 16 + intval($h[$i + 1], 16));\r
+               }\r
+\r
+               return $r;\r
+       }\r
+\r
+       static function crc24($data)\r
+       {\r
+               $crc = 0xb704ce;\r
+\r
+               for($n = 0; $n < strlen($data); $n++) {\r
+                       $crc ^= (ord($data[$n]) & 0xff) << 0x10;\r
+                       for($i = 0; $i < 8; $i++) {\r
+                               $crc <<= 1;\r
+                               if($crc & 0x1000000) $crc ^= 0x1864cfb;\r
+                       }       \r
+               }\r
+           \r
+               return\r
+                       chr(($crc >> 0x10) & 0xff) .\r
+                       chr(($crc >> 0x8) & 0xff) .\r
+                       chr($crc & 0xff);\r
+       }\r
+\r
+       static function s_random($len, $textmode)\r
+       {\r
+               $r = "";\r
+               for($i = 0; $i < $len;)\r
+               {\r
+                       $t = rand(0, 0xff);\r
+                       if($t == 0 && $textmode) continue;\r
+                       $i++;\r
+\r
+                       $r .= chr($t);\r
+               }\r
+\r
+               return $r;\r
+       }\r
+\r
+       static function c_random() {\r
+               return round(rand(0, 0xff));\r
+       }\r
+\r
+}\r
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/libs/GPG/globals.php b/securemail/php-gpg/libs/GPG/globals.php
new file mode 100644 (file)
index 0000000..5b2dbce
--- /dev/null
@@ -0,0 +1,403 @@
+<?php\r
+/** @package    php-gpg::GPG */\r
+\r
+/** assign globals */\r
+global $bs;\r
+global $bx2;\r
+global $bm;\r
+global $bx;\r
+global $bd;\r
+global $bdm;\r
+\r
+$bs = 28;\r
+$bx2 = 1 << $bs;\r
+$bm = $bx2 - 1;\r
+$bx = $bx2 >> 1;\r
+$bd = $bs >> 1;\r
+$bdm = (1 << $bd) - 1;\r
+\r
+/**\r
+ */\r
+function mpi2b($s)\r
+{\r
+    global $bs;\r
+    global $bx2;\r
+    global $bm;\r
+    global $bx;\r
+    global $bd;\r
+    global $bdm;\r
+\r
+    $bn = 1;\r
+    $r = array(0);\r
+    $rn = 0;\r
+    $sb = 256;\r
+    $c = 0;\r
+    $sn = strlen($s);\r
+    if($sn < 2) {\r
+        echo("string too short, not a MPI");\r
+        return 0;\r
+    }\r
+\r
+    $len = ($sn - 2) * 8;\r
+    $bits = ord($s[0]) * 256 + ord($s[1]);\r
+    if ($bits > $len || $bits < $len - 8) {\r
+        echo("not a MPI, bits = $bits, len = $len");\r
+        return 0;\r
+    }\r
+\r
+    for ($n = 0; $n < $len; $n++) {\r
+        if (($sb <<= 1) > 255) {\r
+            $sb = 1; $c = ord($s[--$sn]);\r
+        }\r
+        if ($bn > $bm) {\r
+            $bn = 1;\r
+            $r[++$rn]=0;\r
+        }\r
+        if ($c & $sb) $r[$rn] |= $bn;\r
+        $bn <<= 1;\r
+    }\r
+\r
+    return $r;\r
+}\r
+\r
+/**\r
+ */\r
+function b2mpi($b)\r
+{\r
+    global $bs;\r
+    global $bx2;\r
+    global $bm;\r
+    global $bx;\r
+    global $bd;\r
+    global $bdm;\r
+\r
+    $bn = 1;\r
+    $bc = 0;\r
+    $r = array(0);\r
+    $rb = 1;\r
+    $rn = 0;\r
+    $bits = count($b) * $bs;\r
+    $n = 0;\r
+    $rr = "";\r
+\r
+    for ($n = 0; $n < $bits; $n++) {\r
+        if ($b[$bc] & $bn) $r[$rn] |= $rb;\r
+        if(($rb <<= 1) > 255) {\r
+            $rb = 1; $r[++$rn]=0;\r
+        }\r
+        if (($bn <<= 1) > $bm) {\r
+            $bn=1; $bc++;\r
+        }\r
+    }\r
+\r
+    while ($rn && $r[$rn]==0) $rn--;\r
+\r
+    $bn=256;\r
+    for($bits = 8; $bits > 0; $bits--) if ($r[$rn] & ($bn >>= 1)) break;\r
+    $bits += $rn * 8;\r
+\r
+    $rr .= chr($bits / 256 ) . chr($bits % 256);\r
+    if ($bits) for($n = $rn; $n >= 0; $n--) $rr .= chr($r[$n]);\r
+\r
+    return $rr;\r
+}\r
+\r
+/**\r
+ */\r
+function bmodexp($xx, $y, $m) {\r
+    global $bs;\r
+    global $bx2;\r
+    global $bm;\r
+    global $bx;\r
+    global $bd;\r
+    global $bdm;\r
+\r
+    $r = array(1);\r
+    $an = 0;\r
+    $a = 0;\r
+    $x = array_merge((array)$xx);\r
+    $n = count($m) * 2;\r
+    $mu = array_fill(0, $n + 1, 0);\r
+\r
+    $mu[$n--] = 1;\r
+    for(; $n >= 0; $n--) $mu[$n] = 0;\r
+    $dd = new bdiv($mu, $m);\r
+    $mu = $dd->q;\r
+\r
+    for($n = 0; $n < count($y); $n++) {\r
+        for ($a = 1, $an = 0; $an < $bs; $an++, $a <<= 1) {\r
+            if ($y[$n] & $a) $r = bmod2(bmul($r, $x), $m, $mu);\r
+            $x = bmod2(bmul($x, $x), $m, $mu);\r
+        }\r
+    }\r
+\r
+    return $r;\r
+}\r
+\r
+/**\r
+ */\r
+function simplemod($i, $m) // returns the mod where m < 2^bd\r
+{\r
+    $c = 0;\r
+    $v = 0;\r
+    for ($n = count($i) - 1; $n >= 0; $n--)\r
+    {\r
+        $v = $i[$n];\r
+        $c = (($v >> $bd) + ($c << $bd)) % $m;\r
+        $c = (($v & $bdm) + ($c << $bd)) % $m;\r
+    }\r
+\r
+    return $c;\r
+}\r
+\r
+/**\r
+ */\r
+function bmod($p, $m) // binary modulo\r
+{\r
+    global $bdm;\r
+\r
+    if (count($m) == 1) {\r
+        if(count($p) == 1) return array($p[0] % $m[0]);\r
+        if($m[0] < $bdm) return array(simplemod($p, $m[0]));\r
+    }\r
+\r
+    $r = new bdiv($p, $m);\r
+    return $r->mod;\r
+}\r
+\r
+/**\r
+ */\r
+function bmod2($x, $m, $mu) {\r
+    $xl = count($x) - (count($m) << 1);\r
+    if ($xl > 0) return bmod2(array_concat(array_slice($x, 0, $xl), bmod2(array_slice($x, $xl), $m, $mu)), $m, $mu);\r
+\r
+    $ml1 = count($m) + 1;\r
+    $ml2 = count($m) - 1;\r
+    $rr = 0;\r
+\r
+    $q3 = array_slice(bmul(array_slice($x, $ml2), $mu), $ml1);\r
+    $r1 = array_slice($x, 0, $ml1);\r
+    $r2 = array_slice(bmul($q3, $m), 0, $ml1);\r
+\r
+    $r = bsub($r1, $r2);\r
+    if (count($r) == 0) {\r
+        $r1[$ml1] = 1;\r
+        $r = bsub($r1, $r2);\r
+    }\r
+    for ($n = 0;; $n++) {\r
+        $rr = bsub($r, $m);\r
+        if(count($rr) == 0) break;\r
+        $r = $rr;\r
+        if($n >= 3) return bmod2($r, $m, $mu);\r
+    }\r
+\r
+    return $r;\r
+}\r
+\r
+/**\r
+ */\r
+function toppart($x, $start, $len) {\r
+    global $bx2;\r
+\r
+    $n = 0;\r
+    while ($start >= 0 && $len-- > 0) $n = $n * $bx2 + $x[$start--];\r
+\r
+    return $n;\r
+}\r
+\r
+/**\r
+ */\r
+function zeros($n) {\r
+    $r = array_fill(0, $n, 0);\r
+    while ($n-- > 0) $r[$n] = 0;\r
+    return $r;\r
+}\r
+\r
+/**\r
+ * @package    verysimple::Encryption\r
+ */\r
+class bdiv {\r
+       var $q;\r
+       var $mod;\r
+       function bdiv($x, $y)\r
+       {\r
+               global $bs;\r
+               global $bx2;\r
+               global $bm;\r
+               global $bx;\r
+               global $bd;\r
+               global $bdm;\r
+\r
+               $n = count($x) - 1;\r
+               $t = count($y) - 1;\r
+               $nmt = $n - $t;\r
+\r
+               if ($n < $t || $n == $t && ($x[$n] < $y[$n] || $n > 0 && $x[$n] == $y[$n] && $x[$n - 1] < $y[$n - 1])) {\r
+                       $this->q = array(0);\r
+                       $this->mod = array($x);\r
+                       return;\r
+               }\r
+\r
+               if ($n == $t && toppart($x, $t, 2) / toppart($y, $t, 2) < 4) {\r
+                       $qq = 0;\r
+                       $xx = 0;\r
+                       for(;;) {\r
+                               $xx = bsub($x, $y);\r
+                               if(count($xx) == 0) break;\r
+                               $x = $xx; $qq++;\r
+                       }\r
+                       $this->q = array($qq);\r
+                       $this->mod = $x;\r
+                       return;\r
+               }\r
+\r
+               $shift2 = floor(log($y[$t]) / M_LN2) + 1;\r
+               $shift = $bs - $shift2;\r
+               if ($shift) {\r
+                       $x = array_merge((array)$x); $y = array_merge((array)$y);\r
+                       for($i = $t; $i > 0; $i--) $y[$i] = (($y[$i] << $shift) & $bm) | ($y[$i - 1] >> $shift2);\r
+                       $y[0] = ($y[0] << $shift) & $bm;\r
+                       if($x[$n] & (($bm << $shift2) & $bm)) {\r
+                               $x[++$n] = 0; $nmt++;\r
+                       }\r
+                       for($i = $n; $i > 0; $i--) $x[$i] = (($x[$i] << $shift) & $bm) | ($x[$i - 1] >> $shift2);\r
+                       $x[0] = ($x[0] << $shift) & $bm;\r
+               }\r
+\r
+               $i = 0;\r
+               $j = 0;\r
+               $x2 = 0;\r
+               $q = zeros($nmt + 1);\r
+               $y2 = array_merge(zeros($nmt), (array)$y);\r
+               for (;;) {\r
+                       $x2 = bsub($x, $y2);\r
+                       if(count($x2) == 0) break;\r
+                       $q[$nmt]++;\r
+                       $x = $x2;\r
+               }\r
+\r
+               $yt = $y[$t];\r
+               $top =toppart($y, $t, 2);\r
+               for ($i = $n; $i > $t; $i--) {\r
+                       $m = $i - $t - 1;\r
+                       if ($i >= count($x)) $q[$m] = 1;\r
+                       else if($x[$i] == $yt) $q[$m] = $bm;\r
+                       else $q[$m] = floor(toppart($x, $i, 2) / $yt);\r
+\r
+                       $topx = toppart($x, $i, 3);\r
+                       while ($q[$m] * $top > $topx) $q[$m]--;\r
+\r
+                       $y2 = array_slice($y2, 1);\r
+                       $x2 = bsub($x, bmul(array($q[$m]), $y2));\r
+                       if (count($x2) == 0) {\r
+                               $q[$m]--;\r
+                               $x2 =bsub($x, bmul(array($q[m]), $y2));\r
+                       }\r
+                       $x = $x2;\r
+               }\r
+\r
+               if ($shift) {\r
+                       for($i = 0; $i < count($x) - 1; $i++) $x[$i] = ($x[$i] >> $shift) | (($x[$i + 1] << $shift2) & $bm);\r
+                       $x[count($x) - 1] >>= $shift;\r
+               }\r
+               $n = count($q);\r
+               while ($n > 1 && $q[$n - 1] == 0) $n--;\r
+               $this->q = array_slice($q, 0, $n);\r
+               $n = count($x);\r
+               while ($n > 1 && $x[$n - 1] == 0) $n--;\r
+               $this->mod = array_slice($x, 0, $n);\r
+       }\r
+}\r
+\r
+/**\r
+ */\r
+function bsub($a, $b) {\r
+    global $bs;\r
+    global $bx2;\r
+    global $bm;\r
+    global $bx;\r
+    global $bd;\r
+    global $bdm;\r
+\r
+    $al = count($a);\r
+    $bl = count($b);\r
+\r
+    if ($bl > $al) return array();\r
+    if ($bl == $al) {\r
+        if($b[$bl - 1] > $a[$bl - 1]) return array();\r
+        if($bl == 1) return array($a[0] - $b[0]);\r
+    }\r
+\r
+    $r = array_fill(0, $al, 0);\r
+    $c = 0;\r
+\r
+    for ($n = 0; $n < $bl; $n++) {\r
+        $c += $a[$n] - $b[$n];\r
+        $r[$n] = $c & $bm;\r
+        $c >>= $bs;\r
+    }\r
+    for (; $n < $al; $n++) {\r
+        $c += $a[$n];\r
+        $r[$n] = $c & $bm;\r
+        $c >>= $bs;\r
+    }\r
+    if ($c) return array();\r
+\r
+    if ($r[$n - 1]) return $r;\r
+    while ($n > 1 && $r[$n - 1] == 0) $n--;\r
+\r
+    return array_slice($r, 0, $n);\r
+}\r
+\r
+/**\r
+ */\r
+function bmul($a, $b) {\r
+    global $bs;\r
+    global $bx2;\r
+    global $bm;\r
+    global $bx;\r
+    global $bd;\r
+    global $bdm;\r
+\r
+    $b = array_merge((array)$b, array(0));\r
+    $al = count($a);\r
+    $bl = count($b);\r
+    $n = 0;\r
+    $nn = 0;\r
+    $aa = 0;\r
+    $c = 0;\r
+    $m = 0;\r
+    $g = 0;\r
+    $gg = 0;\r
+    $h = 0;\r
+    $hh = 0;\r
+    $ghh = 0;\r
+    $ghhb = 0;\r
+\r
+    $r = zeros($al + $bl + 1);\r
+\r
+    for ($n = 0; $n < $al; $n++) {\r
+        $aa = $a[$n];\r
+        if ($aa) {\r
+            $c = 0;\r
+            $hh = $aa >> $bd; $h = $aa & $bdm;\r
+            $m = $n;\r
+            for ($nn = 0; $nn < $bl; $nn++, $m++) {\r
+                $g = $b[$nn]; $gg = $g >> $bd; $g = $g & $bdm;\r
+                $ghh = $g * $hh + $h * $gg;\r
+                $ghhb = $ghh >> $bd; $ghh &= $bdm;\r
+                $c += $r[$m] + $h * $g + ($ghh << $bd);\r
+                $r[$m] = $c & $bm;\r
+                $c = ($c >> $bs) + $gg * $hh + $ghhb;\r
+            }\r
+        }\r
+    }\r
+    $n = count($r);\r
+\r
+    if ($r[$n - 1]) return $r;\r
+    while ($n > 1 && $r[$n - 1] == 0) $n--;\r
+\r
+    return array_slice($r, 0, $n);\r
+}\r
+\r
+?>\r
diff --git a/securemail/php-gpg/tests/gpg/EncryptTest.php b/securemail/php-gpg/tests/gpg/EncryptTest.php
new file mode 100644 (file)
index 0000000..fa08c3f
--- /dev/null
@@ -0,0 +1,135 @@
+<?php
+/**
+ * @package GPG::Tests
+ */
+/* ensure the framework libraries can be located */\r
+set_include_path(\r
+               realpath("../libs") .\r
+               PATH_SEPARATOR . get_include_path()\r
+);
+
+require_once 'PHPUnit/Framework/TestCase.php';
+require_once 'GPG.php';\r
+
+/**
+ * 
+ */
+class EncryptTest extends PHPUnit_Framework_TestCase
+{
+       /**\r
+        * @see PHPUnit_Framework_TestCase::setUp()\r
+        */\r
+       function setUp()\r
+       {\r
+       }\r
+       \r
+       /**\r
+        * @see PHPUnit_Framework_TestCase::tearDown()\r
+        */\r
+       function tearDown()\r
+       {\r
+       }
+       
+       /**
+        * Return a public key used for encryption
+        * @return string PGP public key
+        */
+       function getTestKey()
+       {
+               return "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: GnuPG/MacGPG2 v2.0.22 (Darwin)
+Comment: GPGTools - https://gpgtools.org
+
+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
+0w==
+=Opd1
+-----END PGP PUBLIC KEY BLOCK-----";
+       }\r
+       \r
+       /**\r
+        * Test that basic encryption returns a valid encrypted message\r
+        */\r
+       function test_Encrypt()\r
+       {\r
+               // jason's public key
+               $public_key_ascii = $this->getTestKey();
+               
+               // plain text message
+               $plain_text_string = "Whatever 90's tote bag, meggings put a bird on it cray bicycle rights vinyl semiotics Wes Anderson. Selvage Austin umami, letterpress Tumblr deep v kitsch polaroid. Trust fund messenger bag sartorial gluten-free, cred cray church-key pop-up Intelligentsia. Food truck Tumblr paleo mixtape XOXO banjo PBR&B Pinterest tofu banh mi. Portland messenger bag cornhole PBR Tonx High Life, DIY pork belly bespoke hoodie Terry Richardson dreamcatcher ethical forage. Put a bird on it slow-carb mixtape cardigan craft beer messenger bag. Aesthetic twee art party, Odd Future trust fund banjo ugh small batch semiotics.
+
+Whatever asymmetrical keffiyeh literally narwhal. Keytar Odd Future blog, wayfarers literally gluten-free beard. Authentic Cosby sweater sustainable hashtag, VHS food truck kogi seitan put a bird on it YOLO. Selvage tousled mustache, flannel craft beer try-hard McSweeney's literally four loko YOLO keytar beard synth forage. Salvia Schlitz narwhal Terry Richardson typewriter, Wes Anderson butcher wolf. Slow-carb whatever bitters, letterpress trust fund pug before they sold out food truck artisan tousled. Church-key Vice craft beer Wes Anderson artisan flexitarian, kogi YOLO hella Tonx chia Neutra.
+
+Farm-to-table actually Portland, artisan shabby chic vinyl organic seitan roof party distillery. Street art PBR&B banh mi, Tonx authentic you probably haven't heard of them fixie whatever tofu gluten-free. Gentrify locavore lo-fi umami, Thundercats salvia wolf four loko. Mixtape messenger bag gluten-free, squid American Apparel hella Shoreditch whatever selfies sriracha before they sold out. Pickled farm-to-table Intelligentsia occupy. Tumblr Etsy farm-to-table, mlkshk hella shabby chic meh jean shorts dreamcatcher fashion axe trust fund lomo Neutra. Freegan vegan narwhal tousled hoodie wolf flexitarian.
+
+Flannel sriracha XOXO, slow-carb Godard ennui tousled American Apparel street art drinking vinegar lo-fi blog. Whatever Intelligentsia cardigan, Pinterest PBR&B pop-up semiotics. Jean shorts chillwave semiotics biodiesel. McSweeney's fap cardigan messenger bag fanny pack Cosby sweater Odd Future, Pitchfork four loko Marfa keytar mlkshk. 3 wolf moon McSweeney's gluten-free, umami freegan biodiesel fingerstache aesthetic sriracha swag Echo Park. Shabby chic selfies fixie, art party XOXO four loko chambray post-ironic letterpress messenger bag. Mustache beard lo-fi, flexitarian artisan tofu freegan occupy kale chips Carles twee chia bespoke.";
+               
+               $gpg = new GPG();
+               $pub_key = new GPG_Public_Key($public_key_ascii);
+               $encrypted = $gpg->encrypt($pub_key,$plain_text_string);
+               
+               $this->assertContains('-----BEGIN PGP MESSAGE-----', $encrypted, 'PGP Header Expected');
+               
+               $this->assertContains('-----END PGP MESSAGE-----', $encrypted, 'PGP Footer Expected');
+\r
+       }
+
+}
+
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/tests/gpg/KeyTest.php b/securemail/php-gpg/tests/gpg/KeyTest.php
new file mode 100644 (file)
index 0000000..7939502
--- /dev/null
@@ -0,0 +1,1474 @@
+<?php
+/**
+ * @package GPG::Tests
+ */
+/* ensure the framework libraries can be located */
+set_include_path(
+               realpath("../libs") .
+               PATH_SEPARATOR . get_include_path()
+);
+
+require_once 'PHPUnit/Framework/TestCase.php';
+require_once 'GPG.php';
+
+/**
+ * 
+ */
+class KeyTest extends PHPUnit_Framework_TestCase
+{
+       /**
+        * @see PHPUnit_Framework_TestCase::setUp()
+        */
+       function setUp()
+       {
+       }
+       
+       /**
+        * @see PHPUnit_Framework_TestCase::tearDown()
+        */
+       function tearDown()
+       {
+       }
+       
+       function getGnuPGDSAKey()
+       {
+               return "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: GnuPG/MacGPG2 v2.0.22 (Darwin)
+Comment: GPGTools - https://gpgtools.org
+
+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
++ZVkIBkLx7SrbZW6Mogi3f2ViQIcBBMBAgAGBQJPUMRhAAoJEOD9KQZtDBSx0ckQ
+ALAH7uPyQQ30HRM/Y55Ls38YRzGb8zn5vdmU8TNg3F3veHXKU+qa2MglcQLD0wm4
+x7w3JaF8GPLN5YRaDtOoKcbRq5pMqw/bQLLlrX7ZjRzIDkOFOhC9jw3W15M/J8jI
+v/xtf3O727eGvs/orXJF9+iCsBRPIG+0PssLdK8q+4CudRoC7quoxlpRwglW6yan
+BPAElyxMNS3fM9B0sVWRfW+gtBa1VtAZZm+5h4mxybUln96cRBo2LGrJ28i9pc79
+dIfUJMX6XOC7OFZJ5eHlwjPqQLplcE/yjlmHYBcoX62CIxyIV7CV98YOIZ3KrPFr
+Qe+Ad+Ho/yuMVU9C29e8ahugvmSvOodL3R2FiiG3S174FRW9yXRm22WrB82A2LPV
+LtHyRJ97A+LT7a8l3xTm0mCku+9+eiYE+vJY1Lbg7IznPP3junvOO/51Mebb/KdZ
+j6lzx1h5bAzoyH4AOMwb0ZOFadaaw8Ks03AZSWBD71DdFjxtKpib3VeKJ0YQDWk/
+gYdh+6RENzuyz97sOHPFwuriw19K5FHUgTSFvjHDSlg6e2kqLNHzVM5RX4grlZxc
+AZTBlrbEppqoN69qEvnv9luK3IYviHtdaCpsMnT1HVG9HRiuAKg+JhxIdCYczmge
+iUMRCJ3D8JdR6gQ6A4OgZqubAkz3SvXTgIElh4c2N9AviQIcBBMBAgAGBQJPoLUx
+AAoJEG8wgEnVsL7DK/QQAMcgtYvGApHP2XGjAACfFFQLl19MC3M5dQJVoU4h5AM9
+GYQaP4vMDmNWF/xNp4pzhi7J7DcU6UQ/J8a/PESuLHylBrMHzF1ao5Wvgmcv11mP
+3byWKcDcyN/WuXQn7/UQai8MQfapmkaJmutqSmkEh6sPyIx98ftEv8fgaw+gH/Q/
+XCqlMvyPiMKH3EdUx1eOwhS5y2GGzF1+MQQzDaRVDns4XCIUCNGigkJ0S9n2adyR
+jpEhkf/YhLgrfdAXaVIIfvaqi46ItzqJYMhqy3qID62a5QxAiInbV/kL82dCjLTl
+TvknCdN+3h8Pgba4jIr9X4CMqMxKxvRg4I3qisbsC3k9gdYgJEXZyroPlxunHx2r
+wkrOqjPYt5+67O6EGHiNaH4dil/uDjbBk1B+s2yobmm5VPqATpivK5XnzDTm2NHp
+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
+GiUmJygpKjQ1Njc4OTpDREVGR0hJSlNUVVZXWFlaY2RlZmdoaWpzdHV2d3h5eoOE
+hYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX
+2Nna4eLj5OXm5+jp6vHy8/T19vf4+fr/xAAfAQADAQEBAQEBAQEBAAAAAAAAAQID
+BAUGBwgJCgv/xAC1EQACAQIEBAMEBwUEBAABAncAAQIDEQQFITEGEkFRB2FxEyIy
+gQgUQpGhscEJIzNS8BVictEKFiQ04SXxFxgZGiYnKCkqNTY3ODk6Q0RFRkdISUpT
+VFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqCg4SFhoeIiYqSk5SVlpeYmZqio6Slpqeo
+qaqys7S1tre4ubrCw8TFxsfIycrS09TV1tfY2dri4+Tl5ufo6ery8/T19vf4+fr/
+2gAMAwEAAhEDEQA/AP38ooooAKKKra1rNn4c0e71HxDdW9jYWEL3Fzc3Egjit4kU
+s7u7EBVVQSSTgAE0AWa8Q+LX7fHgn4eeLH8L+ChqXj3xmp2nRPDkBvJoW44mdfki
+xnnJyO4rxvUvi14w/wCCizy3Hw+1XVvht+z6rtCmtQKYNe+IABwxsgw3WlicECUj
+fIORhTitvVPHvgX9jHwAmi/CbR7Dw3bOMR2tou68vWx96aU5eRj6kmgDobz4iftA
++Po/PTTvA3ws01xlf7Vu/t9+o7ZSMFM+xxXP3uleLyxPjD9owxzHkrp2iLEg9h+9
+/pXmNpH8Xf2mbx5fCenS6Zprnie4JGF9TngVHf8A7J1vo8pT4ofGHwzpl5/HD9vQ
+uh9CAc0Aep2OkeMgwPgv9otZpgchNS0VZFb2J8w/yret/ib+0D8O4/PvdE8F/FLT
+EwWbRrz7HfsO5EbhV6dgGNeH6f8AslLrUgX4UfF3w1q93/DAt+gdj6BSc06bUPi1
++zHfq3jXTJ7/AE5DzNb5PHqMcGgD6a+Df7evgb4qeKB4a8QPf+CvGQIQ6H4ggNlc
+yN6RF8LJnHAB3H0r2yvkiLxN8P8A9tzwCdM+LOj2fiCKIYxKPK1DTm/vQzDDow9j
+9c1z2lfHXxl/wTiv7KL476xqHxD+AF3Mlrb+MJlMmr+B2Y7UTVQOZrTJA+0DlP4v
+l+6AfbFFQ6fqFvq1hBd6VPDdWt1GssM0Th45UYZVlYcMCCCCOCDU1ABRRRQAUUUU
+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
+Bo827CdOXA==
+=nadi
+-----END PGP PUBLIC KEY BLOCK-----";
+       }
+       
+       /**\r
+        * Return a public key used for encryption\r
+        * @return string PGP public key\r
+        */\r
+       function getOpenPGPTestKey1()\r
+       {\r
+               return "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: OpenPGP.js v.1.20140106
+Comment: http://openpgpjs.org
+
+xo0EUsvlVAEEAJN0OBFbVM21z3OzG9DDCohpaF9+rWUyCreRIDC+Cou9680f
+t8v5m9B0+BTM2OVEB3uK7QbcWhsPkfpn7zW9YntStSXI5ESC+eAhNGbAKnvq
+32MadP7DbwRUrtcldSEd2B6uI/embnmv1CBkmrTAh0MiKscHPh5xrxwcxLLJ
+TQstABEBAAHNF1Rlc3QgPHRlc3RAZXhhbXBsZS5jb20+wpwEEAEIABAFAlLL
+5VUJEI3OSY9gkd/WAAAgKwP/TUeVmXMS3YYvTLC0tRw/Ae1M4sNduvuKcza2
+4l6iuiIhXHntL9u5pQERcyhzL171DsR1S3EUj/nIFpfqN8OWOuj0Wqt3H4F9
+igkfsrJr68qHEQztSXRufP/jv7OX+0EF+ve0+IFa6r5LPRmibl0qta522gHd
+2LVudfBDDi0Y6k4=
+=JjPg
+-----END PGP PUBLIC KEY BLOCK-----";\r
+       }
+       
+       /**\r
+        * Return a public key used for encryption\r
+        * @return string PGP public key\r
+        */\r
+       function getOpenPGPTestKey2()\r
+       {
+               return "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: OpenPGP.js v.1.20140106
+Comment: http://openpgpjs.org
+
+xsBNBFLL5JEBCACFBaNfA4Iicm/MvO0sJcllB/iGc0qNgtqwpXGBydDt8Pj7
++mn0ZZ4Q1ol5wAYAxapGGaoEB1Wh5ALy2UvnrFx1/dyZEQhU3oUTRQevzhm1
+/gp/0l9bNijBONir1spMuDc7okXWaR8GCW0mWwmeFgXZnjL4Dmr6dUJvZHpX
+ZiekLPT3xHWQxrKdsafxmULVgd71ZdBq/6ikWQsK5XqBVykD2C/6jNDJ8Cga
+wzCs8WOSQkpss7L28qQrEkL3+JaLGEe3+6UUnzs5KjwgTZvlAawDkm55corz
+TistbvOotDVbs/nXyu6TnMhZXqJR2a0TEuRDXpS93qGr97flZKwVBp6vABEB
+AAHNF1Rlc3QgPHRlc3RAZXhhbXBsZS5jb20+wsBcBBABCAAQBQJSy+SZCRDI
+dThpeYYhmgAAVecH/R2IXW82smV41eDIwA9PzV6sKF7ywmlEl/zkZTEpTLaB
+bXM3wScspVHGWV7hO+9ZQImtdcqb2AFpNpBgBtpFypM2nMGdFxTzv0m3uRUs
+J8KT0lU0Uj4FEsr5YYCb1UWGgDrZP+vZFxfw8j+NWGIS5NlLHPeTTMJVRhKX
+Xe0c8AaAF8qz10+JyapyDlUlFVr8+n/UjGwsUp15ODnDt0nsGTfw6jKelTU2
+y/d0ckERWE0rWT2eooAxqxIoVayJkEZTzbfx/mHJXeGhOFwjg5danv7JnDI/
+FHAUVqBD8zTkqmjdk9LZ6GnF6tuKRAWS59qU7y4+fchP58dhjep0mIFa6FQ=
+=8aNP
+-----END PGP PUBLIC KEY BLOCK-----";
+       }
+       
+       /**
+        * Return a public key used for encryption
+        * @return string PGP public key
+        */
+       function getGnuPGTestKey()
+       {
+               return "-----BEGIN PGP PUBLIC KEY BLOCK-----
+Version: GnuPG/MacGPG2 v2.0.22 (Darwin)
+Comment: GPGTools - https://gpgtools.org
+
+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
+0w==
+=Opd1
+-----END PGP PUBLIC KEY BLOCK-----";
+       }
+       
+       /**\r
+        * Test key ID\r
+        */\r
+       function test_VerifyGnuPGKey()\r
+       {\r
+               // jason's public key\r
+               $public_key_ascii = $this->getGnuPGTestKey();\r
+       \r
+               $gpg = new GPG();\r
+               $pub_key = new GPG_Public_Key($public_key_ascii);\r
+       \r
+               $this->assertEquals(PK_TYPE_RSA,$pub_key->GetKeyType(),'OpenPGP Incorrect Key Type');\r
+               $this->assertEquals('47009B66424E9476',$pub_key->GetKeyId(),'OpenPGP Incorrect Key ID');\r
+               $this->assertEquals('ED4F E89E 38A3 7833 3CD4 D6FA 4700 9B66 424E 9476',$pub_key->GetFingerprint(),'OpenPGP Incorrect Fingerprint');\r
+       \r
+       }
+
+       /**\r
+        * Test key ID\r
+        */\r
+       function test_VerifyOpenPGPKey1()\r
+       {\r
+               // OpenPGP Test Key\r
+               $public_key_ascii = $this->getOpenPGPTestKey1();\r
+       \r
+               $gpg = new GPG();\r
+               $pub_key = new GPG_Public_Key($public_key_ascii);\r
+                       \r
+               $this->assertEquals(PK_TYPE_RSA,$pub_key->GetKeyType(),'OpenPGP Incorrect Key Type');\r
+               $this->assertEquals('8DCE498F6091DFD6',$pub_key->GetKeyId(),'OpenPGP Incorrect Key ID');\r
+               $this->assertEquals('C893 35AC EDF1 6046 7534 B25E 8DCE 498F 6091 DFD6',$pub_key->GetFingerprint(),'OpenPGP Incorrect Fingerprint');\r
+       \r
+       }
+       
+       /**\r
+        * Test key ID\r
+        */\r
+       function test_VerifyOpenPGPKey2()\r
+       {\r
+               // OpenPGP Test Key\r
+               $public_key_ascii = $this->getOpenPGPTestKey2();\r
+\r
+               $gpg = new GPG();\r
+               $pub_key = new GPG_Public_Key($public_key_ascii);
+                       
+               $this->assertEquals(PK_TYPE_RSA,$pub_key->GetKeyType(),'OpenPGP Incorrect Key Type');
+               $this->assertEquals('C87538697986219A',$pub_key->GetKeyId(),'OpenPGP Incorrect Key ID');
+               $this->assertEquals('3C05 9D07 C624 84A4 EF2D 3651 C875 3869 7986 219A',$pub_key->GetFingerprint(),'OpenPGP Incorrect Fingerprint');\r
+       \r
+       }
+       
+       function test_VerifyGnuPGDSAKey()
+       {
+               // OpenPGP Test Key\r
+               $public_key_ascii = $this->getGnuPGDSAKey();\r
+               \r
+               $gpg = new GPG();\r
+               $pub_key = new GPG_Public_Key($public_key_ascii);\r
+                       \r
+               $this->assertEquals(PK_TYPE_ELGAMAL,$pub_key->GetKeyType(),'OpenPGP Incorrect Key Type');\r
+               $this->assertEquals('76D78F0500D026C4',$pub_key->GetKeyId(),'OpenPGP Incorrect Key ID');\r
+               $this->assertEquals('85E3 8F69 046B 44C1 EC9F B07B 76D7 8F05 00D0 26C4',$pub_key->GetFingerprint(),'OpenPGP Incorrect Fingerprint');\r
+               
+               
+       }
+
+}
+
+?>
\ No newline at end of file
diff --git a/securemail/php-gpg/tests/runtests.sh b/securemail/php-gpg/tests/runtests.sh
new file mode 100644 (file)
index 0000000..32a1f70
--- /dev/null
@@ -0,0 +1,4 @@
+##
+#      Test runner for Phreeze
+##
+phpunit gpg/
\ No newline at end of file
diff --git a/securemail/securemail.php b/securemail/securemail.php
new file mode 100644 (file)
index 0000000..306d12b
--- /dev/null
@@ -0,0 +1,93 @@
+<?php\r
+/**\r
+ * Name: Secure Mail\r
+ * Description: Send notification mail encrypted with user-defined public GPG key\r
+ * Version: 1.0\r
+ * Author: Fabio Comuni <http://kirgroup.com/profile/fabrixxm>\r
+ */\r
+ require_once 'php-gpg/libs/GPG.php';\r
+\r
+ function securemail_install() {\r
+    register_hook('plugin_settings', 'addon/securemail/securemail.php', 'securemail_settings');\r
+    register_hook('plugin_settings_post', 'addon/securemail/securemail.php', 'securemail_settings_post');\r
+\r
+    register_hook('emailer_send_prepare',  'addon/securemail/securemail.php', 'securemail_emailer_send_prepare');\r
+\r
+    logger("installed securemail");\r
+}\r
+\r
+function securemail_uninstall() {\r
+    unregister_hook('plugin_settings', 'addon/securemail/securemail.php', 'securemail_settings');\r
+    unregister_hook('plugin_settings_post', 'addon/securemail/securemail.php', 'securemail_settings_post');\r
+\r
+    unregister_hook('emailer_send_prepare',  'addon/securemail/securemail.php', 'securemail_emailer_send_prepare');\r
+\r
+    logger("removed securemail");\r
+}\r
+\r
+\r
+function securemail_settings(&$a,&$s){\r
+    if(! local_user())\r
+           return;\r
+\r
+    $enable_checked = (intval(get_pconfig(local_user(),'securemail','enable')) ? ' checked="checked"' : '');\r
+    $publickey = get_pconfig(local_user(),'securemail','pkey');\r
+\r
+    # all of this should be in a template...\r
+    $s .= '<span id="settings_securemail_inflated" class="settings-block fakelink" style="display: block;" onclick="openClose(\'settings_securemail_expanded\'); openClose(\'settings_securemail_inflated\');">';\r
+    $s .= '<h3>' . t('"Secure Mail" Settings').'</h3>';\r
+    $s .= '</span>';\r
+    $s .= '<div id="settings_securemail_expanded" class="settings-block" style="display: none;">';\r
+    $s .= '<span class="fakelink" onclick="openClose(\'settings_securemail_expanded\'); openClose(\'settings_securemail_inflated\');">';\r
+    $s .= '<h3>' . t('"Secure Mail" Settings').'</h3>';\r
+    $s .= '</span>';\r
+    $s .= '<div id="securemail-wrapper">';\r
+\r
+    $s .= '<input id="securemail-enable" type="checkbox" name="securemail-enable" value="1"'.$enable_checked.' />';\r
+    $s .= '<label id="securemail-enable-label" for="securemail-enable">'.t('Enable Secure Mail').'</label>';\r
+\r
+    $s .= '<div class="clear"></div>';\r
+    $s .= '<label id="securemail-label" for="securemail-pkey">'.t('Public key').' </label>';\r
+    $s .= '<textarea id="securemail-pkey" name="securemail-pkey">'.$publickey.'</textarea>';\r
+    $s .= '</div><div class="clear"></div>';\r
+\r
+    $s .= '<div class="settings-submit-wrapper" ><input type="submit" id="securemail-submit" name="securemail-submit" class="settings-submit" value="' . t('Save Settings') . '" /></div>';\r
+    $s .= '</div>';\r
+\r
+    return;\r
+}\r
+function securemail_settings_post(&$a, &$b){\r
+\r
+    if(! local_user())\r
+        return;\r
+\r
+    if($_POST['securemail-submit']) {\r
+               set_pconfig(local_user(),'securemail','pkey',trim($_POST['securemail-pkey']));\r
+               $enable = ((x($_POST,'securemail-enable')) ? 1 : 0);\r
+               set_pconfig(local_user(),'securemail','enable', $enable);\r
+               info( t('Secure Mail Settings saved.') . EOL);\r
+    }\r
+}\r
+\r
+function securemail_emailer_send_prepare(&$a, &$b) {\r
+    if (!x($b,'uid')) return;\r
+       $uid = $b['uid'];\r
+\r
+    $enable_checked = get_pconfig($uid,'securemail','enable');\r
+    if (!$enable_checked) return;\r
+\r
+    $public_key_ascii = get_pconfig($uid,'securemail','pkey');\r
+\r
+    $gpg = new GPG();\r
+\r
+    # create an instance of a GPG public key object based on ASCII key\r
+    $pub_key = new GPG_Public_Key($public_key_ascii);\r
+\r
+    # using the key, encrypt your plain text using the public key\r
+    $txt_encrypted = $gpg->encrypt($pub_key,$b['textVersion']);\r
+    $html_encrypted = $gpg->encrypt($pub_key,$b['htmlVersion']);\r
+\r
+    $b['textVersion'] = $txt_encrypted;\r
+    $b['htmlVersion'] = $html_encrypted;\r
+    #var_dump($b);\r
+}\r