123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233 |
- <?php
-
- /**
- +-------------------------------------------------------------------------+
- | S/MIME driver for the Enigma Plugin |
- | |
- | Copyright (C) 2010-2015 The Roundcube Dev Team |
- | |
- | Licensed under the GNU General Public License version 3 or |
- | any later version with exceptions for skins & plugins. |
- | See the README file for a full license statement. |
- | |
- +-------------------------------------------------------------------------+
- | Author: Aleksander Machniak <alec@alec.pl> |
- +-------------------------------------------------------------------------+
- */
-
- class enigma_driver_phpssl extends enigma_driver
- {
- private $rc;
- private $homedir;
- private $user;
-
- function __construct($user)
- {
- $rcmail = rcmail::get_instance();
- $this->rc = $rcmail;
- $this->user = $user;
- }
-
- /**
- * Driver initialization and environment checking.
- * Should only return critical errors.
- *
- * @return mixed NULL on success, enigma_error on failure
- */
- function init()
- {
- $homedir = $this->rc->config->get('enigma_smime_homedir', INSTALL_PATH . '/plugins/enigma/home');
-
- if (!$homedir)
- return new enigma_error(enigma_error::INTERNAL,
- "Option 'enigma_smime_homedir' not specified");
-
- // check if homedir exists (create it if not) and is readable
- if (!file_exists($homedir))
- return new enigma_error(enigma_error::INTERNAL,
- "Keys directory doesn't exists: $homedir");
- if (!is_writable($homedir))
- return new enigma_error(enigma_error::INTERNAL,
- "Keys directory isn't writeable: $homedir");
-
- $homedir = $homedir . '/' . $this->user;
-
- // check if user's homedir exists (create it if not) and is readable
- if (!file_exists($homedir))
- mkdir($homedir, 0700);
-
- if (!file_exists($homedir))
- return new enigma_error(enigma_error::INTERNAL,
- "Unable to create keys directory: $homedir");
- if (!is_writable($homedir))
- return new enigma_error(enigma_error::INTERNAL,
- "Unable to write to keys directory: $homedir");
-
- $this->homedir = $homedir;
-
- }
-
- function encrypt($text, $keys)
- {
- }
-
- function decrypt($text, $keys = array())
- {
- }
-
- function sign($text, $key, $passwd, $mode = null)
- {
- }
-
- function verify($struct, $message)
- {
- // use common temp dir
- $temp_dir = $this->rc->config->get('temp_dir');
- $msg_file = tempnam($temp_dir, 'rcmMsg');
- $cert_file = tempnam($temp_dir, 'rcmCert');
-
- $fh = fopen($msg_file, "w");
- if ($struct->mime_id) {
- $message->get_part_body($struct->mime_id, false, 0, $fh);
- }
- else {
- $this->rc->storage->get_raw_body($message->uid, $fh);
- }
- fclose($fh);
-
- // @TODO: use stored certificates
-
- // try with certificate verification
- $sig = openssl_pkcs7_verify($msg_file, 0, $cert_file);
- $validity = true;
-
- if ($sig !== true) {
- // try without certificate verification
- $sig = openssl_pkcs7_verify($msg_file, PKCS7_NOVERIFY, $cert_file);
- $validity = enigma_error::UNVERIFIED;
- }
-
- if ($sig === true) {
- $sig = $this->parse_sig_cert($cert_file, $validity);
- }
- else {
- $errorstr = $this->get_openssl_error();
- $sig = new enigma_error(enigma_error::INTERNAL, $errorstr);
- }
-
- // remove temp files
- @unlink($msg_file);
- @unlink($cert_file);
-
- return $sig;
- }
-
- public function import($content, $isfile=false)
- {
- }
-
- public function export($key, $with_private = false)
- {
- }
-
- public function list_keys($pattern='')
- {
- }
-
- public function get_key($keyid)
- {
- }
-
- public function gen_key($data)
- {
- }
-
- public function delete_key($keyid)
- {
- }
-
- public function delete_privkey($keyid)
- {
- }
-
- public function delete_pubkey($keyid)
- {
- }
-
- /**
- * Converts Crypt_GPG_Key object into Enigma's key object
- *
- * @param Crypt_GPG_Key Key object
- *
- * @return enigma_key Key object
- */
- private function parse_key($key)
- {
- /*
- $ekey = new enigma_key();
-
- foreach ($key->getUserIds() as $idx => $user) {
- $id = new enigma_userid();
- $id->name = $user->getName();
- $id->comment = $user->getComment();
- $id->email = $user->getEmail();
- $id->valid = $user->isValid();
- $id->revoked = $user->isRevoked();
-
- $ekey->users[$idx] = $id;
- }
-
- $ekey->name = trim($ekey->users[0]->name . ' <' . $ekey->users[0]->email . '>');
-
- foreach ($key->getSubKeys() as $idx => $subkey) {
- $skey = new enigma_subkey();
- $skey->id = $subkey->getId();
- $skey->revoked = $subkey->isRevoked();
- $skey->created = $subkey->getCreationDate();
- $skey->expires = $subkey->getExpirationDate();
- $skey->fingerprint = $subkey->getFingerprint();
- $skey->has_private = $subkey->hasPrivate();
-
- $ekey->subkeys[$idx] = $skey;
- };
-
- $ekey->id = $ekey->subkeys[0]->id;
-
- return $ekey;
- */
- }
-
- private function get_openssl_error()
- {
- $tmp = array();
- while ($errorstr = openssl_error_string()) {
- $tmp[] = $errorstr;
- }
-
- return join("\n", array_values($tmp));
- }
-
- private function parse_sig_cert($file, $validity)
- {
- $cert = openssl_x509_parse(file_get_contents($file));
-
- if (empty($cert) || empty($cert['subject'])) {
- $errorstr = $this->get_openssl_error();
- return new enigma_error(enigma_error::INTERNAL, $errorstr);
- }
-
- $data = new enigma_signature();
-
- $data->id = $cert['hash']; //?
- $data->valid = $validity;
- $data->fingerprint = $cert['serialNumber'];
- $data->created = $cert['validFrom_time_t'];
- $data->expires = $cert['validTo_time_t'];
- $data->name = $cert['subject']['CN'];
- // $data->comment = '';
- $data->email = $cert['subject']['emailAddress'];
-
- return $data;
- }
-
- }
|