Overview

Packages

  • IMP

Classes

  • IMP
  • IMP_Ajax_Addresses
  • IMP_Ajax_Application
  • IMP_Ajax_Application_Compose
  • IMP_Ajax_Application_Handler_Common
  • IMP_Ajax_Application_Handler_ComposeAttach
  • IMP_Ajax_Application_Handler_Draft
  • IMP_Ajax_Application_Handler_Dynamic
  • IMP_Ajax_Application_Handler_ImageUnblock
  • IMP_Ajax_Application_Handler_Mboxtoggle
  • IMP_Ajax_Application_Handler_Passphrase
  • IMP_Ajax_Application_Handler_Remote
  • IMP_Ajax_Application_Handler_RemotePrefs
  • IMP_Ajax_Application_Handler_Search
  • IMP_Ajax_Application_Handler_Smartmobile
  • IMP_Ajax_Application_ListMessages
  • IMP_Ajax_Application_ShowMessage
  • IMP_Ajax_Application_Viewport
  • IMP_Ajax_Application_Viewport_Error
  • IMP_Ajax_Imple_ImportEncryptKey
  • IMP_Ajax_Imple_ItipRequest
  • IMP_Ajax_Imple_PassphraseDialog
  • IMP_Ajax_Imple_VcardImport
  • IMP_Ajax_Queue
  • IMP_Api
  • IMP_Application
  • IMP_Auth
  • IMP_Basic_Base
  • IMP_Basic_Compose
  • IMP_Basic_Contacts
  • IMP_Basic_Error
  • IMP_Basic_Folders
  • IMP_Basic_Listinfo
  • IMP_Basic_Mailbox
  • IMP_Basic_Message
  • IMP_Basic_Pgp
  • IMP_Basic_Saveimage
  • IMP_Basic_Search
  • IMP_Basic_Searchbasic
  • IMP_Basic_Smime
  • IMP_Basic_Thread
  • IMP_Block_Newmail
  • IMP_Block_Summary
  • IMP_Compose
  • IMP_Compose_Attachment
  • IMP_Compose_Attachment_Linked_Metadata
  • IMP_Compose_Attachment_Metadata
  • IMP_Compose_Attachment_Storage
  • IMP_Compose_Attachment_Storage_AutoDetermine
  • IMP_Compose_Attachment_Storage_Temp
  • IMP_Compose_Attachment_Storage_VfsLinked
  • IMP_Compose_Exception
  • IMP_Compose_Exception_Address
  • IMP_Compose_HtmlSignature
  • IMP_Compose_Link
  • IMP_Compose_LinkedAttachment
  • IMP_Compose_Ui
  • IMP_Compose_View
  • IMP_Contacts
  • IMP_Contacts_Avatar_Addressbook
  • IMP_Contacts_Avatar_Gravatar
  • IMP_Contacts_Avatar_Unknown
  • IMP_Contacts_Flag_Host
  • IMP_Contacts_Image
  • IMP_Contents
  • IMP_Contents_InlineOutput
  • IMP_Contents_View
  • IMP_Crypt_Pgp
  • IMP_Crypt_Smime
  • IMP_Dynamic_AddressList
  • IMP_Dynamic_Base
  • IMP_Dynamic_Compose
  • IMP_Dynamic_Compose_Common
  • IMP_Dynamic_Helper_Base
  • IMP_Dynamic_Mailbox
  • IMP_Dynamic_Message
  • IMP_Exception
  • IMP_Factory_AuthImap
  • IMP_Factory_Compose
  • IMP_Factory_ComposeAtc
  • IMP_Factory_Contacts
  • IMP_Factory_Contents
  • IMP_Factory_Flags
  • IMP_Factory_Ftree
  • IMP_Factory_Identity
  • IMP_Factory_Imap
  • IMP_Factory_Mail
  • IMP_Factory_MailAutoconfig
  • IMP_Factory_Mailbox
  • IMP_Factory_MailboxCache
  • IMP_Factory_MailboxList
  • IMP_Factory_Maillog
  • IMP_Factory_MimeViewer
  • IMP_Factory_Pgp
  • IMP_Factory_PrefsSort
  • IMP_Factory_Quota
  • IMP_Factory_Search
  • IMP_Factory_Sentmail
  • IMP_Factory_Smime
  • IMP_Factory_Spam
  • IMP_Filter
  • IMP_Flag_Base
  • IMP_Flag_Imap
  • IMP_Flag_Imap_Answered
  • IMP_Flag_Imap_Deleted
  • IMP_Flag_Imap_Draft
  • IMP_Flag_Imap_Flagged
  • IMP_Flag_Imap_Forwarded
  • IMP_Flag_Imap_Junk
  • IMP_Flag_Imap_NotJunk
  • IMP_Flag_Imap_Seen
  • IMP_Flag_System_Attachment
  • IMP_Flag_System_Encrypted
  • IMP_Flag_System_HighPriority
  • IMP_Flag_System_List
  • IMP_Flag_System_LowPriority
  • IMP_Flag_System_Match_Address
  • IMP_Flag_System_Match_Flag
  • IMP_Flag_System_Match_Header
  • IMP_Flag_System_Personal
  • IMP_Flag_System_Signed
  • IMP_Flag_System_Unseen
  • IMP_Flag_User
  • IMP_Flags
  • IMP_Ftree
  • IMP_Ftree_Account
  • IMP_Ftree_Account_Imap
  • IMP_Ftree_Account_Inboxonly
  • IMP_Ftree_Account_Remote
  • IMP_Ftree_Account_Vfolder
  • IMP_Ftree_Element
  • IMP_Ftree_Eltdiff
  • IMP_Ftree_Iterator
  • IMP_Ftree_Iterator_Ancestors
  • IMP_Ftree_IteratorFilter
  • IMP_Ftree_IteratorFilter_Children
  • IMP_Ftree_IteratorFilter_Containers
  • IMP_Ftree_IteratorFilter_Expanded
  • IMP_Ftree_IteratorFilter_Invisible
  • IMP_Ftree_IteratorFilter_Mailboxes
  • IMP_Ftree_IteratorFilter_Nonimap
  • IMP_Ftree_IteratorFilter_Polled
  • IMP_Ftree_IteratorFilter_Remote
  • IMP_Ftree_IteratorFilter_Special
  • IMP_Ftree_IteratorFilter_Subscribed
  • IMP_Ftree_IteratorFilter_Vfolder
  • IMP_Ftree_Prefs
  • IMP_Ftree_Prefs_Expanded
  • IMP_Ftree_Prefs_Poll
  • IMP_Ftree_Select
  • IMP_Images
  • IMP_Imap
  • IMP_Imap_Acl
  • IMP_Imap_Cache_Wrapper
  • IMP_Imap_Config
  • IMP_Imap_Exception
  • IMP_Imap_Password
  • IMP_Imap_PermanentFlags
  • IMP_Imap_Remote
  • IMP_Indices
  • IMP_Indices_Mailbox
  • IMP_LoginTasks_SystemTask_GarbageCollection
  • IMP_LoginTasks_SystemTask_Upgrade
  • IMP_LoginTasks_SystemTask_UpgradeAuth
  • IMP_LoginTasks_Task_Autocreate
  • IMP_LoginTasks_Task_DeleteAttachmentsMonthly
  • IMP_LoginTasks_Task_DeleteSentmailMonthly
  • IMP_LoginTasks_Task_FilterOnLogin
  • IMP_LoginTasks_Task_PurgeSentmail
  • IMP_LoginTasks_Task_PurgeSpam
  • IMP_LoginTasks_Task_PurgeTrash
  • IMP_LoginTasks_Task_RecoverDraft
  • IMP_LoginTasks_Task_RenameSentmailMonthly
  • IMP_Mailbox
  • IMP_Mailbox_List
  • IMP_Mailbox_List_Pop3
  • IMP_Mailbox_List_Thread
  • IMP_Mailbox_List_Virtual
  • IMP_Mailbox_SessionCache
  • IMP_Mailbox_Ui
  • IMP_Maillog
  • IMP_Maillog_Log_Base
  • IMP_Maillog_Log_Forward
  • IMP_Maillog_Log_Mdn
  • IMP_Maillog_Log_Redirect
  • IMP_Maillog_Log_Reply
  • IMP_Maillog_Log_Replyall
  • IMP_Maillog_Log_Replylist
  • IMP_Maillog_Message
  • IMP_Maillog_Storage_Base
  • IMP_Maillog_Storage_Composite
  • IMP_Maillog_Storage_History
  • IMP_Maillog_Storage_Mdnsent
  • IMP_Maillog_Storage_Null
  • IMP_Mbox_Generate
  • IMP_Mbox_Import
  • IMP_Mbox_Size
  • IMP_Message
  • IMP_Message_Date
  • IMP_Message_Ui
  • IMP_Mime_Headers
  • IMP_Mime_Status
  • IMP_Mime_Status_RenderIssue
  • IMP_Mime_Status_RenderIssue_Display
  • IMP_Mime_Viewer_Alternative
  • IMP_Mime_Viewer_Appledouble
  • IMP_Mime_Viewer_Audio
  • IMP_Mime_Viewer_Enriched
  • IMP_Mime_Viewer_Externalbody
  • IMP_Mime_Viewer_Html
  • IMP_Mime_Viewer_Images
  • IMP_Mime_Viewer_Itip
  • IMP_Mime_Viewer_Mdn
  • IMP_Mime_Viewer_Partial
  • IMP_Mime_Viewer_Pdf
  • IMP_Mime_Viewer_Pgp
  • IMP_Mime_Viewer_Plain
  • IMP_Mime_Viewer_Related
  • IMP_Mime_Viewer_Rfc822
  • IMP_Mime_Viewer_Smil
  • IMP_Mime_Viewer_Smime
  • IMP_Mime_Viewer_Status
  • IMP_Mime_Viewer_Vcard
  • IMP_Mime_Viewer_Video
  • IMP_Mime_Viewer_Zip
  • IMP_Minimal_Base
  • IMP_Minimal_Compose
  • IMP_Minimal_Error
  • IMP_Minimal_Folders
  • IMP_Minimal_Mailbox
  • IMP_Minimal_Message
  • IMP_Minimal_Messagepart
  • IMP_Minimal_Search
  • IMP_Notification_Event_Status
  • IMP_Notification_Handler_Decorator_ImapAlerts
  • IMP_Notification_Handler_Decorator_NewmailNotify
  • IMP_Perms
  • IMP_Prefs_AttribText
  • IMP_Prefs_Identity
  • IMP_Prefs_Sort
  • IMP_Prefs_Sort_FixedDate
  • IMP_Prefs_Sort_None
  • IMP_Prefs_Sort_Sortpref
  • IMP_Prefs_Sort_Sortpref_Locked
  • IMP_Prefs_Special_Acl
  • IMP_Prefs_Special_ComposeTemplates
  • IMP_Prefs_Special_Drafts
  • IMP_Prefs_Special_Encrypt
  • IMP_Prefs_Special_Flag
  • IMP_Prefs_Special_HtmlSignature
  • IMP_Prefs_Special_ImageReplacement
  • IMP_Prefs_Special_InitialPage
  • IMP_Prefs_Special_Mailto
  • IMP_Prefs_Special_NewmailSound
  • IMP_Prefs_Special_PgpPrivateKey
  • IMP_Prefs_Special_PgpPublicKey
  • IMP_Prefs_Special_Remote
  • IMP_Prefs_Special_Searches
  • IMP_Prefs_Special_Sentmail
  • IMP_Prefs_Special_SmimePrivateKey
  • IMP_Prefs_Special_SmimePublicKey
  • IMP_Prefs_Special_Sourceselect
  • IMP_Prefs_Special_Spam
  • IMP_Prefs_Special_SpecialMboxes
  • IMP_Prefs_Special_Trash
  • IMP_Quota
  • IMP_Quota_Hook
  • IMP_Quota_Imap
  • IMP_Quota_Null
  • IMP_Quota_Ui
  • IMP_Remote
  • IMP_Remote_Account
  • IMP_Script_Package_Autocomplete
  • IMP_Script_Package_ComposeBase
  • IMP_Script_Package_DynamicBase
  • IMP_Script_Package_Editor
  • IMP_Script_Package_Imp
  • IMP_Search
  • IMP_Search_Element
  • IMP_Search_Element_Attachment
  • IMP_Search_Element_Autogenerated
  • IMP_Search_Element_Bulk
  • IMP_Search_Element_Contacts
  • IMP_Search_Element_Daterange
  • IMP_Search_Element_Flag
  • IMP_Search_Element_Header
  • IMP_Search_Element_Mailinglist
  • IMP_Search_Element_Or
  • IMP_Search_Element_Personal
  • IMP_Search_Element_Recipient
  • IMP_Search_Element_Size
  • IMP_Search_Element_Text
  • IMP_Search_Element_Within
  • IMP_Search_Filter
  • IMP_Search_Filter_Attachment
  • IMP_Search_Filter_Autogenerated
  • IMP_Search_Filter_Builtin
  • IMP_Search_Filter_Bulk
  • IMP_Search_Filter_Contacts
  • IMP_Search_Filter_Mailinglist
  • IMP_Search_Filter_Personal
  • IMP_Search_IteratorFilter
  • IMP_Search_Query
  • IMP_Search_Ui
  • IMP_Search_Vfolder
  • IMP_Search_Vfolder_Builtin
  • IMP_Search_Vfolder_Vinbox
  • IMP_Search_Vfolder_Vtrash
  • IMP_Sentmail
  • IMP_Sentmail_Mongo
  • IMP_Sentmail_Null
  • IMP_Sentmail_Sql
  • IMP_Smartmobile
  • IMP_Spam
  • IMP_Spam_Email
  • IMP_Spam_Null
  • IMP_Spam_Program
  • IMP_Test
  • IMP_Tree_Flist
  • IMP_Tree_Jquerymobile
  • IMP_Tree_Simplehtml
  • IMP_View_Subinfo

