Always leave password encrypted in Imap object
authorMichael M Slusarz <slusarz@curecanti.org>
Sat, 4 Sep 2010 07:16:59 +0000 (01:16 -0600)
committerMichael M Slusarz <slusarz@curecanti.org>
Mon, 6 Sep 2010 20:31:15 +0000 (14:31 -0600)
framework/Imap_Client/lib/Horde/Imap/Client.php
framework/Imap_Client/lib/Horde/Imap/Client/Base.php
framework/Imap_Client/lib/Horde/Imap/Client/Cclient.php
framework/Imap_Client/lib/Horde/Imap/Client/Socket.php
framework/Imap_Client/lib/Horde/Imap/Client/Socket/Pop3.php
imp/lib/Imap.php

index a6f8fac..83010bd 100644 (file)
@@ -102,7 +102,7 @@ class Horde_Imap_Client
     const DATA_STRING = 8;
 
     /**
-     * The key used to encrypt the password when serializing.
+     * The key used to encrypt the password within the object.
      *
      * @var string
      */
index 1403c77..cc19167 100644 (file)
@@ -104,6 +104,14 @@ abstract class Horde_Imap_Client_Base
             throw new Horde_Imap_Client_Exception('Horde_Imap_Client requires a username and password.');
         }
 
+        // Encrypt password.
+        $key = Horde_Imap_Client::$encryptKey;
+        if (!is_null($key)) {
+            $secret = new Horde_Secret();
+            $params['password'] = $secret->write($key, $params['password']);
+            $params['_passencrypt'] = true;
+        }
+
         // Default values.
         if (empty($params['hostspec'])) {
             $params['hostspec'] = 'localhost';
@@ -158,16 +166,6 @@ abstract class Horde_Imap_Client_Base
         // Don't store Horde_Imap_Client_Cache object or temp data.
         $this->cache = null;
         $this->_temp = array();
-
-        // Encrypt password in serialized object.
-        if (!isset($this->_params['_passencrypt'])) {
-            $key = Horde_Imap_Client::$encryptKey;
-            if (!is_null($key)) {
-                $secret = new Horde_Secret();
-                $this->_params['_passencrypt'] = $secret->write($key, $this->_params['password']);
-                $this->_params['password'] = null;
-            }
-        }
     }
 
     /**
@@ -175,12 +173,6 @@ abstract class Horde_Imap_Client_Base
      */
     public function __wakeup()
     {
-        if (isset($this->_params['_passencrypt']) &&
-            !is_null(Horde_Imap_Client::$encryptKey)) {
-            $secret = new Horde_Secret();
-            $this->_params['password'] = $secret->read(Horde_Imap_Client::$encryptKey, $this->_params['_passencrypt']);
-        }
-
         if (!empty($this->_params['debug'])) {
             $this->_debug = @fopen($this->_params['debug'], 'a');
         }
@@ -245,7 +237,19 @@ abstract class Horde_Imap_Client_Base
      */
     public function getParam($key)
     {
-        return isset($this->_params[$key]) ? $this->_params[$key] : null;
+        /* Passwords may be stored encrypted. */
+        if (($key == 'password') && !empty($this->_params['_passencrypt'])) {
+            if (is_null(Horde_Imap_Client::$encryptKey)) {
+                return null;
+            }
+
+            $secret = new Horde_Secret();
+            return $secret->read(Horde_Imap_Client::$encryptKey, $this->_params['password']);
+        }
+
+        return isset($this->_params[$key])
+            ? $this->_params[$key]
+            : null;
     }
 
     /**
index 462e295..200e30c 100644 (file)
@@ -203,7 +203,7 @@ class Horde_Imap_Client_Cclient extends Horde_Imap_Client_Base
 
         $old_error = error_reporting(0);
         if (version_compare(PHP_VERSION, '5.2.1') != -1) {
-            $res = imap_open($this->_connString(), $this->_params['username'], $this->_params['password'], $mask, $this->_params['retries']);
+            $res = imap_open($this->_connString(), $this->_params['username'], $this->getParam('password'), $mask, $this->_params['retries']);
         } else {
             while (($res === false) &&
                    !strstr(strtolower(imap_last_error()), 'login failure') &&
@@ -211,7 +211,7 @@ class Horde_Imap_Client_Cclient extends Horde_Imap_Client_Base
                 if ($i != 0) {
                     sleep(1);
                 }
-                $res = imap_open($this->_connString(), $this->_params['username'], $this->_params['password'], $mask);
+                $res = imap_open($this->_connString(), $this->_params['username'], $this->getParam('password'), $mask);
             }
         }
         error_reporting($old_error);
index 8d38704..a37ddb0 100644 (file)
@@ -535,7 +535,7 @@ class Horde_Imap_Client_Socket extends Horde_Imap_Client_Base
                     throw new Horde_Imap_Client_Exception('The Auth_SASL package is required for CRAM-MD5 authentication');
                 }
                 $auth_sasl = Auth_SASL::factory('crammd5');
-                $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->_params['password'], base64_decode($ob['line'])));
+                $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->getParam('password'), base64_decode($ob['line'])));
                 $this->_sendLine($response, array(
                     'debug' => '[CRAM-MD5 Response]',
                     'notag' => true
@@ -547,7 +547,7 @@ class Horde_Imap_Client_Socket extends Horde_Imap_Client_Base
                     throw new Horde_Imap_Client_Exception('The Auth_SASL package is required for DIGEST-MD5 authentication');
                 }
                 $auth_sasl = Auth_SASL::factory('digestmd5');
-                $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->_params['password'], base64_decode($ob['line']), $this->_params['hostspec'], 'imap'));
+                $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->getParam('password'), base64_decode($ob['line']), $this->_params['hostspec'], 'imap'));
                 $ob = $this->_sendLine($response, array(
                     'debug' => '[DIGEST-MD5 Response]',
                     'noparse' => true,
@@ -568,7 +568,7 @@ class Horde_Imap_Client_Socket extends Horde_Imap_Client_Base
             $this->_sendLine(array(
                 'LOGIN',
                 array('t' => Horde_Imap_Client::DATA_ASTRING, 'v' => $this->_params['username']),
-                array('t' => Horde_Imap_Client::DATA_ASTRING, 'v' => $this->_params['password'])
+                array('t' => Horde_Imap_Client::DATA_ASTRING, 'v' => $this->getParam('password'))
             ), array(
                 'debug' => sprintf('[LOGIN Command - username: %s]', $this->_params['username'])
             ));
@@ -576,7 +576,7 @@ class Horde_Imap_Client_Socket extends Horde_Imap_Client_Base
 
         case 'PLAIN':
             // RFC 2595/4616 - PLAIN SASL mechanism
-            $auth = base64_encode(implode("\0", array($this->_params['username'], $this->_params['username'], $this->_params['password'])));
+            $auth = base64_encode(implode("\0", array($this->_params['username'], $this->_params['username'], $this->getParam('password'))));
             if ($this->queryCapability('SASL-IR')) {
                 // IMAP Extension for SASL Initial Client Response (RFC 4959)
                 $this->_sendLine(array(
index 076fe2d..cafec7c 100644 (file)
@@ -316,7 +316,7 @@ class Horde_Imap_Client_Socket_Pop3 extends Horde_Imap_Client_Base
             $challenge = $this->_sendLine('AUTH CRAM-MD5');
 
             $auth_sasl = Auth_SASL::factory('crammd5');
-            $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->_params['password'], base64_decode(substr($challenge['line'], 2))));
+            $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->getParam('password'), base64_decode(substr($challenge['line'], 2))));
             $this->_sendLine($response, array('debug' => '[CRAM-MD5 Response]'));
             break;
 
@@ -329,7 +329,7 @@ class Horde_Imap_Client_Socket_Pop3 extends Horde_Imap_Client_Base
             $challenge = $this->_sendLine('AUTH DIGEST-MD5');
 
             $auth_sasl = Auth_SASL::factory('digestmd5');
-            $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->_params['password'], base64_decode(substr($challenge['line'], 2)), $this->_params['hostspec'], 'pop3'));
+            $response = base64_encode($auth_sasl->getResponse($this->_params['username'], $this->getParam('password'), base64_decode(substr($challenge['line'], 2)), $this->_params['hostspec'], 'pop3'));
 
             $sresponse = $this->_sendLine($response, array('debug' => '[DIGEST-MD5 Response]'));
             if (stripos(base64_decode(substr($sresponse['line'], 2)), 'rspauth=') === false) {
@@ -344,12 +344,12 @@ class Horde_Imap_Client_Socket_Pop3 extends Horde_Imap_Client_Base
             // RFC 5034
             $this->_sendLine('AUTH LOGIN');
             $this->_sendLine(base64_encode($this->_params['username']));
-            $this->_sendLine(base64_encode($this->_params['password']));
+            $this->_sendLine(base64_encode($this->getParam('password')));
             break;
 
         case 'PLAIN':
             // RFC 5034
-            $this->_sendLine('AUTH PLAIN ' . base64_encode(chr(0) . $this->_params['username'] . chr(0) . $this->_params['password']));
+            $this->_sendLine('AUTH PLAIN ' . base64_encode(chr(0) . $this->_params['username'] . chr(0) . $this->getParam('password')));
             break;
 
         case 'APOP':
@@ -360,7 +360,7 @@ class Horde_Imap_Client_Socket_Pop3 extends Horde_Imap_Client_Base
         case 'USER':
             // RFC 1939 [7]
             $this->_sendLine('USER ' . $this->_params['username']);
-            $this->_sendLine('PASS ' . $this->_params['password']);
+            $this->_sendLine('PASS ' . $this->getParam('password'));
             break;
         }
     }
index b9f34ed..8ebb948 100644 (file)
@@ -64,6 +64,9 @@ class IMP_Imap
         /* Register the logging callback. */
         Horde_Imap_Client_Exception::$logCallback = array($this, 'logException');
 
+        /* Set the encryption key. */
+        Horde_Imap_Client::$encryptKey = $GLOBALS['injector']->getInstance('Horde_Secret')->getKey('imp');
+
         /* Rebuild the Horde_Imap_Client object. */
         $this->_loadImapObject();
 
@@ -98,8 +101,6 @@ class IMP_Imap
             return false;
         }
 
-        Horde_Imap_Client::$encryptKey = $GLOBALS['injector']->getInstance('Horde_Secret')->getKey('imp');
-
         $this->ob = @unserialize($_SESSION['imp']['imap_ob'][$this->_serverkey]);
         if (empty($this->ob)) {
             /* Throw fatal error here - should never reach here and if we