Mercurial > hg > rc1
comparison vendor/pear/net_sieve/Sieve.php @ 35:05c4c32948af
.hgignore: add vendor tree
composer.json: new packages
plugins/thunderbird_labels/thunderbird_labels.php: change hook and RFC822 use wrt whitelisting to avoid deprecated stuff
index.php: commented debugging hooks
others: new releases of vendor packages?
author | Charlie Root |
---|---|
date | Thu, 30 Aug 2018 16:21:59 -0400 |
parents | 1e000243b222 |
children |
comparison
equal
deleted
inserted
replaced
34:50ac5484d514 | 35:05c4c32948af |
---|---|
44 | 44 |
45 require_once 'PEAR.php'; | 45 require_once 'PEAR.php'; |
46 require_once 'Net/Socket.php'; | 46 require_once 'Net/Socket.php'; |
47 | 47 |
48 /** | 48 /** |
49 * TODO | 49 * Disconnected state |
50 * | 50 * |
51 * o supportsAuthMech() | |
52 */ | |
53 | |
54 /** | |
55 * Disconnected state | |
56 * @const NET_SIEVE_STATE_DISCONNECTED | 51 * @const NET_SIEVE_STATE_DISCONNECTED |
57 */ | 52 */ |
58 define('NET_SIEVE_STATE_DISCONNECTED', 1, true); | 53 define('NET_SIEVE_STATE_DISCONNECTED', 1, true); |
59 | 54 |
60 /** | 55 /** |
61 * Authorisation state | 56 * Authorisation state |
57 * | |
62 * @const NET_SIEVE_STATE_AUTHORISATION | 58 * @const NET_SIEVE_STATE_AUTHORISATION |
63 */ | 59 */ |
64 define('NET_SIEVE_STATE_AUTHORISATION', 2, true); | 60 define('NET_SIEVE_STATE_AUTHORISATION', 2, true); |
65 | 61 |
66 /** | 62 /** |
67 * Transaction state | 63 * Transaction state |
64 * | |
68 * @const NET_SIEVE_STATE_TRANSACTION | 65 * @const NET_SIEVE_STATE_TRANSACTION |
69 */ | 66 */ |
70 define('NET_SIEVE_STATE_TRANSACTION', 3, true); | 67 define('NET_SIEVE_STATE_TRANSACTION', 3, true); |
71 | 68 |
72 | 69 |
77 * @package Net_Sieve | 74 * @package Net_Sieve |
78 * @author Richard Heyes <richard@phpguru.org> | 75 * @author Richard Heyes <richard@phpguru.org> |
79 * @author Damian Fernandez Sosa <damlists@cnba.uba.ar> | 76 * @author Damian Fernandez Sosa <damlists@cnba.uba.ar> |
80 * @author Anish Mistry <amistry@am-productions.biz> | 77 * @author Anish Mistry <amistry@am-productions.biz> |
81 * @author Jan Schneider <jan@horde.org> | 78 * @author Jan Schneider <jan@horde.org> |
79 * @author Neil Munday <neil@mundayweb.com> | |
82 * @copyright 2002-2003 Richard Heyes | 80 * @copyright 2002-2003 Richard Heyes |
83 * @copyright 2006-2008 Anish Mistry | 81 * @copyright 2006-2008 Anish Mistry |
84 * @license http://www.opensource.org/licenses/bsd-license.php BSD | 82 * @license http://www.opensource.org/licenses/bsd-license.php BSD |
85 * @version Release: @package_version@ | 83 * @version Release: @package_version@ |
86 * @link http://pear.php.net/package/Net_Sieve | 84 * @link http://pear.php.net/package/Net_Sieve |
101 var $supportedAuthMethods = array( | 99 var $supportedAuthMethods = array( |
102 'DIGEST-MD5', | 100 'DIGEST-MD5', |
103 'CRAM-MD5', | 101 'CRAM-MD5', |
104 'EXTERNAL', | 102 'EXTERNAL', |
105 'PLAIN' , | 103 'PLAIN' , |
106 'LOGIN' | 104 'LOGIN', |
105 'GSSAPI' | |
107 ); | 106 ); |
108 | 107 |
109 /** | 108 /** |
110 * SASL authentication methods that require Auth_SASL. | 109 * SASL authentication methods that require Auth_SASL. |
111 * | 110 * |
191 * Maximum number of referral loops | 190 * Maximum number of referral loops |
192 * | 191 * |
193 * @var array | 192 * @var array |
194 */ | 193 */ |
195 var $_maxReferralCount = 15; | 194 var $_maxReferralCount = 15; |
195 | |
196 /** | |
197 * Kerberos service principal to use for GSSAPI authentication. | |
198 * | |
199 * @var string | |
200 */ | |
201 var $_gssapiPrincipal = null; | |
202 | |
203 /** | |
204 * Kerberos service cname to use for GSSAPI authentication. | |
205 * | |
206 * @var string | |
207 */ | |
208 var $_gssapiCN = null; | |
196 | 209 |
197 /** | 210 /** |
198 * Constructor. | 211 * Constructor. |
199 * | 212 * |
200 * Sets up the object, connects to the server and logs in. Stores any | 213 * Sets up the object, connects to the server and logs in. Stores any |
214 * socket is already open. | 227 * socket is already open. |
215 * @param boolean $useTLS Use TLS if available. | 228 * @param boolean $useTLS Use TLS if available. |
216 * @param array $options Additional options for | 229 * @param array $options Additional options for |
217 * stream_context_create(). | 230 * stream_context_create(). |
218 * @param mixed $handler A callback handler for the debug output. | 231 * @param mixed $handler A callback handler for the debug output. |
232 * @param string $principal Kerberos service principal to use | |
233 * with GSSAPI authentication. | |
234 * @param string $cname Kerberos service cname to use | |
235 * with GSSAPI authentication. | |
219 */ | 236 */ |
220 function __construct($user = null, $pass = null, $host = 'localhost', | 237 function __construct($user = null, $pass = null, $host = 'localhost', |
221 $port = 2000, $logintype = '', $euser = '', | 238 $port = 2000, $logintype = '', $euser = '', |
222 $debug = false, $bypassAuth = false, $useTLS = true, | 239 $debug = false, $bypassAuth = false, $useTLS = true, |
223 $options = null, $handler = null | 240 $options = null, $handler = null, $principal = null, $cname = null |
224 ) { | 241 ) { |
225 $this->_pear = new PEAR(); | 242 $this->_pear = new PEAR(); |
226 $this->_state = NET_SIEVE_STATE_DISCONNECTED; | 243 $this->_state = NET_SIEVE_STATE_DISCONNECTED; |
227 $this->_data['user'] = $user; | 244 $this->_data['user'] = $user; |
228 $this->_data['pass'] = $pass; | 245 $this->_data['pass'] = $pass; |
232 $this->_data['euser'] = $euser; | 249 $this->_data['euser'] = $euser; |
233 $this->_sock = new Net_Socket(); | 250 $this->_sock = new Net_Socket(); |
234 $this->_bypassAuth = $bypassAuth; | 251 $this->_bypassAuth = $bypassAuth; |
235 $this->_useTLS = $useTLS; | 252 $this->_useTLS = $useTLS; |
236 $this->_options = (array) $options; | 253 $this->_options = (array) $options; |
254 $this->_gssapiPrincipal = $principal; | |
255 $this->_gssapiCN = $cname; | |
256 | |
237 $this->setDebug($debug, $handler); | 257 $this->setDebug($debug, $handler); |
238 | 258 |
239 /* Try to include the Auth_SASL package. If the package is not | 259 /* Try to include the Auth_SASL package. If the package is not |
240 * available, we disable the authentication methods that depend upon | 260 * available, we disable the authentication methods that depend upon |
241 * it. */ | 261 * it. */ |
275 $this->_debug = $debug; | 295 $this->_debug = $debug; |
276 $this->_debug_handler = $handler; | 296 $this->_debug_handler = $handler; |
277 } | 297 } |
278 | 298 |
279 /** | 299 /** |
300 * Sets the Kerberos service principal for use with GSSAPI | |
301 * authentication. | |
302 * | |
303 * @param string $principal The Kerberos service principal | |
304 * | |
305 * @return void | |
306 */ | |
307 function setServicePrincipal($principal) | |
308 { | |
309 $this->_gssapiPrincipal = $principal; | |
310 } | |
311 | |
312 /** | |
313 * Sets the Kerberos service CName for use with GSSAPI | |
314 * authentication. | |
315 * | |
316 * @param string $cname The Kerberos service principal | |
317 * | |
318 * @return void | |
319 */ | |
320 function setServiceCN($cname) | |
321 { | |
322 $this->_gssapiCN = $cname; | |
323 } | |
324 | |
325 /** | |
280 * Connects to the server and logs in. | 326 * Connects to the server and logs in. |
281 * | 327 * |
282 * @return boolean True on success, PEAR_Error on failure. | 328 * @return boolean True on success, PEAR_Error on failure. |
283 */ | 329 */ |
284 function _handleConnectAndLogin() | 330 function _handleConnectAndLogin() |
326 return $res; | 372 return $res; |
327 } | 373 } |
328 | 374 |
329 if ($this->_bypassAuth) { | 375 if ($this->_bypassAuth) { |
330 $this->_state = NET_SIEVE_STATE_TRANSACTION; | 376 $this->_state = NET_SIEVE_STATE_TRANSACTION; |
377 | |
378 // Reset capabilities | |
379 $this->_parseCapability(''); | |
331 } else { | 380 } else { |
332 $this->_state = NET_SIEVE_STATE_AUTHORISATION; | 381 $this->_state = NET_SIEVE_STATE_AUTHORISATION; |
382 | |
333 $res = $this->_doCmd(); | 383 $res = $this->_doCmd(); |
334 if (is_a($res, 'PEAR_Error')) { | 384 if (is_a($res, 'PEAR_Error')) { |
335 return $res; | 385 return $res; |
336 } | 386 } |
337 } | 387 |
338 | 388 // Reset capabilities (use unattended capabilities) |
339 // Explicitly ask for the capabilities in case the connection is | 389 $this->_parseCapability($res); |
340 // picked up from an existing connection. | 390 } |
341 $res = $this->_cmdCapability(); | 391 |
342 if (is_a($res, 'PEAR_Error')) { | 392 // Explicitly ask for the capabilities if needed |
343 return $this->_pear->raiseError( | 393 if (empty($this->_capability['implementation'])) { |
344 'Failed to connect, server said: ' . $res->getMessage(), 2 | 394 $res = $this->_cmdCapability(); |
345 ); | 395 if (is_a($res, 'PEAR_Error')) { |
396 return $this->_pear->raiseError( | |
397 'Failed to connect, server said: ' . $res->getMessage(), 2 | |
398 ); | |
399 } | |
346 } | 400 } |
347 | 401 |
348 // Check if we can enable TLS via STARTTLS. | 402 // Check if we can enable TLS via STARTTLS. |
349 if ($useTLS && !empty($this->_capability['starttls']) | 403 if ($useTLS && !empty($this->_capability['starttls']) |
350 && function_exists('stream_socket_enable_crypto') | 404 && function_exists('stream_socket_enable_crypto') |
398 $res = $this->_cmdAuthenticate($user, $pass, $logintype, $euser); | 452 $res = $this->_cmdAuthenticate($user, $pass, $logintype, $euser); |
399 if (is_a($res, 'PEAR_Error')) { | 453 if (is_a($res, 'PEAR_Error')) { |
400 return $res; | 454 return $res; |
401 } | 455 } |
402 } | 456 } |
457 | |
403 $this->_state = NET_SIEVE_STATE_TRANSACTION; | 458 $this->_state = NET_SIEVE_STATE_TRANSACTION; |
404 | 459 |
405 return true; | 460 return true; |
406 } | 461 } |
407 | 462 |
408 /** | 463 /** |
409 * Returns an indexed array of scripts currently on the server. | 464 * Returns an indexed array of scripts currently on the server. |
410 * | 465 * |
411 * @return array Indexed array of scriptnames. | 466 * @param string $active Will be set to the name of the active script |
412 */ | 467 * |
413 function listScripts() | 468 * @return array Indexed array of scriptnames, PEAR_Error on failure |
469 */ | |
470 function listScripts(&$active = null) | |
414 { | 471 { |
415 if (is_array($scripts = $this->_cmdListScripts())) { | 472 if (is_array($scripts = $this->_cmdListScripts())) { |
473 if (isset($scripts[1])) { | |
474 $active = $scripts[1]; | |
475 } | |
476 | |
416 return $scripts[0]; | 477 return $scripts[0]; |
417 } else { | 478 } |
418 return $scripts; | 479 |
419 } | 480 return $scripts; |
420 } | 481 } |
421 | 482 |
422 /** | 483 /** |
423 * Returns the active script. | 484 * Returns the active script. |
424 * | 485 * |
468 { | 529 { |
469 $res = $this->_cmdPutScript($scriptname, $script); | 530 $res = $this->_cmdPutScript($scriptname, $script); |
470 if (is_a($res, 'PEAR_Error')) { | 531 if (is_a($res, 'PEAR_Error')) { |
471 return $res; | 532 return $res; |
472 } | 533 } |
534 | |
473 if ($makeactive) { | 535 if ($makeactive) { |
474 return $this->_cmdSetActive($scriptname); | 536 return $this->_cmdSetActive($scriptname); |
475 } | 537 } |
538 | |
476 return true; | 539 return true; |
477 } | 540 } |
478 | 541 |
479 /** | 542 /** |
480 * Removes a script from the server. | 543 * Removes a script from the server. |
506 | 569 |
507 $res = $this->_doCmd(sprintf('HAVESPACE %s %d', $this->_escape($scriptname), $size)); | 570 $res = $this->_doCmd(sprintf('HAVESPACE %s %d', $this->_escape($scriptname), $size)); |
508 if (is_a($res, 'PEAR_Error')) { | 571 if (is_a($res, 'PEAR_Error')) { |
509 return $res; | 572 return $res; |
510 } | 573 } |
574 | |
511 return true; | 575 return true; |
512 } | 576 } |
513 | 577 |
514 /** | 578 /** |
515 * Returns the list of extensions the server supports. | 579 * Returns the list of extensions the server supports. |
519 function getExtensions() | 583 function getExtensions() |
520 { | 584 { |
521 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { | 585 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { |
522 return $this->_pear->raiseError('Not currently connected', 7); | 586 return $this->_pear->raiseError('Not currently connected', 7); |
523 } | 587 } |
588 | |
524 return $this->_capability['extensions']; | 589 return $this->_capability['extensions']; |
525 } | 590 } |
526 | 591 |
527 /** | 592 /** |
528 * Returns whether the server supports an extension. | 593 * Returns whether the server supports an extension. |
558 function getAuthMechs() | 623 function getAuthMechs() |
559 { | 624 { |
560 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { | 625 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { |
561 return $this->_pear->raiseError('Not currently connected', 7); | 626 return $this->_pear->raiseError('Not currently connected', 7); |
562 } | 627 } |
628 | |
563 return $this->_capability['sasl']; | 629 return $this->_capability['sasl']; |
564 } | 630 } |
565 | 631 |
566 /** | 632 /** |
567 * Returns whether the server supports an authentication method. | 633 * Returns whether the server supports an authentication method. |
576 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { | 642 if (NET_SIEVE_STATE_DISCONNECTED == $this->_state) { |
577 return $this->_pear->raiseError('Not currently connected', 7); | 643 return $this->_pear->raiseError('Not currently connected', 7); |
578 } | 644 } |
579 | 645 |
580 $method = trim($this->_toUpper($method)); | 646 $method = trim($this->_toUpper($method)); |
647 | |
581 if (is_array($this->_capability['sasl'])) { | 648 if (is_array($this->_capability['sasl'])) { |
582 foreach ($this->_capability['sasl'] as $sasl) { | 649 foreach ($this->_capability['sasl'] as $sasl) { |
583 if ($sasl == $method) { | 650 if ($sasl == $method) { |
584 return true; | 651 return true; |
585 } | 652 } |
604 { | 671 { |
605 $method = $this->_getBestAuthMethod($userMethod); | 672 $method = $this->_getBestAuthMethod($userMethod); |
606 if (is_a($method, 'PEAR_Error')) { | 673 if (is_a($method, 'PEAR_Error')) { |
607 return $method; | 674 return $method; |
608 } | 675 } |
676 | |
609 switch ($method) { | 677 switch ($method) { |
610 case 'DIGEST-MD5': | 678 case 'DIGEST-MD5': |
611 return $this->_authDigestMD5($uid, $pwd, $euser); | 679 return $this->_authDigestMD5($uid, $pwd, $euser); |
612 case 'CRAM-MD5': | 680 case 'CRAM-MD5': |
613 $result = $this->_authCRAMMD5($uid, $pwd, $euser); | 681 $result = $this->_authCRAMMD5($uid, $pwd, $euser); |
619 $result = $this->_authPLAIN($uid, $pwd, $euser); | 687 $result = $this->_authPLAIN($uid, $pwd, $euser); |
620 break; | 688 break; |
621 case 'EXTERNAL': | 689 case 'EXTERNAL': |
622 $result = $this->_authEXTERNAL($uid, $pwd, $euser); | 690 $result = $this->_authEXTERNAL($uid, $pwd, $euser); |
623 break; | 691 break; |
692 case 'GSSAPI': | |
693 $result = $this->_authGSSAPI($pwd); | |
694 break; | |
624 default : | 695 default : |
625 $result = $this->_pear->raiseError( | 696 $result = $this->_pear->raiseError( |
626 $method . ' is not a supported authentication method' | 697 $method . ' is not a supported authentication method' |
627 ); | 698 ); |
628 break; | 699 break; |
631 $res = $this->_doCmd(); | 702 $res = $this->_doCmd(); |
632 if (is_a($res, 'PEAR_Error')) { | 703 if (is_a($res, 'PEAR_Error')) { |
633 return $res; | 704 return $res; |
634 } | 705 } |
635 | 706 |
636 // Query the server capabilities again now that we are authenticated. | |
637 if ($this->_pear->isError($res = $this->_cmdCapability())) { | 707 if ($this->_pear->isError($res = $this->_cmdCapability())) { |
638 return $this->_pear->raiseError( | 708 return $this->_pear->raiseError( |
639 'Failed to connect, server said: ' . $res->getMessage(), 2 | 709 'Failed to connect, server said: ' . $res->getMessage(), 2 |
640 ); | 710 ); |
641 } | 711 } |
661 ) | 731 ) |
662 ); | 732 ); |
663 } | 733 } |
664 | 734 |
665 /** | 735 /** |
736 * Authenticates the user using the GSSAPI method. | |
737 * | |
738 * @note the PHP krb5 extension is required and the service principal and cname | |
739 * must have been set. | |
740 * @see setServicePrincipal() | |
741 * | |
742 * @return void | |
743 */ | |
744 function _authGSSAPI() | |
745 { | |
746 if (!extension_loaded('krb5')) { | |
747 return $this->_pear->raiseError('The krb5 extension is required for GSSAPI authentication', 2); | |
748 } | |
749 | |
750 if (!$this->_gssapiPrincipal) { | |
751 return $this->_pear->raiseError('No Kerberos service principal set', 2); | |
752 } | |
753 | |
754 if (!$this->_gssapiCN) { | |
755 return $this->_pear->raiseError('No Kerberos service CName set', 2); | |
756 } | |
757 | |
758 putenv('KRB5CCNAME=' . $this->_gssapiCN); | |
759 | |
760 try { | |
761 $ccache = new KRB5CCache(); | |
762 $ccache->open($this->_gssapiCN); | |
763 | |
764 $gssapicontext = new GSSAPIContext(); | |
765 $gssapicontext->acquireCredentials($ccache); | |
766 | |
767 $token = ''; | |
768 $success = $gssapicontext->initSecContext($this->_gssapiPrincipal, null, null, null, $token); | |
769 $token = base64_encode($token); | |
770 } | |
771 catch (Exception $e) { | |
772 return $this->_pear->raiseError('GSSAPI authentication failed: ' . $e->getMessage()); | |
773 } | |
774 | |
775 $this->_sendCmd("AUTHENTICATE \"GSSAPI\" {" . strlen($token) . "+}"); | |
776 | |
777 $response = $this->_doCmd($token, true); | |
778 | |
779 try { | |
780 $challenge = base64_decode(substr($response, 1, -1)); | |
781 $gssapicontext->unwrap($challenge, $challenge); | |
782 $gssapicontext->wrap($challenge, $challenge, true); | |
783 } | |
784 catch (Exception $e) { | |
785 return $this->_pear->raiseError('GSSAPI authentication failed: ' . $e->getMessage()); | |
786 } | |
787 | |
788 $response = base64_encode($challenge); | |
789 | |
790 $this->_sendCmd("{" . strlen($response) . "+}"); | |
791 | |
792 return $this->_sendCmd($response); | |
793 } | |
794 | |
795 /** | |
666 * Authenticates the user using the LOGIN method. | 796 * Authenticates the user using the LOGIN method. |
667 * | 797 * |
668 * @param string $user The userid to authenticate as. | 798 * @param string $user The userid to authenticate as. |
669 * @param string $pass The password to authenticate with. | 799 * @param string $pass The password to authenticate with. |
670 * @param string $euser The effective uid to authenticate as. Not used. | 800 * @param string $euser The effective uid to authenticate as. Not used. |
675 { | 805 { |
676 $result = $this->_sendCmd('AUTHENTICATE "LOGIN"'); | 806 $result = $this->_sendCmd('AUTHENTICATE "LOGIN"'); |
677 if (is_a($result, 'PEAR_Error')) { | 807 if (is_a($result, 'PEAR_Error')) { |
678 return $result; | 808 return $result; |
679 } | 809 } |
810 | |
680 $result = $this->_doCmd('"' . base64_encode($user) . '"', true); | 811 $result = $this->_doCmd('"' . base64_encode($user) . '"', true); |
681 if (is_a($result, 'PEAR_Error')) { | 812 if (is_a($result, 'PEAR_Error')) { |
682 return $result; | 813 return $result; |
683 } | 814 } |
815 | |
684 return $this->_doCmd('"' . base64_encode($pass) . '"', true); | 816 return $this->_doCmd('"' . base64_encode($pass) . '"', true); |
685 } | 817 } |
686 | 818 |
687 /** | 819 /** |
688 * Authenticates the user using the CRAM-MD5 method. | 820 * Authenticates the user using the CRAM-MD5 method. |
740 | 872 |
741 $result = $this->_sendStringResponse(base64_encode($response)); | 873 $result = $this->_sendStringResponse(base64_encode($response)); |
742 if (is_a($result, 'PEAR_Error')) { | 874 if (is_a($result, 'PEAR_Error')) { |
743 return $result; | 875 return $result; |
744 } | 876 } |
877 | |
745 $result = $this->_doCmd('', true); | 878 $result = $this->_doCmd('', true); |
746 if (is_a($result, 'PEAR_Error')) { | 879 if (is_a($result, 'PEAR_Error')) { |
747 return $result; | 880 return $result; |
748 } | 881 } |
882 | |
749 if ($this->_toUpper(substr($result, 0, 2)) == 'OK') { | 883 if ($this->_toUpper(substr($result, 0, 2)) == 'OK') { |
750 return; | 884 return; |
751 } | 885 } |
752 | 886 |
753 /* We don't use the protocol's third step because SIEVE doesn't allow | 887 /* We don't use the protocol's third step because SIEVE doesn't allow |
767 * @param string $pass The password to authenticate with. | 901 * @param string $pass The password to authenticate with. |
768 * @param string $euser The effective uid to authenticate as. | 902 * @param string $euser The effective uid to authenticate as. |
769 * | 903 * |
770 * @return void | 904 * @return void |
771 * | 905 * |
772 * @since 1.1.7 | 906 * @since 1.1.7 |
773 */ | 907 */ |
774 function _authEXTERNAL($user, $pass, $euser) | 908 function _authEXTERNAL($user, $pass, $euser) |
775 { | 909 { |
776 $cmd = sprintf( | 910 $cmd = sprintf( |
777 'AUTHENTICATE "EXTERNAL" "%s"', | 911 'AUTHENTICATE "EXTERNAL" "%s"', |
778 base64_encode(strlen($euser) ? $euser : $user) | 912 base64_encode(strlen($euser) ? $euser : $user) |
779 ); | 913 ); |
914 | |
780 return $this->_sendCmd($cmd); | 915 return $this->_sendCmd($cmd); |
781 } | 916 } |
782 | 917 |
783 /** | 918 /** |
784 * Removes a script from the server. | 919 * Removes a script from the server. |
795 | 930 |
796 $res = $this->_doCmd(sprintf('DELETESCRIPT %s', $this->_escape($scriptname))); | 931 $res = $this->_doCmd(sprintf('DELETESCRIPT %s', $this->_escape($scriptname))); |
797 if (is_a($res, 'PEAR_Error')) { | 932 if (is_a($res, 'PEAR_Error')) { |
798 return $res; | 933 return $res; |
799 } | 934 } |
935 | |
800 return true; | 936 return true; |
801 } | 937 } |
802 | 938 |
803 /** | 939 /** |
804 * Retrieves the contents of the named script. | 940 * Retrieves the contents of the named script. |
976 case 'IMPLEMENTATION': | 1112 case 'IMPLEMENTATION': |
977 $this->_capability['implementation'] = $matches[3]; | 1113 $this->_capability['implementation'] = $matches[3]; |
978 break; | 1114 break; |
979 | 1115 |
980 case 'SASL': | 1116 case 'SASL': |
981 $this->_capability['sasl'] = preg_split('/\s+/', $matches[3]); | 1117 if (!empty($matches[3])) { |
1118 $this->_capability['sasl'] = preg_split('/\s+/', $matches[3]); | |
1119 } | |
982 break; | 1120 break; |
983 | 1121 |
984 case 'SIEVE': | 1122 case 'SIEVE': |
985 $this->_capability['extensions'] = preg_split('/\s+/', $matches[3]); | 1123 if (!empty($matches[3])) { |
1124 $this->_capability['extensions'] = preg_split('/\s+/', $matches[3]); | |
1125 } | |
986 break; | 1126 break; |
987 | 1127 |
988 case 'STARTTLS': | 1128 case 'STARTTLS': |
989 $this->_capability['starttls'] = true; | 1129 $this->_capability['starttls'] = true; |
990 break; | 1130 break; |
1225 return $res; | 1365 return $res; |
1226 } | 1366 } |
1227 | 1367 |
1228 if (isset($this->_options['ssl']['crypto_method'])) { | 1368 if (isset($this->_options['ssl']['crypto_method'])) { |
1229 $crypto_method = $this->_options['ssl']['crypto_method']; | 1369 $crypto_method = $this->_options['ssl']['crypto_method']; |
1230 } | 1370 } else { |
1231 else { | |
1232 // There is no flag to enable all TLS methods. Net_SMTP | 1371 // There is no flag to enable all TLS methods. Net_SMTP |
1233 // handles enabling TLS similarly. | 1372 // handles enabling TLS similarly. |
1234 $crypto_method = STREAM_CRYPTO_METHOD_TLS_CLIENT | 1373 $crypto_method = STREAM_CRYPTO_METHOD_TLS_CLIENT |
1235 | @STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT | 1374 | @STREAM_CRYPTO_METHOD_TLSv1_1_CLIENT |
1236 | @STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT; | 1375 | @STREAM_CRYPTO_METHOD_TLSv1_2_CLIENT; |
1248 // CAPABILITY response, thus we would wait here forever. Parse the | 1387 // CAPABILITY response, thus we would wait here forever. Parse the |
1249 // Cyrus version and work around this broken behavior. | 1388 // Cyrus version and work around this broken behavior. |
1250 if (!preg_match('/^CYRUS TIMSIEVED V([0-9.]+)/', $this->_capability['implementation'], $matches) | 1389 if (!preg_match('/^CYRUS TIMSIEVED V([0-9.]+)/', $this->_capability['implementation'], $matches) |
1251 || version_compare($matches[1], '2.3.10', '>=') | 1390 || version_compare($matches[1], '2.3.10', '>=') |
1252 ) { | 1391 ) { |
1253 $this->_doCmd(); | 1392 $res = $this->_doCmd(); |
1254 } | 1393 } |
1255 | 1394 |
1256 // Query the server capabilities again now that we are under | 1395 // Reset capabilities (use unattended capabilities) |
1257 // encryption. | 1396 $this->_parseCapability(is_string($res) ? $res : ''); |
1258 $res = $this->_cmdCapability(); | 1397 |
1259 if (is_a($res, 'PEAR_Error')) { | 1398 // Query the server capabilities again now that we are under encryption. |
1260 return $this->_pear->raiseError( | 1399 if (empty($this->_capability['implementation'])) { |
1261 'Failed to connect, server said: ' . $res->getMessage(), 2 | 1400 $res = $this->_cmdCapability(); |
1262 ); | 1401 if (is_a($res, 'PEAR_Error')) { |
1402 return $this->_pear->raiseError( | |
1403 'Failed to connect, server said: ' . $res->getMessage(), 2 | |
1404 ); | |
1405 } | |
1263 } | 1406 } |
1264 | 1407 |
1265 return true; | 1408 return true; |
1266 } | 1409 } |
1267 | 1410 |
1273 * @return integer The length of the string. | 1416 * @return integer The length of the string. |
1274 */ | 1417 */ |
1275 function _getLineLength($string) | 1418 function _getLineLength($string) |
1276 { | 1419 { |
1277 if (extension_loaded('mbstring')) { | 1420 if (extension_loaded('mbstring')) { |
1278 return mb_strlen($string, 'latin1'); | 1421 return mb_strlen($string, '8bit'); |
1279 } else { | 1422 } else { |
1280 return strlen($string); | 1423 return strlen($string); |
1281 } | 1424 } |
1282 } | 1425 } |
1283 | 1426 |