Interfaces

  • IMP_Compose_Attachment_Linked
  • IMP_Contacts_Avatar_Backend
  • IMP_Contacts_Flag_Backend
  • IMP_Spam_Base
  • Overview
  • Package
  • Class
  • Tree
  1: <?php
  2: /**
  3:  * Copyright 2002-2014 Horde LLC (http://www.horde.org/)
  4:  *
  5:  * See the enclosed file COPYING for license information (GPL). If you
  6:  * did not receive this file, see http://www.horde.org/licenses/gpl.
  7:  *
  8:  * @category  Horde
  9:  * @copyright 2002-2014 Horde LLC
 10:  * @license   http://www.horde.org/licenses/gpl GPL
 11:  * @package   IMP
 12:  */
 13: 
 14: /**
 15:  * Renderer to allow viewing/decrypting of PGP formatted messages (RFC 3156).
 16:  *
 17:  * This class handles the following MIME types:
 18:  *   - application/pgp-encrypted (in multipart/encrypted part)
 19:  *   - application/pgp-keys
 20:  *   - application/pgp-signature (in multipart/signed part)
 21:  *
 22:  * This driver may add the following parameters to the URL:
 23:  *   - pgp_verify_msg: (boolean) Do verification of PGP signed data?
 24:  *   - pgp_view_key: (boolean) View PGP key details?
 25:  *
 26:  * @author    Michael Slusarz <slusarz@horde.org>
 27:  * @category  Horde
 28:  * @copyright 2002-2014 Horde LLC
 29:  * @license   http://www.horde.org/licenses/gpl GPL
 30:  * @package   IMP
 31:  */
 32: class IMP_Mime_Viewer_Pgp extends Horde_Mime_Viewer_Base
 33: {
 34:     /* Metadata constants. */
 35:     const PGP_SIGN_ENC = 'imp-pgp-signed-encrypted';
 36: 
 37:     /**
 38:      * This driver's display capabilities.
 39:      *
 40:      * @var array
 41:      */
 42:     protected $_capability = array(
 43:         'full' => false,
 44:         'info' => false,
 45:         'inline' => true,
 46:         /* This driver *does* render raw data, but only for
 47:          * application/pgp-signature parts that have been processed by the
 48:          * text/plain driver and for displaying raw pgp keys. Altering this
 49:          * value is handled via the canRender() function. */
 50:         'raw' => false
 51:     );
 52: 
 53:     /**
 54:      * Metadata for the current viewer/data.
 55:      *
 56:      * @var array
 57:      */
 58:     protected $_metadata = array(
 59:         'compressed' => false,
 60:         'embedded' => true,
 61:         'forceinline' => true
 62:     );
 63: 
 64:     /**
 65:      * The address of the sender.
 66:      *
 67:      * @var Horde_Mail_Rfc822_Address
 68:      */
 69:     protected $_sender = null;
 70: 
 71:     /**
 72:      * Return the full rendered version of the Horde_Mime_Part object.
 73:      *
 74:      * @return array  See parent::render().
 75:      */
 76:     protected function _render()
 77:     {
 78:         switch ($this->_mimepart->getType()) {
 79:         case 'application/pgp-keys':
 80:             $vars = $GLOBALS['injector']->getInstance('Horde_Variables');
 81:             if ($vars->pgp_view_key) {
 82:                 // Throws exception on error.
 83:                 return array(
 84:                     $this->_mimepart->getMimeId() => array(
 85:                         'data' => '<html><body><tt>' . nl2br(str_replace(' ', '&nbsp;', $GLOBALS['injector']->getInstance('IMP_Crypt_Pgp')->pgpPrettyKey($this->_mimepart->getContents()))) . '</tt></body></html>',
 86:                         'type' => 'text/html; charset=' . $this->getConfigParam('charset')
 87:                     )
 88:                 );
 89:             }
 90: 
 91:             return array(
 92:                 $this->_mimepart->getMimeId() => array(
 93:                     'data' => $this->_mimepart->getContents(),
 94:                     'type' => 'text/plain; charset=' . $this->_mimepart->getCharset()
 95:                 )
 96:             );
 97:         }
 98:     }
 99: 
100:     /**
101:      * Return the full rendered version of the Horde_Mime_Part object.
102:      *
103:      * @return array  See parent::render().
104:      */
105:     protected function _renderRaw()
106:     {
107:         $ret = array(
108:             'data' => '',
109:             'type' => 'text/plain; charset=' . $this->getConfigParam('charset')
110:         );
111: 
112:         switch ($this->_mimepart->getType()) {
113:         case 'application/pgp-signature':
114:             $parts = $GLOBALS['injector']->getInstance('IMP_Crypt_Pgp_Parse')->parse($this->_mimepart->getContents());
115:             foreach (array_keys($parts) as $key) {
116:                 if ($parts[$key]['type'] == Horde_Crypt_Pgp::ARMOR_SIGNATURE) {
117:                     $ret['data'] = implode("\r\n", $parts[$key]['data']);
118:                     break;
119:                 }
120:             }
121:             break;
122:         }
123: 
124:         return array(
125:             $this->_mimepart->getMimeId() => $ret
126:         );
127:     }
128: 
129:     /**
130:      * Return the rendered inline version of the Horde_Mime_Part object.
131:      *
132:      * @return array  See parent::render().
133:      */
134:     protected function _renderInline()
135:     {
136:         $id = $this->_mimepart->getMimeId();
137: 
138:         switch ($this->_mimepart->getType()) {
139:         case 'application/pgp-keys':
140:             return $this->_outputPGPKey();
141: 
142:         case 'multipart/signed':
143:             return $this->_outputPGPSigned();
144: 
145:         case 'multipart/encrypted':
146:             $cache = $this->getConfigParam('imp_contents')->getViewCache();
147: 
148:             if (isset($cache->pgp[$id])) {
149:                 return array_merge(array(
150:                     $id => array(
151:                         'data' => null,
152:                         'status' => $cache->pgp[$id]['status'],
153:                         'type' => 'text/plain; charset=' . $this->getConfigParam('charset'),
154:                         'wrap' => $cache->pgp[$id]['wrap']
155:                     )
156:                 ), $cache->pgp[$id]['other']);
157:             }
158:             // Fall-through
159: 
160:         case 'application/pgp-encrypted':
161:         case 'application/pgp-signature':
162:         default:
163:             return array();
164:         }
165:     }
166: 
167:     /**
168:      * If this MIME part can contain embedded MIME part(s), and those part(s)
169:      * exist, return a representation of that data.
170:      *
171:      * @return mixed  A Horde_Mime_Part object representing the embedded data.
172:      *                Returns null if no embedded MIME part(s) exist.
173:      */
174:     protected function _getEmbeddedMimeParts()
175:     {
176:         if ($this->_mimepart->getType() != 'multipart/encrypted') {
177:             return null;
178:         }
179: 
180:         $partlist = array_keys($this->_mimepart->contentTypeMap());
181:         $base_id = reset($partlist);
182:         $version_id = next($partlist);
183: 
184:         $id_ob = new Horde_Mime_Id($version_id);
185:         $data_id = $id_ob->idArithmetic($id_ob::ID_NEXT);
186: 
187:         $status = new IMP_Mime_Status();
188:         $status->icon('mime/encryption.png', 'PGP');
189: 
190:         $cache = $this->getConfigParam('imp_contents')->getViewCache();
191:         $cache->pgp[$base_id] = array(
192:             'status' => array($status),
193:             'other' => array(
194:                 $version_id => null,
195:                 $data_id => null
196:             ),
197:             'wrap' => ''
198:         );
199: 
200:         /* Is PGP active? */
201:         if (empty($GLOBALS['conf']['gnupg']['path']) ||
202:             !$GLOBALS['prefs']->getValue('use_pgp')) {
203:             $status->addText(_("The data in this part has been encrypted via PGP, however, PGP support is disabled so the message cannot be decrypted."));
204:             return null;
205:         }
206: 
207:         /* PGP version information appears in the first MIME subpart. We
208:          * don't currently need to do anything with this information. The
209:          * encrypted data appears in the second MIME subpart. */
210:         $encrypted_part = $this->getConfigParam('imp_contents')->getMIMEPart($data_id);
211:         $encrypted_data = $encrypted_part->getContents();
212: 
213:         $symmetric_pass = $personal_pass = null;
214: 
215:         /* Check if this a symmetrically encrypted message. */
216:         try {
217:             $imp_pgp = $GLOBALS['injector']->getInstance('IMP_Crypt_Pgp');
218:             $symmetric = $imp_pgp->encryptedSymmetrically($encrypted_data);
219:             if ($symmetric) {
220:                 $symmetric_id = $this->_getSymmetricID();
221:                 $symmetric_pass = $imp_pgp->getPassphrase('symmetric', $symmetric_id);
222: 
223:                 if (is_null($symmetric_pass)) {
224:                     $status->addText(_("The data in this part has been encrypted via PGP."));
225: 
226:                     /* Ask for the correct passphrase if this is encrypted
227:                      * symmetrically. */
228:                     $imple = $GLOBALS['injector']->getInstance('Horde_Core_Factory_Imple')->create('IMP_Ajax_Imple_PassphraseDialog', array(
229:                         'params' => array(
230:                             'symmetricid' => $symmetric_id
231:                         ),
232:                         'type' => 'pgpSymmetric'
233:                     ));
234:                     $status->addText(Horde::link('#', '', '', '', '', '', '', array('id' => $imple->getDomId())) . _("You must enter the passphrase used to encrypt this message to view it.") . '</a>');
235:                     return null;
236:                 }
237:             }
238:         } catch (Horde_Exception $e) {
239:             Horde::log($e, 'INFO');
240:             return null;
241:         }
242: 
243:         /* Check if this is a literal compressed message. */
244:         try {
245:             $info = $imp_pgp->pgpPacketInformation($encrypted_data);
246:         } catch (Horde_Exception $e) {
247:             Horde::log($e, 'INFO');
248:             return null;
249:         }
250: 
251:         $literal = !empty($info['literal']);
252:         if ($literal) {
253:             $status->addText(_("The data in this part has been compressed via PGP."));
254:         } else {
255:             $status->addText(_("The data in this part has been encrypted via PGP."));
256: 
257:             if (!$symmetric) {
258:                 if ($imp_pgp->getPersonalPrivateKey()) {
259:                     $personal_pass = $imp_pgp->getPassphrase('personal');
260:                     if (is_null($personal_pass)) {
261:                         /* Ask for the private key's passphrase if this is
262:                          * encrypted asymmetrically. */
263:                         $imple = $GLOBALS['injector']->getInstance('Horde_Core_Factory_Imple')->create('IMP_Ajax_Imple_PassphraseDialog', array(
264:                             'type' => 'pgpPersonal'
265:                         ));
266:                         $status->addText(Horde::link('#', '', '', '', '', '', '', array('id' => $imple->getDomId())) . _("You must enter the passphrase for your PGP private key to view this message.") . '</a>');
267:                         return null;
268:                     }
269:                 } else {
270:                     /* Output if there is no personal private key to decrypt
271:                      * with. */
272:                     $status->addText(_("However, no personal private key exists so the message cannot be decrypted."));
273:                     return null;
274:                 }
275:             }
276:         }
277: 
278:         try {
279:             if (!is_null($symmetric_pass)) {
280:                 $decrypted_data = $imp_pgp->decryptMessage($encrypted_data, 'symmetric', array(
281:                     'passphrase' => $symmetric_pass,
282:                     'sender' => $this->_getSender()->bare_address
283:                 ));
284:             } elseif (!is_null($personal_pass)) {
285:                 $decrypted_data = $imp_pgp->decryptMessage($encrypted_data, 'personal', array(
286:                     'passphrase' => $personal_pass,
287:                     'sender' => $this->_getSender()->bare_address
288:                 ));
289:             } else {
290:                 $decrypted_data = $imp_pgp->decryptMessage($encrypted_data, 'literal');
291:             }
292:         } catch (Horde_Exception $e) {
293:             $status->addText(_("The data in this part does not appear to be a valid PGP encrypted message. Error: ") . $e->getMessage());
294:             if (!is_null($symmetric_pass)) {
295:                 $imp_pgp->unsetPassphrase('symmetric', $this->_getSymmetricID());
296:                 return $this->_getEmbeddedMimeParts();
297:             }
298:             return null;
299:         }
300: 
301:         $cache->pgp[$base_id]['wrap'] = 'mimePartWrapValid';
302: 
303:         /* Check for combined encryption/signature data. */
304:         if ($decrypted_data->result) {
305:             $sig_text = is_bool($decrypted_data->result)
306:                 ? _("The data in this part has been digitally signed via PGP.")
307:                 : $this->_textFilter($decrypted_data->result, 'text2html', array('parselevel' => Horde_Text_Filter_Text2html::NOHTML));
308: 
309:             $status2 = new IMP_Mime_Status($sig_text);
310:             $status2->action(IMP_Mime_Status::SUCCESS);
311: 
312:             $cache->pgp[$base_id]['status'][] = $status2;
313:         }
314: 
315:         /* Force armor data as text/plain data. */
316:         if ($this->_mimepart->getMetadata(Horde_Crypt_Pgp_Parse::PGP_ARMOR)) {
317:             $decrypted_data->message = "Content-Type: text/plain\n\n" .
318:                                        $decrypted_data->message;
319:         }
320: 
321:         $new_part = Horde_Mime_Part::parseMessage($decrypted_data->message, array(
322:             'forcemime' => true
323:         ));
324: 
325:         if ($new_part->getType() == 'multipart/signed') {
326:             $data = new Horde_Stream_Temp();
327:             try {
328:                 $data->add(Horde_Mime_Part::getRawPartText($decrypted_data->message, 'header', '1'));
329:                 $data->add("\n\n");
330:                 $data->add(Horde_Mime_Part::getRawPartText($decrypted_data->message, 'body', '1'));
331:             } catch (Horde_Mime_Exception $e) {}
332: 
333:             $new_part->setMetadata(self::PGP_SIGN_ENC, $data->stream);
334:             $new_part->setContents($decrypted_data->message, array(
335:                 'encoding' => 'binary'
336:             ));
337:         }
338: 
339:         return $new_part;
340:     }
341: 
342:     /**
343:      * Generates output for 'application/pgp-keys' MIME_Parts.
344:      *
345:      * @return string  The HTML output.
346:      */
347:     protected function _outputPGPKey()
348:     {
349:         /* Is PGP active? */
350:         if (empty($GLOBALS['conf']['gnupg']['path']) ||
351:             !$GLOBALS['prefs']->getValue('use_pgp')) {
352:             return array();
353:         }
354: 
355:         /* Initialize status message. */
356:         $status = new IMP_Mime_Status(_("A PGP Public Key is attached to the message."));
357:         $status->icon('mime/encryption.png', 'PGP');
358: 
359:         $imp_contents = $this->getConfigParam('imp_contents');
360:         $mime_id = $this->_mimepart->getMimeId();
361: 
362:         if ($GLOBALS['prefs']->getValue('use_pgp') &&
363:             $GLOBALS['prefs']->getValue('add_source') &&
364:             $GLOBALS['registry']->hasMethod('contacts/addField')) {
365:             // TODO: Check for key existence.
366:             $imple = $GLOBALS['injector']->getInstance('Horde_Core_Factory_Imple')->create('IMP_Ajax_Imple_ImportEncryptKey', array(
367:                 'mime_id' => $mime_id,
368:                 'muid' => strval($imp_contents->getIndicesOb()),
369:                 'type' => 'pgp'
370:             ));
371:             $status->addText(Horde::link('#', '', '', '', '', '', '', array('id' => $imple->getDomId())) . _("Save the key to your address book.") . '</a>');
372:         }
373:         $status->addText($imp_contents->linkViewJS($this->_mimepart, 'view_attach', _("View key details."), array('params' => array('mode' => IMP_Contents::RENDER_FULL, 'pgp_view_key' => 1))));
374: 
375:         return array(
376:             $mime_id => array(
377:                 'data' => '',
378:                 'status' => $status,
379:                 'type' => 'text/html; charset=' . $this->getConfigParam('charset')
380:             )
381:         );
382:     }
383: 
384:     /**
385:      * Generates HTML output for 'multipart/signed' MIME parts.
386:      *
387:      * @return string  The HTML output.
388:      */
389:     protected function _outputPGPSigned()
390:     {
391:         global $conf, $injector, $prefs, $registry, $session;
392: 
393:         $partlist = array_keys($this->_mimepart->contentTypeMap());
394:         $base_id = reset($partlist);
395:         $signed_id = next($partlist);
396: 
397:         $id_ob = new Horde_Mime_Id($signed_id);
398:         $sig_id = $id_ob->idArithmetic($id_ob::ID_NEXT);
399: 
400:         if (!$prefs->getValue('use_pgp') || empty($conf['gnupg']['path'])) {
401:             return array(
402:                 $sig_id => null
403:             );
404:         }
405: 
406:         $status = new IMP_Mime_Status();
407:         $status->addText(_("The data in this part has been digitally signed via PGP."));
408:         $status->icon('mime/encryption.png', 'PGP');
409: 
410:         $ret = array(
411:             $base_id => array(
412:                 'data' => '',
413:                 'nosummary' => true,
414:                 'status' => array($status),
415:                 'type' => 'text/html; charset=' . $this->getConfigParam('charset'),
416:                 'wrap' => 'mimePartWrap'
417:             ),
418:             $sig_id => null
419:         );
420: 
421:         if ($prefs->getValue('pgp_verify') ||
422:             $injector->getInstance('Horde_Variables')->pgp_verify_msg) {
423:             $imp_contents = $this->getConfigParam('imp_contents');
424:             $sig_part = $imp_contents->getMIMEPart($sig_id);
425: 
426:             $status2 = new IMP_Mime_Status();
427: 
428:             if (!$sig_part) {
429:                 $status2->action(IMP_Mime_Status::ERROR);
430:                 $sig_text = _("This digitally signed message is broken.");
431:                 $ret[$base_id]['wrap'] = 'mimePartWrapInvalid';
432:             } else {
433:                 /* Close session, since this may be a long-running
434:                  * operation. */
435:                 $session->close();
436: 
437:                 try {
438:                     $imp_pgp = $injector->getInstance('IMP_Crypt_Pgp');
439:                     if ($sig_raw = $sig_part->getMetadata(Horde_Crypt_Pgp_Parse::SIG_RAW)) {
440:                         $sig_result = $imp_pgp->verifySignature($sig_raw, $this->_getSender()->bare_address, null, $sig_part->getMetadata(Horde_Crypt_Pgp_Parse::SIG_CHARSET));
441:                     } else {
442:                         $stream = $imp_contents->isEmbedded($signed_id)
443:                             ? $this->_mimepart->getMetadata(self::PGP_SIGN_ENC)
444:                             : $imp_contents->getBodyPart($signed_id, array('mimeheaders' => true, 'stream' => true))->data;
445: 
446:                         rewind($stream);
447:                         stream_filter_register('horde_eol', 'Horde_Stream_Filter_Eol');
448:                         stream_filter_append($stream, 'horde_eol', STREAM_FILTER_READ, array(
449:                             'eol' => Horde_Mime_Part::RFC_EOL
450:                         ));
451: 
452:                         $sig_result = $imp_pgp->verifySignature(stream_get_contents($stream), $this->_getSender()->bare_address, $sig_part->getContents());
453:                     }
454: 
455:                     $status2->action(IMP_Mime_Status::SUCCESS);
456:                     $sig_text = $sig_result->message;
457:                     $ret[$base_id]['wrap'] = 'mimePartWrapValid';
458:                 } catch (Horde_Exception $e) {
459:                     $status2->action(IMP_Mime_Status::ERROR);
460:                     $sig_text = $e->getMessage();
461:                     $ret[$base_id]['wrap'] = 'mimePartWrapInvalid';
462:                 }
463:             }
464: 
465:             $status2->addText($this->_textFilter($sig_text, 'text2html', array(
466:                 'parselevel' => Horde_Text_Filter_Text2html::NOHTML
467:             )));
468:             $ret[$base_id]['status'][] = $status2;
469:         } else {
470:             switch ($registry->getView()) {
471:             case Horde_Registry::VIEW_BASIC:
472:                 $status->addText(Horde::link(Horde::selfUrlParams()->add(array('pgp_verify_msg' => 1))) . _("Click HERE to verify the message.") . '</a>');
473:                 break;
474: 
475:             case Horde_Registry::VIEW_DYNAMIC:
476:                 $status->addText(Horde::link('#', '', 'pgpVerifyMsg') . _("Click HERE to verify the message.") . '</a>');
477:                 break;
478:             }
479:         }
480: 
481:         return $ret;
482:     }
483: 
484:     /**
485:      * Generates the symmetric ID for this message.
486:      *
487:      * @return string  Symmetric ID.
488:      */
489:     protected function _getSymmetricID()
490:     {
491:         return $GLOBALS['injector']->getInstance('IMP_Crypt_Pgp')->getSymmetricID($this->getConfigParam('imp_contents')->getMailbox(), $this->getConfigParam('imp_contents')->getUid(), $this->_mimepart->getMimeId());
492:     }
493: 
494:     /**
495:      * Determine the address of the sender.
496:      *
497:      * @return Horde_Mail_Rfc822_Address  The from address.
498:      */
499:     protected function _getSender()
500:     {
501:         if (is_null($this->_sender)) {
502:             $headers = $this->getConfigParam('imp_contents')->getHeader();
503:             $tmp = $headers->getOb('from');
504:             $this->_sender = $tmp[0];
505:         }
506: 
507:         return $this->_sender;
508:     }
509: 
510:     /**
511:      * Can this driver render the data?
512:      *
513:      * @param string $mode  See parent::canRender().
514:      *
515:      * @return boolean  See parent::canRender().
516:      */
517:     public function canRender($mode)
518:     {
519:         switch ($mode) {
520:         case 'full':
521:             if ($this->_mimepart->getType() == 'application/pgp-keys') {
522:                 return true;
523:             }
524:             break;
525: 
526:         case 'raw':
527:             if (($this->_mimepart->getType() == 'application/pgp-signature') &&
528:                 $this->_mimepart->getMetadata(Horde_Crypt_Pgp_Parse::SIG_RAW)) {
529:                 return true;
530:             }
531:             break;
532:         }
533: 
534:         return parent::canRender($mode);
535:     }
536: 
537: }
538: 
API documentation generated by ApiGen