[SVN] r714 - /branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch

debian at incase.de debian at incase.de
Thu Mar 8 17:07:18 CET 2007


Author: sven
Date: Thu Mar  8 17:07:17 2007
New Revision: 714

URL: https://mail.incase.de/viewcvs?rev=714&root=cyrus22&view=rev
Log:
Fix up cyradm-tls patch #1

Modified:
    branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch

Modified: branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch
URL: https://mail.incase.de/viewcvs/branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch?rev=714&root=cyrus22&r1=713&r2=714&view=diff
==============================================================================
--- branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch (original)
+++ branches/sarge-2.2.13-cyradm-tls/debian/patches/66-cyradm-tls-enabled.dpatch Thu Mar  8 17:07:17 2007
@@ -5,79 +5,9 @@
 ## DP: No description.
 
 @DPATCH@
-diff -urNad sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed /tmp/dpep.9n8yig/sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed
---- sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed	1970-01-01 01:00:00.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed	2007-03-08 16:42:22.000000000 +0100
-@@ -0,0 +1,66 @@
-+patching file perl/imap/IMAP/Shell.pm
-+Hunk #1 FAILED at 436.
-+Hunk #2 FAILED at 449.
-+Hunk #3 FAILED at 469.
-+Hunk #4 succeeded at 795 with fuzz 2 (offset 18 lines).
-+Hunk #5 FAILED at 820.
-+4 out of 5 hunks FAILED -- saving rejects to file perl/imap/IMAP/Shell.pm.rej
-+patching file perl/imap/IMAP.pm
-+Hunk #1 FAILED at 196.
-+Hunk #2 succeeded at 302 with fuzz 2 (offset 41 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/imap/IMAP.pm.rej
-+patching file perl/imap/IMAP.xs
-+Hunk #1 FAILED at 57.
-+Hunk #2 succeeded at 457 with fuzz 2 (offset 39 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/imap/IMAP.xs.rej
-+patching file perl/imap/Makefile.PL
-+Hunk #1 FAILED at 1.
-+Hunk #2 FAILED at 65.
-+2 out of 2 hunks FAILED -- saving rejects to file perl/imap/Makefile.PL.rej
-+patching file perl/imap/cyradm.sh
-+Hunk #1 FAILED at 54.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/imap/cyradm.sh.rej
-+patching file perl/sieve/lib/isieve.c
-+Hunk #1 succeeded at 47 with fuzz 2 (offset 2 lines).
-+Hunk #2 succeeded at 72 with fuzz 2 (offset 11 lines).
-+Hunk #3 FAILED at 103.
-+Hunk #4 FAILED at 313.
-+Hunk #5 succeeded at 430 with fuzz 1 (offset 54 lines).
-+Hunk #6 succeeded at 702 with fuzz 2 (offset 58 lines).
-+Hunk #7 FAILED at 867.
-+3 out of 7 hunks FAILED -- saving rejects to file perl/sieve/lib/isieve.c.rej
-+patching file perl/sieve/lib/isieve.h
-+Hunk #1 FAILED at 67.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/sieve/lib/isieve.h.rej
-+patching file perl/sieve/lib/request.c
-+Hunk #1 FAILED at 168.
-+Hunk #2 succeeded at 669 with fuzz 2 (offset 30 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/sieve/lib/request.c.rej
-+patching file perl/sieve/lib/request.h
-+Hunk #1 FAILED at 91.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/sieve/lib/request.h.rej
-+patching file perl/sieve/managesieve/Makefile.PL
-+Hunk #1 FAILED at 46.
-+Hunk #2 FAILED at 62.
-+2 out of 2 hunks FAILED -- saving rejects to file perl/sieve/managesieve/Makefile.PL.rej
-+patching file perl/sieve/managesieve/managesieve.xs
-+Hunk #1 FAILED at 211.
-+Hunk #2 succeeded at 253 with fuzz 2 (offset 3 lines).
-+Hunk #3 succeeded at 310 (offset 8 lines).
-+1 out of 3 hunks FAILED -- saving rejects to file perl/sieve/managesieve/managesieve.xs.rej
-+patching file perl/sieve/scripts/installsieve.pl
-+Hunk #1 FAILED at 44.
-+Hunk #2 FAILED at 56.
-+Hunk #3 succeeded at 76 with fuzz 2 (offset 7 lines).
-+Hunk #4 FAILED at 127.
-+3 out of 4 hunks FAILED -- saving rejects to file perl/sieve/scripts/installsieve.pl.rej
-+patching file perl/sieve/scripts/sieveshell.pl
-+Hunk #1 FAILED at 61.
-+Hunk #2 FAILED at 73.
-+Hunk #3 succeeded at 96 with fuzz 2 (offset 8 lines).
-+Hunk #4 FAILED at 172.
-+Hunk #5 FAILED at 189.
-+Hunk #6 FAILED at 334.
-+Hunk #7 succeeded at 388 with fuzz 2 (offset 17 lines).
-+5 out of 7 hunks FAILED -- saving rejects to file perl/sieve/scripts/sieveshell.pl.rej
-+md5sum: 63d18aece91f37515327eaefdb6d24ae  /tmp/dpep.9n8yig/sarge-2.2.13/debian/patches/66-cyradm-tls-enabled.dpatch
-diff -urNad sarge-2.2.13/perl/imap/IMAP/Shell.pm /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP/Shell.pm
---- sarge-2.2.13/perl/imap/IMAP/Shell.pm	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP/Shell.pm	2007-03-08 16:42:22.306556343 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/imap/IMAP/Shell.pm /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP/Shell.pm
+--- sarge-2.2.13-cyradm-tls/perl/imap/IMAP/Shell.pm	2007-03-08 16:59:55.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP/Shell.pm	2007-03-08 16:59:55.941293692 +0100
 @@ -436,9 +436,10 @@
  # (It's not as trivial as run() because it does things expected of standalone
  # programs, as opposed to things expected from within a program.)
@@ -110,7 +40,7 @@
        or die "cyradm: cannot authenticate to server" . (defined($mech)?" with $mech":"") . " as $auth\n";
    }
    my $fstk = [*STDIN, *STDOUT, *STDERR];
-@@ -773,6 +777,34 @@
+@@ -773,6 +777,62 @@
        $want = '-service';
        next;
      }
@@ -142,10 +72,38 @@
 +	    "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
 +      }
 +    }
++    if (Cyrus::IMAP::imclient_havetls()) {
++      if ($opt ne '' && '-tlskey' =~ /^\Q$opt/ || $opt eq '--tlskey') {
++	$want = '-tlskey';
++	next;
++      }
++      if ($opt ne '' && '-notls' =~ /^\Q$opt/ || $opt eq '--notls') {
++	$want = '-notls';
++	next;
++      }
++      if ($opt =~ /^-/) {
++	die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
++	    "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
++      }
++    }
++    if (Cyrus::IMAP::imclient_havetls()) {
++      if ($opt ne '' && '-tlskey' =~ /^\Q$opt/ || $opt eq '--tlskey') {
++	$want = '-tlskey';
++	next;
++      }
++      if ($opt ne '' && '-notls' =~ /^\Q$opt/ || $opt eq '--notls') {
++	$want = '-notls';
++	next;
++      }
++      if ($opt =~ /^-/) {
++	die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
++	    "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
++      }
++    }
      if ($opt =~ /^-/) {
        die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
  	  "                    [-service name] [user]\n";
-@@ -784,8 +816,13 @@
+@@ -784,8 +844,13 @@
    }
    push(@nargv, @argv);
    if (@nargv > 1) {
@@ -161,9 +119,9 @@
    }
    if (@nargv) {
      $opts{-user} = shift(@nargv);
-diff -urNad sarge-2.2.13/perl/imap/IMAP.pm /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.pm
---- sarge-2.2.13/perl/imap/IMAP.pm	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.pm	2007-03-08 16:42:22.307556244 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/imap/IMAP.pm /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP.pm
+--- sarge-2.2.13-cyradm-tls/perl/imap/IMAP.pm	2007-03-08 16:49:33.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP.pm	2007-03-08 16:59:55.942293593 +0100
 @@ -196,16 +196,43 @@
  sub authenticate {
    my ($self, $first) = @_;
@@ -211,7 +169,7 @@
    }
    if (!defined($opts{-mechanism})) {
      $opts{-mechanism} = '';
-@@ -234,6 +261,34 @@
+@@ -234,6 +261,62 @@
  			       $opts{-authz}, $opts{-user}, $opts{-password},
  			       $opts{-minssf}, $opts{-maxssf});
    }
@@ -243,12 +201,40 @@
 +      return undef;
 +    }
 +  }
++  if (!$rc) {
++    $self->addcallback({-trigger => 'CAPABILITY',
++			-callback => sub {my %a = @_;
++					  map { $logindisabled = 1
++						    if /^LOGINDISABLED$/i;
++					    }
++					  split(/ /, $a{-text})}});
++    $self->send(undef, undef, 'CAPABILITY');
++    $self->addcallback({-trigger => 'CAPABILITY'});
++    if ($logindisabled) {
++      warn "Login disabled.\n";
++      return undef;
++    }
++  }
++  if (!$rc) {
++    $self->addcallback({-trigger => 'CAPABILITY',
++			-callback => sub {my %a = @_;
++					  map { $logindisabled = 1
++						    if /^LOGINDISABLED$/i;
++					    }
++					  split(/ /, $a{-text})}});
++    $self->send(undef, undef, 'CAPABILITY');
++    $self->addcallback({-trigger => 'CAPABILITY'});
++    if ($logindisabled) {
++      warn "Login disabled.\n";
++      return undef;
++    }
++  }
    $opts{-mechanism} ||= 'plain';
    if (!$rc && $opts{-mechanism} =~ /(\b|^)(plain|login)($|\b)/i) {
      $opts{-user} = getlogin if !defined($opts{-user});
-diff -urNad sarge-2.2.13/perl/imap/IMAP.xs /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.xs
---- sarge-2.2.13/perl/imap/IMAP.xs	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.xs	2007-03-08 16:42:22.308556145 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/imap/IMAP.xs /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP.xs
+--- sarge-2.2.13-cyradm-tls/perl/imap/IMAP.xs	2007-03-08 16:49:33.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/IMAP.xs	2007-03-08 16:59:55.942293593 +0100
 @@ -57,6 +57,7 @@
  #include "xmalloc.h"
  
@@ -257,9 +243,9 @@
  
  typedef struct xscyrus *Cyrus_IMAP;
  
-@@ -417,6 +418,82 @@
- 	  ST(0) = &sv_yes;
- 	}
+@@ -367,6 +368,82 @@
+ OUTPUT:
+ 	RETVAL
  
 +int
 +imclient_havetls()
@@ -338,11 +324,94 @@
 +#endif /* HAVE_SSL */
 +
  void
+ imclient_processoneevent(client)
+ 	Cyrus_IMAP client
+@@ -417,6 +494,82 @@
+ 	  ST(0) = &sv_yes;
+ 	}
+ 
++int
++imclient_havetls()
++CODE:
++#ifdef HAVE_SSL
++	RETVAL = 1;
++#else
++	RETVAL = 0;
++#endif /* HAVE_SSL */
++OUTPUT:
++	RETVAL
++
++SV *
++imclient__starttls(client, tls_cert_file, tls_key_file, CAfile, CApath)
++	Cyrus_IMAP client
++	char* tls_cert_file
++	char* tls_key_file
++        char* CAfile
++        char* CApath
++PREINIT:
++	int rc;
++	int tls_layer;
++CODE:
++	ST(0) = sv_newmortal();
++
++	/* If the tls_{cert, key}_file parameters are undef, set to be NULL */
++	if(!SvOK(ST(2))) tls_cert_file = NULL;
++	if(!SvOK(ST(3))) tls_key_file = NULL;
++#ifdef HAVE_SSL
++	rc = imclient_starttls(client->imclient, tls_cert_file, tls_key_file, CAfile, CApath);
++	if (rc)
++	  ST(0) = &sv_no;
++	else {
++	  ST(0) = &sv_yes;
++	}
++#else
++	ST(0) = &sv_no;
++#endif /* HAVE_SSL */
++
++int
++imclient_havetls()
++CODE:
++#ifdef HAVE_SSL
++	RETVAL = 1;
++#else
++	RETVAL = 0;
++#endif /* HAVE_SSL */
++OUTPUT:
++	RETVAL
++
++SV *
++imclient__starttls(client, tls_cert_file, tls_key_file, CAfile, CApath)
++	Cyrus_IMAP client
++	char* tls_cert_file
++	char* tls_key_file
++        char* CAfile
++        char* CApath
++PREINIT:
++	int rc;
++	int tls_layer;
++CODE:
++	ST(0) = sv_newmortal();
++
++	/* If the tls_{cert, key}_file parameters are undef, set to be NULL */
++	if(!SvOK(ST(2))) tls_cert_file = NULL;
++	if(!SvOK(ST(3))) tls_key_file = NULL;
++#ifdef HAVE_SSL
++	rc = imclient_starttls(client->imclient, tls_cert_file, tls_key_file, CAfile, CApath);
++	if (rc)
++	  ST(0) = &sv_no;
++	else {
++	  ST(0) = &sv_yes;
++	}
++#else
++	ST(0) = &sv_no;
++#endif /* HAVE_SSL */
++
+ void
  imclient_addcallback(client, ...)
  	Cyrus_IMAP client
-diff -urNad sarge-2.2.13/perl/imap/Makefile.PL /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/Makefile.PL
---- sarge-2.2.13/perl/imap/Makefile.PL	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/Makefile.PL	2007-03-08 16:42:22.308556145 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/imap/Makefile.PL /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/Makefile.PL
+--- sarge-2.2.13-cyradm-tls/perl/imap/Makefile.PL	2007-03-08 16:49:33.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/Makefile.PL	2007-03-08 16:59:55.943293493 +0100
 @@ -1,5 +1,4 @@
  # 
 -# Copyright (c) 2000 Carnegie Mellon University.  All rights reserved.
@@ -359,9 +428,9 @@
 +    'INC'	=> "-I../../lib -I../.. $SASL_INC $OPENSSL_INC", 
      'EXE_FILES' => [cyradm],
  );
-diff -urNad sarge-2.2.13/perl/imap/cyradm.sh /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/cyradm.sh
---- sarge-2.2.13/perl/imap/cyradm.sh	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/cyradm.sh	2007-03-08 16:42:22.309556046 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/imap/cyradm.sh /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/cyradm.sh
+--- sarge-2.2.13-cyradm-tls/perl/imap/cyradm.sh	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/imap/cyradm.sh	2007-03-08 16:59:55.943293493 +0100
 @@ -54,7 +54,8 @@
  =head1 SYNOPSIS
  
@@ -372,13 +441,17 @@
  
  but possibly
  
-diff -urNad sarge-2.2.13/perl/sieve/lib/isieve.c /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.c
---- sarge-2.2.13/perl/sieve/lib/isieve.c	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.c	2007-03-08 16:42:22.311555847 +0100
-@@ -45,6 +45,10 @@
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.c /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.c
+--- sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.c	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.c	2007-03-08 16:59:55.944293394 +0100
+@@ -45,6 +45,14 @@
  #include <config.h>
  #endif
  
++#include <assert.h>
++
++#include <assert.h>
++
 +#include <assert.h>
 +
 +#include <assert.h>
@@ -386,7 +459,7 @@
  #ifdef HAVE_UNISTD_H
  #include <unistd.h>
  #endif
-@@ -59,6 +63,24 @@
+@@ -59,6 +67,42 @@
  #include <sasl/sasl.h>
  #include <sasl/saslutil.h>
  
@@ -408,10 +481,28 @@
 +#include <openssl/ssl.h>
 +#endif /* HAVE_SSL */
 +
++#ifdef HAVE_SSL
++#include <openssl/lhash.h>
++#include <openssl/bn.h>
++#include <openssl/err.h>
++#include <openssl/pem.h>
++#include <openssl/x509.h>
++#include <openssl/ssl.h>
++#endif /* HAVE_SSL */
++
++#ifdef HAVE_SSL
++#include <openssl/lhash.h>
++#include <openssl/bn.h>
++#include <openssl/err.h>
++#include <openssl/pem.h>
++#include <openssl/x509.h>
++#include <openssl/ssl.h>
++#endif /* HAVE_SSL */
++
  #include "isieve.h"
  #include "lex.h"
  #include "request.h"
-@@ -81,13 +103,27 @@
+@@ -81,13 +125,27 @@
      sasl_callback_t *refer_callbacks;
  
      int version;
@@ -439,7 +530,7 @@
  /* we need this separate from the free() call so that we can reuse
   * the same memory for referrals */
  static void sieve_dispose(isieve_t *obj) 
-@@ -277,7 +313,7 @@
+@@ -277,7 +335,7 @@
        } else if (strcasecmp(attr,"IMPLEMENTATION")==0) {
  
        } else if (strcasecmp(attr,"STARTTLS")==0) {
@@ -448,7 +539,7 @@
        } else if (val && strncmp(val,"SASL=",5)==0) {
  	  obj->version = OLD_VERSION;
  	  cap = (char *) xmalloc(strlen(val));
-@@ -351,6 +387,64 @@
+@@ -351,6 +409,122 @@
    return STAT_CONT;
  }
  
@@ -510,10 +601,68 @@
 +  return 0;
 +}
 +
++int auth_starttls(isieve_t *obj, char *tls_keyfile,
++		  char **mechlist, char **errstr)
++{
++  unsigned ext_ssf = 0;
++  int ret;
++  char *refer_to;
++
++  if (!obj->tls_keyfile) obj->tls_keyfile = tls_keyfile;
++
++  if (!obj->starttls || !obj->tls_keyfile) return 0;
++
++#ifdef HAVE_SSL
++  ret = starttls(obj->version, obj->pout, obj->pin, &refer_to, errstr);
++  /* xxx handle referrals */
++  if (ret != 0) return -1;
++
++  ret = isieve_starttls(obj, 0, tls_keyfile, tls_keyfile, &ext_ssf);
++  if (ret != 0) return -1;
++
++  prot_printf(obj->pout, "CAPABILITY\r\n");
++  prot_flush(obj->pout);
++  
++  if (*mechlist) free(*mechlist);
++  *mechlist = read_capability(obj);
++#endif /* HAVE_SSL */
++
++  return 0;
++}
++
++int auth_starttls(isieve_t *obj, char *tls_keyfile,
++		  char **mechlist, char **errstr)
++{
++  unsigned ext_ssf = 0;
++  int ret;
++  char *refer_to;
++
++  if (!obj->tls_keyfile) obj->tls_keyfile = tls_keyfile;
++
++  if (!obj->starttls || !obj->tls_keyfile) return 0;
++
++#ifdef HAVE_SSL
++  ret = starttls(obj->version, obj->pout, obj->pin, &refer_to, errstr);
++  /* xxx handle referrals */
++  if (ret != 0) return -1;
++
++  ret = isieve_starttls(obj, 0, tls_keyfile, tls_keyfile, &ext_ssf);
++  if (ret != 0) return -1;
++
++  prot_printf(obj->pout, "CAPABILITY\r\n");
++  prot_flush(obj->pout);
++  
++  if (*mechlist) free(*mechlist);
++  *mechlist = read_capability(obj);
++#endif /* HAVE_SSL */
++
++  return 0;
++}
++
  
  int auth_sasl(char *mechlist, isieve_t *obj, const char **mechusing,
  	      char **errstr)
-@@ -590,6 +684,14 @@
+@@ -590,6 +764,22 @@
      /* Authenticate */
      mechlist = read_capability(obj_new);
  
@@ -525,10 +674,18 @@
 +    ret = auth_starttls(obj, obj->tls_keyfile, &mechlist, &errstr);
 +   if (ret) return STAT_NO;
 +
++    /* Perform STARTTLS */
++    ret = auth_starttls(obj, obj->tls_keyfile, &mechlist, &errstr);
++   if (ret) return STAT_NO;
++
++    /* Perform STARTTLS */
++    ret = auth_starttls(obj, obj->tls_keyfile, &mechlist, &errstr);
++   if (ret) return STAT_NO;
++
      do {
  	mtried = NULL;
  	ret = auth_sasl(mechlist, obj_new, &mtried, &errstr);
-@@ -751,3 +853,342 @@
+@@ -751,3 +941,342 @@
  
      return ret;
  }
@@ -871,9 +1028,9 @@
 +  return 0;
 +}
 +#endif /* HAVE_SSL */
-diff -urNad sarge-2.2.13/perl/sieve/lib/isieve.h /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.h
---- sarge-2.2.13/perl/sieve/lib/isieve.h	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.h	2007-03-08 16:42:22.312555748 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.h /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.h
+--- sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.h	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/isieve.h	2007-03-08 16:59:55.945293294 +0100
 @@ -67,6 +67,7 @@
      STAT_OK = 2
  } imt_stat;
@@ -882,9 +1039,9 @@
  int auth_sasl(char *mechlist, isieve_t *obj, const char **mechusing, char **errstr);
  
  int isieve_logout(isieve_t **obj);
-diff -urNad sarge-2.2.13/perl/sieve/lib/request.c /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.c
---- sarge-2.2.13/perl/sieve/lib/request.c	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.c	2007-03-08 16:42:22.313555649 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.c /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.c
+--- sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.c	2007-03-08 16:59:55.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.c	2007-03-08 16:59:55.945293294 +0100
 @@ -168,22 +168,24 @@
        /* SASL response */
        res = yylex(&state, pin);
@@ -923,7 +1080,7 @@
        } else if (version != OLD_VERSION && res == EOL) {
  	  return r;
        }
-@@ -637,3 +639,59 @@
+@@ -637,3 +639,115 @@
    return 0;
  
  }
@@ -983,9 +1140,65 @@
 +  }
 +  return 0;
 +}
-diff -urNad sarge-2.2.13/perl/sieve/lib/request.h /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.h
---- sarge-2.2.13/perl/sieve/lib/request.h	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.h	2007-03-08 16:42:22.313555649 +0100
++
++
++int starttls(int version, struct protstream *pout, struct protstream *pin,
++	     char **refer_to, char **errstrp)
++{
++  lexstate_t state;
++  int res;
++  int ret;
++  mystring_t *errstr;
++
++  prot_printf(pout, "STARTTLS\r\n");
++  prot_flush(pout);
++	    
++  res = yylex(&state, pin);
++
++  ret = handle_response(res, version, pin, refer_to, &errstr);
++
++  /* if command failed */
++  if(ret == -2 && *refer_to) {
++      return -2;
++  } else if (ret != 0) {
++      *errstrp = malloc(128);
++      snprintf(*errstrp, 127, 
++	       "Starttls: %s",string_DATAPTR(errstr));
++      return -1;
++  }
++  return 0;
++}
++
++
++int starttls(int version, struct protstream *pout, struct protstream *pin,
++	     char **refer_to, char **errstrp)
++{
++  lexstate_t state;
++  int res;
++  int ret;
++  mystring_t *errstr;
++
++  prot_printf(pout, "STARTTLS\r\n");
++  prot_flush(pout);
++	    
++  res = yylex(&state, pin);
++
++  ret = handle_response(res, version, pin, refer_to, &errstr);
++
++  /* if command failed */
++  if(ret == -2 && *refer_to) {
++      return -2;
++  } else if (ret != 0) {
++      *errstrp = malloc(128);
++      snprintf(*errstrp, 127, 
++	       "Starttls: %s",string_DATAPTR(errstr));
++      return -1;
++  }
++  return 0;
++}
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.h /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.h
+--- sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.h	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/lib/request.h	2007-03-08 16:59:55.946293195 +0100
 @@ -91,5 +91,7 @@
  
  void parseerror(char *str);
@@ -994,9 +1207,9 @@
 +	    char **refer_to, char **errstr);
  
  #endif
-diff -urNad sarge-2.2.13/perl/sieve/managesieve/Makefile.PL /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/Makefile.PL
---- sarge-2.2.13/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:42:22.313555649 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/Makefile.PL /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/Makefile.PL
+--- sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:59:55.946293195 +0100
 @@ -46,6 +46,7 @@
  my $SASL_LIB = $ENV{SASL_LIB} || "-lsasl2";
  my $OPENSSL_INC = $ENV{OPENSSL_INC};
@@ -1014,9 +1227,9 @@
      'INC'	=> "-I../lib/ -I../../../lib/ $SASL_INC $OPENSSL_INC",
      'CC'	=> $ENV{CC},
      'LD'	=> $ENV{CC}
-diff -urNad sarge-2.2.13/perl/sieve/managesieve/managesieve.xs /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/managesieve.xs
---- sarge-2.2.13/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:42:22.314555550 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/managesieve.xs /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/managesieve.xs
+--- sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:49:34.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:59:55.946293195 +0100
 @@ -211,12 +211,13 @@
  
  
@@ -1032,10 +1245,14 @@
  
    PREINIT:
    Sieveobj ret = NULL;
-@@ -249,6 +250,10 @@
+@@ -249,6 +250,14 @@
    callbacks[3].context = password_cb;
    callbacks[4].id = SASL_CB_LIST_END;
  
++  if (!SvOK(ST(5))) tls_keyfile = NULL;
++
++  if (!SvOK(ST(5))) tls_keyfile = NULL;
++
 +  if (!SvOK(ST(5))) tls_keyfile = NULL;
 +
 +  if (!SvOK(ST(5))) tls_keyfile = NULL;
@@ -1043,7 +1260,7 @@
    /* see if we have server:port (or IPv6, etc)*/
    p = servername;
    if (*servername == '[') {
-@@ -299,6 +304,16 @@
+@@ -299,6 +308,26 @@
  	XSRETURN_UNDEF;
    }
  
@@ -1057,12 +1274,22 @@
 +	XSRETURN_UNDEF;
 +  }
 +
++  if (auth_starttls(obj, tls_keyfile, &mlist, &ret->errstr) != 0) {
++	globalerr = "starttls failed";
++	XSRETURN_UNDEF;
++  }
++
++  if (auth_starttls(obj, tls_keyfile, &mlist, &ret->errstr) != 0) {
++	globalerr = "starttls failed";
++	XSRETURN_UNDEF;
++  }
++
    /* loop through all the mechanisms */
    do {
      mtried = NULL;
-diff -urNad sarge-2.2.13/perl/sieve/scripts/installsieve.pl /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/installsieve.pl
---- sarge-2.2.13/perl/sieve/scripts/installsieve.pl	2007-03-08 16:40:29.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/installsieve.pl	2007-03-08 16:42:22.315555451 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/scripts/installsieve.pl /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/scripts/installsieve.pl
+--- sarge-2.2.13-cyradm-tls/perl/sieve/scripts/installsieve.pl	2007-03-08 16:59:55.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/scripts/installsieve.pl	2007-03-08 16:59:55.947293095 +0100
 @@ -44,6 +44,7 @@
  use Getopt::Long;
  
@@ -1080,7 +1307,7 @@
  		  "g|gets:s" => \$gets,
                    "u|username:s" => \$username,
  #		  "w|password:s" => \$pass
-@@ -66,6 +69,14 @@
+@@ -66,6 +69,22 @@
  
  $acapserver = $ARGV[0];
  
@@ -1092,10 +1319,18 @@
 +    $tls_keyfile = undef;
 +}
 +
++if ($notls) {
++    $tls_keyfile = undef;
++}
++
++if ($notls) {
++    $tls_keyfile = undef;
++}
++
  sub list_cb {
  
    my($name, $isactive) = @_ ;
-@@ -113,11 +124,13 @@
+@@ -113,11 +132,13 @@
    print "  -g <name>    Get script <name> and save to disk\n";
    print "  -u <user>    Userid/Authname to use\n";
  #  print "  -w <passwd>  Specify password (Should only be used for automated scripts)\n";
@@ -1110,9 +1345,9 @@
  
  if (!defined $obj) {
    die "Unable to connect to server";
-diff -urNad sarge-2.2.13/perl/sieve/scripts/sieveshell.pl /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/sieveshell.pl
---- sarge-2.2.13/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:42:22.316555352 +0100
+diff -urNad sarge-2.2.13-cyradm-tls/perl/sieve/scripts/sieveshell.pl /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/scripts/sieveshell.pl
+--- sarge-2.2.13-cyradm-tls/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:59:55.000000000 +0100
++++ /tmp/dpep.9Kj3l4/sarge-2.2.13-cyradm-tls/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:59:55.947293095 +0100
 @@ -61,6 +61,8 @@
  my $authname = $ENV{USER};
  my $realm = "";
@@ -1131,7 +1366,7 @@
      "e|exec:s" => \$ex,
      "f|execfile:s" => \$exfile,
      "help|?" => \$help,
-@@ -84,6 +88,14 @@
+@@ -84,6 +88,22 @@
  
  my $acapserver = $ARGV[0];
  
@@ -1143,10 +1378,18 @@
 +    $tls_keyfile = undef;
 +}
 +
++if ($notls) {
++    $tls_keyfile = undef;
++}
++
++if ($notls) {
++    $tls_keyfile = undef;
++}
++
  my $filehandle;
  my $interactive;
  
-@@ -156,7 +168,7 @@
+@@ -156,7 +176,7 @@
  
  sub show_help {
    print "Usage:\n";
@@ -1155,7 +1398,7 @@
    print "\n";
    print "help             - this screen\n";
    print "list             - list scripts on server\n";
-@@ -173,7 +185,7 @@
+@@ -173,7 +193,7 @@
  print "connecting to $acapserver\n";
  
  my $obj = sieve_get_handle($acapserver,
@@ -1164,7 +1407,7 @@
  
  if (!defined $obj) {
      die "unable to connect to server";
-@@ -318,6 +330,7 @@
+@@ -318,6 +338,7 @@
  
  sieveshell [B<--user>=I<user>] [B<--authname>=I<authname>] 
  [B<--realm>=I<realm>] [B<--password>=I<password>]
@@ -1172,7 +1415,7 @@
  [B<--exec>=I<script>] [B<--execfile>=I<file>] I<server>[B<:>I<port>]
  
  sieveshell B<--help>
-@@ -362,6 +375,22 @@
+@@ -362,6 +383,38 @@
  
  The realm to attempt authentication in.
  
@@ -1192,1203 +1435,22 @@
 +
 +Disable TLS.
 +
++=item B<-t> I<keyfile>, B<--tlskey>=I<keyfile>
++
++I<keyfile> contains the TLS public and private keys to use.
++
++=item B<-n>, B<--notls>
++
++Disable TLS.
++
++=item B<-t> I<keyfile>, B<--tlskey>=I<keyfile>
++
++I<keyfile> contains the TLS public and private keys to use.
++
++=item B<-n>, B<--notls>
++
++Disable TLS.
++
  =item B<-p> I<password>, B<--password>=I<password>
  
  The password to use when authenticating to server. Note that this
-#! /bin/sh /usr/share/dpatch/dpatch-run
-## fileUtqrG1.dpatch by Sven Mueller <sven at debian.org>
-##
-## All lines beginning with `## DP:' are a description of the patch.
-## DP: No description.
-
- at DPATCH@
-diff -urNad sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed /tmp/dpep.9n8yig/sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed
---- sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed	1970-01-01 01:00:00.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/debian/patched/66-cyradm-tls-enabled.dpatch.failed	2007-03-08 16:42:22.000000000 +0100
-@@ -0,0 +1,66 @@
-+patching file perl/imap/IMAP/Shell.pm
-+Hunk #1 FAILED at 436.
-+Hunk #2 FAILED at 449.
-+Hunk #3 FAILED at 469.
-+Hunk #4 succeeded at 795 with fuzz 2 (offset 18 lines).
-+Hunk #5 FAILED at 820.
-+4 out of 5 hunks FAILED -- saving rejects to file perl/imap/IMAP/Shell.pm.rej
-+patching file perl/imap/IMAP.pm
-+Hunk #1 FAILED at 196.
-+Hunk #2 succeeded at 302 with fuzz 2 (offset 41 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/imap/IMAP.pm.rej
-+patching file perl/imap/IMAP.xs
-+Hunk #1 FAILED at 57.
-+Hunk #2 succeeded at 457 with fuzz 2 (offset 39 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/imap/IMAP.xs.rej
-+patching file perl/imap/Makefile.PL
-+Hunk #1 FAILED at 1.
-+Hunk #2 FAILED at 65.
-+2 out of 2 hunks FAILED -- saving rejects to file perl/imap/Makefile.PL.rej
-+patching file perl/imap/cyradm.sh
-+Hunk #1 FAILED at 54.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/imap/cyradm.sh.rej
-+patching file perl/sieve/lib/isieve.c
-+Hunk #1 succeeded at 47 with fuzz 2 (offset 2 lines).
-+Hunk #2 succeeded at 72 with fuzz 2 (offset 11 lines).
-+Hunk #3 FAILED at 103.
-+Hunk #4 FAILED at 313.
-+Hunk #5 succeeded at 430 with fuzz 1 (offset 54 lines).
-+Hunk #6 succeeded at 702 with fuzz 2 (offset 58 lines).
-+Hunk #7 FAILED at 867.
-+3 out of 7 hunks FAILED -- saving rejects to file perl/sieve/lib/isieve.c.rej
-+patching file perl/sieve/lib/isieve.h
-+Hunk #1 FAILED at 67.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/sieve/lib/isieve.h.rej
-+patching file perl/sieve/lib/request.c
-+Hunk #1 FAILED at 168.
-+Hunk #2 succeeded at 669 with fuzz 2 (offset 30 lines).
-+1 out of 2 hunks FAILED -- saving rejects to file perl/sieve/lib/request.c.rej
-+patching file perl/sieve/lib/request.h
-+Hunk #1 FAILED at 91.
-+1 out of 1 hunk FAILED -- saving rejects to file perl/sieve/lib/request.h.rej
-+patching file perl/sieve/managesieve/Makefile.PL
-+Hunk #1 FAILED at 46.
-+Hunk #2 FAILED at 62.
-+2 out of 2 hunks FAILED -- saving rejects to file perl/sieve/managesieve/Makefile.PL.rej
-+patching file perl/sieve/managesieve/managesieve.xs
-+Hunk #1 FAILED at 211.
-+Hunk #2 succeeded at 253 with fuzz 2 (offset 3 lines).
-+Hunk #3 succeeded at 310 (offset 8 lines).
-+1 out of 3 hunks FAILED -- saving rejects to file perl/sieve/managesieve/managesieve.xs.rej
-+patching file perl/sieve/scripts/installsieve.pl
-+Hunk #1 FAILED at 44.
-+Hunk #2 FAILED at 56.
-+Hunk #3 succeeded at 76 with fuzz 2 (offset 7 lines).
-+Hunk #4 FAILED at 127.
-+3 out of 4 hunks FAILED -- saving rejects to file perl/sieve/scripts/installsieve.pl.rej
-+patching file perl/sieve/scripts/sieveshell.pl
-+Hunk #1 FAILED at 61.
-+Hunk #2 FAILED at 73.
-+Hunk #3 succeeded at 96 with fuzz 2 (offset 8 lines).
-+Hunk #4 FAILED at 172.
-+Hunk #5 FAILED at 189.
-+Hunk #6 FAILED at 334.
-+Hunk #7 succeeded at 388 with fuzz 2 (offset 17 lines).
-+5 out of 7 hunks FAILED -- saving rejects to file perl/sieve/scripts/sieveshell.pl.rej
-+md5sum: 63d18aece91f37515327eaefdb6d24ae  /tmp/dpep.9n8yig/sarge-2.2.13/debian/patches/66-cyradm-tls-enabled.dpatch
-diff -urNad sarge-2.2.13/perl/imap/IMAP/Shell.pm /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP/Shell.pm
---- sarge-2.2.13/perl/imap/IMAP/Shell.pm	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP/Shell.pm	2007-03-08 16:42:22.306556343 +0100
-@@ -436,9 +436,10 @@
- # (It's not as trivial as run() because it does things expected of standalone
- # programs, as opposed to things expected from within a program.)
- sub shell {
--  my ($server, $port, $authz, $auth, $systemrc, $userrc, $dorc, $mech, $pw) =
-+  my ($server, $port, $authz, $auth, $systemrc, $userrc, $dorc, $mech, $pw,
-+      $tlskey, $notls) =
-     ('', 143, undef, $ENV{USER} || $ENV{LOGNAME}, '/etc/cyradmrc.pl',
--     "$ENV{HOME}/.cyradmrc.pl", 1, undef, undef);
-+     "$ENV{HOME}/.cyradmrc.pl", 1, undef, undef, "", undef);
-   GetOptions('user|u=s' => \$auth,
- 	     'authz|z=s' => \$authz,
- 	     'rc|r!' => \$dorc,
-@@ -448,6 +449,8 @@
- 	     'port|p=i' => \$port,
- 	     'auth|a=s' => \$mech,
- 	     'password|w=s' => \$pw,
-+  	     'tlskey|t=s' => \$tlskey,
-+  	     'notls' => \$notls,
- 	     'help|h' => sub { cyradm_usage(); exit(0); }
- 	    );
-   if ($server ne '' && @ARGV) {
-@@ -466,7 +469,8 @@
- 			  -callback => \&_cb_eof,
- 			  -rock => \$cyradm});
-     $cyradm->authenticate(-authz => $authz, -user => $auth,
--			  -mechanism => $mech, -password => $pw)
-+			  -mechanism => $mech, -password => $pw,
-+			  -tlskey => $tlskey, -notls => $notls)
-       or die "cyradm: cannot authenticate to server" . (defined($mech)?" with $mech":"") . " as $auth\n";
-   }
-   my $fstk = [*STDIN, *STDOUT, *STDERR];
-@@ -773,6 +777,34 @@
-       $want = '-service';
-       next;
-     }
-+    if (Cyrus::IMAP::imclient_havetls()) {
-+      if ($opt ne '' && '-tlskey' =~ /^\Q$opt/ || $opt eq '--tlskey') {
-+	$want = '-tlskey';
-+	next;
-+      }
-+      if ($opt ne '' && '-notls' =~ /^\Q$opt/ || $opt eq '--notls') {
-+	$want = '-notls';
-+	next;
-+      }
-+      if ($opt =~ /^-/) {
-+	die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
-+	    "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
-+      }
-+    }
-+    if (Cyrus::IMAP::imclient_havetls()) {
-+      if ($opt ne '' && '-tlskey' =~ /^\Q$opt/ || $opt eq '--tlskey') {
-+	$want = '-tlskey';
-+	next;
-+      }
-+      if ($opt ne '' && '-notls' =~ /^\Q$opt/ || $opt eq '--notls') {
-+	$want = '-notls';
-+	next;
-+      }
-+      if ($opt =~ /^-/) {
-+	die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
-+	    "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
-+      }
-+    }
-     if ($opt =~ /^-/) {
-       die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
- 	  "                    [-service name] [user]\n";
-@@ -784,8 +816,13 @@
-   }
-   push(@nargv, @argv);
-   if (@nargv > 1) {
--    die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
--        "                    [-service name] [user]\n";
-+    if (Cyrus::IMAP::imclient_havetls()) {
-+      die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
-+          "                    [-service name] [-tlskey keyfile] [-notls] [user]\n";
-+    } else {
-+      die "usage: authenticate [-minssf N] [-maxssf N] [-mechanisms STR]\n".
-+          "                    [-service name] [user]\n";
-+    }
-   }
-   if (@nargv) {
-     $opts{-user} = shift(@nargv);
-diff -urNad sarge-2.2.13/perl/imap/IMAP.pm /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.pm
---- sarge-2.2.13/perl/imap/IMAP.pm	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.pm	2007-03-08 16:42:22.307556244 +0100
-@@ -196,16 +196,43 @@
- sub authenticate {
-   my ($self, $first) = @_;
-   my (%opts, $rc);
-+  my ($starttls, $logindisabled) = (0, 0);
- 
-   if (defined $first &&
--      $first =~ /^-\w+|Mechanism|Service|Authz|User|Minssf|Maxssf|Password$/) {
-+      $first =~ /^-\w+|Mechanism|Service|Authz|User|Minssf|Maxssf|Password|Tlskey|Notls|CAfile|CApath$/) {
-     (undef, %opts) = @_;
--    foreach (qw(mechanism service authz user minssf maxssf password)) {
-+    foreach (qw(mechanism service authz user minssf maxssf password tlskey notls)) {
-       $opts{'-' . $_} = $opts{ucfirst($_)} if !defined($opts{'-' . $_});
-     }
-   } else {
-     (undef, $opts{-mechanism}, $opts{-service}, $opts{-authz}, $opts{-user},
--     $opts{-minssf}, $opts{-maxssf}, $opts{-password}) = @_;
-+     $opts{-minssf}, $opts{-maxssf}, $opts{-password},
-+     $opts{-tlskey}, $opts{-notls}, $opts{-cafile}, $opts{-capath}) = @_;
-+  }
-+  if (havetls()) {
-+    if (!defined($opts{-tlskey})) {
-+      $opts{-tlskey} = "";
-+    }
-+    if (!defined($opts{-cafile})) {
-+      $opts{-cafile} = "";
-+    }
-+    if (!defined($opts{-capath})) {
-+      $opts{-capath} = "";
-+    }
-+    if ($opts{-notls}) {
-+      $opts{-tlskey} = undef;
-+    }
-+    $self->addcallback({-trigger => 'CAPABILITY',
-+			-callback => sub {my %a = @_;
-+					  map { $starttls = 1
-+						    if /^STARTTLS$/i;
-+					    }
-+					  split(/ /, $a{-text})}});
-+    $self->send(undef, undef, 'CAPABILITY');
-+    $self->addcallback({-trigger => 'CAPABILITY'});
-+    if ($starttls && defined($opts{-tlskey})) {
-+      $self->_starttls($opts{-tlskey}, $opts{-tlskey}, $opts{-cafile}, $opts{-capath});
-+    }
-   }
-   if (!defined($opts{-mechanism})) {
-     $opts{-mechanism} = '';
-@@ -234,6 +261,34 @@
- 			       $opts{-authz}, $opts{-user}, $opts{-password},
- 			       $opts{-minssf}, $opts{-maxssf});
-   }
-+  if (!$rc) {
-+    $self->addcallback({-trigger => 'CAPABILITY',
-+			-callback => sub {my %a = @_;
-+					  map { $logindisabled = 1
-+						    if /^LOGINDISABLED$/i;
-+					    }
-+					  split(/ /, $a{-text})}});
-+    $self->send(undef, undef, 'CAPABILITY');
-+    $self->addcallback({-trigger => 'CAPABILITY'});
-+    if ($logindisabled) {
-+      warn "Login disabled.\n";
-+      return undef;
-+    }
-+  }
-+  if (!$rc) {
-+    $self->addcallback({-trigger => 'CAPABILITY',
-+			-callback => sub {my %a = @_;
-+					  map { $logindisabled = 1
-+						    if /^LOGINDISABLED$/i;
-+					    }
-+					  split(/ /, $a{-text})}});
-+    $self->send(undef, undef, 'CAPABILITY');
-+    $self->addcallback({-trigger => 'CAPABILITY'});
-+    if ($logindisabled) {
-+      warn "Login disabled.\n";
-+      return undef;
-+    }
-+  }
-   $opts{-mechanism} ||= 'plain';
-   if (!$rc && $opts{-mechanism} =~ /(\b|^)(plain|login)($|\b)/i) {
-     $opts{-user} = getlogin if !defined($opts{-user});
-diff -urNad sarge-2.2.13/perl/imap/IMAP.xs /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.xs
---- sarge-2.2.13/perl/imap/IMAP.xs	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/IMAP.xs	2007-03-08 16:42:22.308556145 +0100
-@@ -57,6 +57,7 @@
- #include "xmalloc.h"
- 
- #include "cyrperl.h"
-+#include "config.h"
- 
- typedef struct xscyrus *Cyrus_IMAP;
- 
-@@ -417,6 +418,82 @@
- 	  ST(0) = &sv_yes;
- 	}
- 
-+int
-+imclient_havetls()
-+CODE:
-+#ifdef HAVE_SSL
-+	RETVAL = 1;
-+#else
-+	RETVAL = 0;
-+#endif /* HAVE_SSL */
-+OUTPUT:
-+	RETVAL
-+
-+SV *
-+imclient__starttls(client, tls_cert_file, tls_key_file, CAfile, CApath)
-+	Cyrus_IMAP client
-+	char* tls_cert_file
-+	char* tls_key_file
-+        char* CAfile
-+        char* CApath
-+PREINIT:
-+	int rc;
-+	int tls_layer;
-+CODE:
-+	ST(0) = sv_newmortal();
-+
-+	/* If the tls_{cert, key}_file parameters are undef, set to be NULL */
-+	if(!SvOK(ST(2))) tls_cert_file = NULL;
-+	if(!SvOK(ST(3))) tls_key_file = NULL;
-+#ifdef HAVE_SSL
-+	rc = imclient_starttls(client->imclient, tls_cert_file, tls_key_file, CAfile, CApath);
-+	if (rc)
-+	  ST(0) = &sv_no;
-+	else {
-+	  ST(0) = &sv_yes;
-+	}
-+#else
-+	ST(0) = &sv_no;
-+#endif /* HAVE_SSL */
-+
-+int
-+imclient_havetls()
-+CODE:
-+#ifdef HAVE_SSL
-+	RETVAL = 1;
-+#else
-+	RETVAL = 0;
-+#endif /* HAVE_SSL */
-+OUTPUT:
-+	RETVAL
-+
-+SV *
-+imclient__starttls(client, tls_cert_file, tls_key_file, CAfile, CApath)
-+	Cyrus_IMAP client
-+	char* tls_cert_file
-+	char* tls_key_file
-+        char* CAfile
-+        char* CApath
-+PREINIT:
-+	int rc;
-+	int tls_layer;
-+CODE:
-+	ST(0) = sv_newmortal();
-+
-+	/* If the tls_{cert, key}_file parameters are undef, set to be NULL */
-+	if(!SvOK(ST(2))) tls_cert_file = NULL;
-+	if(!SvOK(ST(3))) tls_key_file = NULL;
-+#ifdef HAVE_SSL
-+	rc = imclient_starttls(client->imclient, tls_cert_file, tls_key_file, CAfile, CApath);
-+	if (rc)
-+	  ST(0) = &sv_no;
-+	else {
-+	  ST(0) = &sv_yes;
-+	}
-+#else
-+	ST(0) = &sv_no;
-+#endif /* HAVE_SSL */
-+
- void
- imclient_addcallback(client, ...)
- 	Cyrus_IMAP client
-diff -urNad sarge-2.2.13/perl/imap/Makefile.PL /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/Makefile.PL
---- sarge-2.2.13/perl/imap/Makefile.PL	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/Makefile.PL	2007-03-08 16:42:22.308556145 +0100
-@@ -1,5 +1,4 @@
- # 
--# Copyright (c) 2000 Carnegie Mellon University.  All rights reserved.
- #
- # Redistribution and use in source and binary forms, with or without
- # modification, are permitted provided that the following conditions
-@@ -66,7 +65,7 @@
-     'OBJECT'    => 'IMAP.o',
-     'MYEXTLIB'  => '../../lib/libcyrus.a ../../lib/libcyrus_min.a',
-     'LIBS'	=> ["$BDB_LIB $SASL_LIB $OPENSSL_LIB $LIB_RT -lssl -lcrypto"],
--    'DEFINE'	=> '-DPERL_POLLUTE',     # e.g., '-DHAVE_SOMETHING' 
--    'INC'	=> "-I../../lib $SASL_INC $OPENSSL_INC", 
-+    'DEFINE'	=> '-DPERL_POLLUTE',    # e.g., '-DHAVE_SOMETHING' 
-+    'INC'	=> "-I../../lib -I../.. $SASL_INC $OPENSSL_INC", 
-     'EXE_FILES' => [cyradm],
- );
-diff -urNad sarge-2.2.13/perl/imap/cyradm.sh /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/cyradm.sh
---- sarge-2.2.13/perl/imap/cyradm.sh	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/imap/cyradm.sh	2007-03-08 16:42:22.309556046 +0100
-@@ -54,7 +54,8 @@
- =head1 SYNOPSIS
- 
-   $ cyradm [--user user] [--[no]rc] [--systemrc file] [--userrc file] \
--  > [--port n] [--auth mechanism] [--server] server
-+  > [--port n] [--auth mechanism] [--tlskey keyfile] [--notls] \
-+  > [--server] server
- 
- but possibly
- 
-diff -urNad sarge-2.2.13/perl/sieve/lib/isieve.c /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.c
---- sarge-2.2.13/perl/sieve/lib/isieve.c	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.c	2007-03-08 16:42:22.311555847 +0100
-@@ -45,6 +45,10 @@
- #include <config.h>
- #endif
- 
-+#include <assert.h>
-+
-+#include <assert.h>
-+
- #ifdef HAVE_UNISTD_H
- #include <unistd.h>
- #endif
-@@ -59,6 +63,24 @@
- #include <sasl/sasl.h>
- #include <sasl/saslutil.h>
- 
-+#ifdef HAVE_SSL
-+#include <openssl/lhash.h>
-+#include <openssl/bn.h>
-+#include <openssl/err.h>
-+#include <openssl/pem.h>
-+#include <openssl/x509.h>
-+#include <openssl/ssl.h>
-+#endif /* HAVE_SSL */
-+
-+#ifdef HAVE_SSL
-+#include <openssl/lhash.h>
-+#include <openssl/bn.h>
-+#include <openssl/err.h>
-+#include <openssl/pem.h>
-+#include <openssl/x509.h>
-+#include <openssl/ssl.h>
-+#endif /* HAVE_SSL */
-+
- #include "isieve.h"
- #include "lex.h"
- #include "request.h"
-@@ -81,13 +103,27 @@
-     sasl_callback_t *refer_callbacks;
- 
-     int version;
-+    int starttls;
-+    char *tls_keyfile;
- 
-     struct protstream *pin;
-     struct protstream *pout;
-+
-+#ifdef HAVE_SSL
-+    SSL_CTX *tls_ctx;
-+    SSL *tls_conn;
-+#endif /* HAVE_SSL */
- };
- 
- void fillin_interactions(sasl_interact_t *tlist);
- 
-+#ifdef HAVE_SSL
-+static int isieve_starttls(isieve_t *obj, int verifydepth,
-+			   char *var_tls_cert_file, char *var_tls_key_file,
-+			   int *layer);
-+#endif /* HAVE_SSL */
-+
-+
- /* we need this separate from the free() call so that we can reuse
-  * the same memory for referrals */
- static void sieve_dispose(isieve_t *obj) 
-@@ -277,7 +313,7 @@
-       } else if (strcasecmp(attr,"IMPLEMENTATION")==0) {
- 
-       } else if (strcasecmp(attr,"STARTTLS")==0) {
--	  /* TODO */
-+	  obj->starttls = 1;
-       } else if (val && strncmp(val,"SASL=",5)==0) {
- 	  obj->version = OLD_VERSION;
- 	  cap = (char *) xmalloc(strlen(val));
-@@ -351,6 +387,64 @@
-   return STAT_CONT;
- }
- 
-+int auth_starttls(isieve_t *obj, char *tls_keyfile,
-+		  char **mechlist, char **errstr)
-+{
-+  unsigned ext_ssf = 0;
-+  int ret;
-+  char *refer_to;
-+
-+  if (!obj->tls_keyfile) obj->tls_keyfile = tls_keyfile;
-+
-+  if (!obj->starttls || !obj->tls_keyfile) return 0;
-+
-+#ifdef HAVE_SSL
-+  ret = starttls(obj->version, obj->pout, obj->pin, &refer_to, errstr);
-+  /* xxx handle referrals */
-+  if (ret != 0) return -1;
-+
-+  ret = isieve_starttls(obj, 0, tls_keyfile, tls_keyfile, &ext_ssf);
-+  if (ret != 0) return -1;
-+
-+  prot_printf(obj->pout, "CAPABILITY\r\n");
-+  prot_flush(obj->pout);
-+  
-+  if (*mechlist) free(*mechlist);
-+  *mechlist = read_capability(obj);
-+#endif /* HAVE_SSL */
-+
-+  return 0;
-+}
-+
-+int auth_starttls(isieve_t *obj, char *tls_keyfile,
-+		  char **mechlist, char **errstr)
-+{
-+  unsigned ext_ssf = 0;
-+  int ret;
-+  char *refer_to;
-+
-+  if (!obj->tls_keyfile) obj->tls_keyfile = tls_keyfile;
-+
-+  if (!obj->starttls || !obj->tls_keyfile) return 0;
-+
-+#ifdef HAVE_SSL
-+  ret = starttls(obj->version, obj->pout, obj->pin, &refer_to, errstr);
-+  /* xxx handle referrals */
-+  if (ret != 0) return -1;
-+
-+  ret = isieve_starttls(obj, 0, tls_keyfile, tls_keyfile, &ext_ssf);
-+  if (ret != 0) return -1;
-+
-+  prot_printf(obj->pout, "CAPABILITY\r\n");
-+  prot_flush(obj->pout);
-+  
-+  if (*mechlist) free(*mechlist);
-+  *mechlist = read_capability(obj);
-+#endif /* HAVE_SSL */
-+
-+  return 0;
-+}
-+
- 
- int auth_sasl(char *mechlist, isieve_t *obj, const char **mechusing,
- 	      char **errstr)
-@@ -590,6 +684,14 @@
-     /* Authenticate */
-     mechlist = read_capability(obj_new);
- 
-+    /* Perform STARTTLS */
-+    ret = auth_starttls(obj, obj->tls_keyfile, &mechlist, &errstr);
-+   if (ret) return STAT_NO;
-+
-+    /* Perform STARTTLS */
-+    ret = auth_starttls(obj, obj->tls_keyfile, &mechlist, &errstr);
-+   if (ret) return STAT_NO;
-+
-     do {
- 	mtried = NULL;
- 	ret = auth_sasl(mechlist, obj_new, &mtried, &errstr);
-@@ -751,3 +853,342 @@
- 
-     return ret;
- }
-+
-+/*************** All these functions help do the starttls; these are copied from imclient.c ********/
-+#ifdef HAVE_SSL
-+
-+static int verify_depth;
-+static int verify_error = X509_V_OK;
-+
-+#define CCERT_BUFSIZ 256
-+static char peer_CN[CCERT_BUFSIZ];
-+static char issuer_CN[CCERT_BUFSIZ];
-+
-+/*
-+  * Set up the cert things on the server side. We do need both the
-+  * private key (in key_file) and the cert (in cert_file).
-+  * Both files may be identical.
-+  *
-+  * This function is taken from OpenSSL apps/s_cb.c
-+  */
-+
-+static int set_cert_stuff(SSL_CTX * ctx, char *cert_file, char *key_file)
-+{
-+    if (cert_file != NULL) {
-+	if (SSL_CTX_use_certificate_file(ctx, cert_file,
-+					 SSL_FILETYPE_PEM) <= 0) {
-+	  printf("[ unable to get certificate from '%s' ]\n", cert_file);
-+	  return (0);
-+	}
-+	if (key_file == NULL)
-+	    key_file = cert_file;
-+	if (SSL_CTX_use_PrivateKey_file(ctx, key_file,
-+					SSL_FILETYPE_PEM) <= 0) {
-+	  printf("[ unable to get private key from '%s' ]\n", key_file);
-+	  return (0);
-+	}
-+	/* Now we know that a key and cert have been set against
-+         * the SSL context */
-+	if (!SSL_CTX_check_private_key(ctx)) {
-+	  printf("[ Private key does not match the certificate public key ]\n");
-+	  return (0);
-+	}
-+    }
-+    return (1);
-+}
-+
-+/* taken from OpenSSL apps/s_cb.c */
-+
-+static int verify_callback(int ok, X509_STORE_CTX * ctx)
-+{
-+    char    buf[256];
-+    X509   *err_cert;
-+    int     err;
-+    int     depth;
-+
-+    err_cert = X509_STORE_CTX_get_current_cert(ctx);
-+    err = X509_STORE_CTX_get_error(ctx);
-+    depth = X509_STORE_CTX_get_error_depth(ctx);
-+
-+    X509_NAME_oneline(X509_get_subject_name(err_cert), buf, 256);
-+
-+    /*    if (verbose==1)
-+	  printf("Peer cert verify depth=%d %s\n", depth, buf);*/
-+
-+    if (!ok) {
-+      printf("verify error:num=%d:%s\n", err,
-+	     X509_verify_cert_error_string(err));
-+	if (verify_depth >= depth) {
-+	    ok = 1;
-+	    verify_error = X509_V_OK;
-+	} else {
-+	    ok = 0;
-+	    verify_error = X509_V_ERR_CERT_CHAIN_TOO_LONG;
-+	}
-+    }
-+    switch (ctx->error) {
-+    case X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT:
-+	X509_NAME_oneline(X509_get_issuer_name(ctx->current_cert), buf, 256);
-+	printf("issuer= %s\n", buf);
-+	break;
-+    case X509_V_ERR_CERT_NOT_YET_VALID:
-+    case X509_V_ERR_ERROR_IN_CERT_NOT_BEFORE_FIELD:
-+      printf("cert not yet valid\n");
-+      break;
-+    case X509_V_ERR_CERT_HAS_EXPIRED:
-+    case X509_V_ERR_ERROR_IN_CERT_NOT_AFTER_FIELD:
-+      printf("cert has expired\n");
-+      break;
-+    }
-+
-+    /*    if (verbose==1)
-+	  printf("verify return:%d\n", ok);*/
-+
-+    return (ok);
-+}
-+
-+
-+/* taken from OpenSSL apps/s_cb.c */
-+static RSA *tmp_rsa_cb(SSL *s __attribute__((unused)),
-+		       int export __attribute__((unused)),
-+		       int keylength)
-+{
-+    static RSA *rsa_tmp = NULL;
-+
-+    if (rsa_tmp == NULL) {
-+	rsa_tmp = RSA_generate_key(keylength, RSA_F4, NULL, NULL);
-+    }
-+    return (rsa_tmp);
-+}
-+
-+/*
-+ * Seed the random number generator.
-+ */
-+static int tls_rand_init(void)
-+{
-+#ifdef EGD_SOCKET
-+    return (RAND_egd(EGD_SOCKET));
-+#else
-+    /* otherwise let OpenSSL do it internally */
-+    return 0;
-+#endif
-+}
-+
-+static char *var_tls_CAfile="";
-+static char *var_tls_CApath="";
-+ /*
-+  * This is the setup routine for the SSL client. 
-+  *
-+  * The skeleton of this function is taken from OpenSSL apps/s_client.c.
-+  */
-+
-+static int tls_init_clientengine(isieve_t *obj,
-+				 int verifydepth, char *var_tls_cert_file, char *var_tls_key_file)
-+{
-+    int     off = 0;
-+    int     verify_flags = SSL_VERIFY_NONE;
-+    char   *CApath;
-+    char   *CAfile;
-+    char   *c_cert_file;
-+    char   *c_key_file;
-+
-+    assert(obj);
-+
-+    SSL_load_error_strings();
-+    SSLeay_add_ssl_algorithms();
-+    if (tls_rand_init() == -1) {
-+	printf("[ TLS engine: cannot seed PRNG ]\n");
-+	return -1;
-+    }
-+
-+    obj->tls_ctx = SSL_CTX_new(TLSv1_client_method());
-+    if (obj->tls_ctx == NULL) {
-+	return -1;
-+    };
-+
-+    off |= SSL_OP_ALL;		/* Work around all known bugs */
-+    SSL_CTX_set_options(obj->tls_ctx, off);
-+    
-+    /* debugging   SSL_CTX_set_info_callback(obj->tls_ctx, apps_ssl_info_callback); */
-+
-+    if (strlen(var_tls_CAfile) == 0)
-+	CAfile = NULL;
-+    else
-+	CAfile = var_tls_CAfile;
-+    if (strlen(var_tls_CApath) == 0)
-+	CApath = NULL;
-+    else
-+	CApath = var_tls_CApath;
-+
-+    if (CAfile || CApath)
-+	if ((!SSL_CTX_load_verify_locations(obj->tls_ctx, CAfile, CApath)) ||
-+	    (!SSL_CTX_set_default_verify_paths(obj->tls_ctx))) {
-+	    printf("[ TLS engine: cannot load CA data ]\n");
-+	    return -1;
-+	}
-+    if (strlen(var_tls_cert_file) == 0)
-+	c_cert_file = NULL;
-+    else
-+	c_cert_file = var_tls_cert_file;
-+    if (strlen(var_tls_key_file) == 0)
-+	c_key_file = NULL;
-+    else
-+	c_key_file = var_tls_key_file;
-+
-+    if (c_cert_file || c_key_file)
-+	if (!set_cert_stuff(obj->tls_ctx, c_cert_file, c_key_file)) {
-+	    printf("[ TLS engine: cannot load cert/key data ]\n");
-+	    return -1;
-+	}
-+    SSL_CTX_set_tmp_rsa_callback(obj->tls_ctx, tmp_rsa_cb);
-+
-+    verify_depth = verifydepth;
-+    SSL_CTX_set_verify(obj->tls_ctx, verify_flags, verify_callback);
-+
-+    return 0;
-+}
-+
-+
-+static int tls_start_clienttls(isieve_t *obj,
-+			       unsigned *layer, char **authid, int fd)
-+{
-+    int     sts;
-+    SSL_SESSION *session;
-+    SSL_CIPHER *cipher;
-+    X509   *peer;
-+    const char *tls_protocol = NULL;
-+    const char *tls_cipher_name = NULL;
-+    int tls_cipher_usebits = 0;
-+    int tls_cipher_algbits = 0;
-+    char *tls_peer_CN = "";
-+    char *tls_issuer_CN = NULL;
-+
-+    if (obj->tls_conn == NULL) {
-+	obj->tls_conn = (SSL *) SSL_new(obj->tls_ctx);
-+    }
-+    if (obj->tls_conn == NULL) {
-+	printf("Could not allocate 'con' with SSL_new()\n");
-+	return -1;
-+    }
-+    SSL_clear(obj->tls_conn);
-+
-+    if (!SSL_set_fd(obj->tls_conn, fd)) {
-+      printf("SSL_set_fd failed\n");
-+      return -1;
-+    }
-+
-+    /*SSL_set_read_ahead(obj->tls_conn, 1);*/
-+
-+    /*
-+     * This is the actual handshake routine. It will do all the negotiations
-+     * and will check the client cert etc.
-+     */
-+    SSL_set_connect_state(obj->tls_conn);
-+
-+
-+    /*
-+     * We do have an SSL_set_fd() and now suddenly a BIO_ routine is called?
-+     * Well there is a BIO below the SSL routines that is automatically
-+     * created for us, so we can use it for debugging purposes.
-+     */
-+    /*    if (verbose==1) */
-+    /*    BIO_set_callback(SSL_get_rbio(obj->tls_conn), bio_dump_cb);*/
-+
-+    /* Dump the negotiation for loglevels 3 and 4 */
-+
-+    if ((sts = SSL_connect(obj->tls_conn)) <= 0) {
-+	printf("[ SSL_connect error %d ]\n", sts); /* xxx get string error? */
-+	session = SSL_get_session(obj->tls_conn);
-+	if (session) {
-+	    SSL_CTX_remove_session(obj->tls_ctx, session);
-+	    printf("[ SSL session removed ]\n");
-+	}
-+	if (obj->tls_conn!=NULL)
-+	    SSL_free(obj->tls_conn);
-+	obj->tls_conn = NULL;
-+	return -1;
-+    }
-+
-+    /*
-+     * Lets see, whether a peer certificate is availabe and what is
-+     * the actual information. We want to save it for later use.
-+     */
-+    peer = SSL_get_peer_certificate(obj->tls_conn);
-+    if (peer != NULL) {
-+	X509_NAME_get_text_by_NID(X509_get_subject_name(peer),
-+			  NID_commonName, peer_CN, CCERT_BUFSIZ);
-+	tls_peer_CN = peer_CN;
-+	X509_NAME_get_text_by_NID(X509_get_issuer_name(peer),
-+			  NID_commonName, issuer_CN, CCERT_BUFSIZ);
-+	/*	if (verbose==1)
-+		printf("subject_CN=%s, issuer_CN=%s\n", peer_CN, issuer_CN);*/
-+	tls_issuer_CN = issuer_CN;
-+
-+    }
-+    tls_protocol = SSL_get_version(obj->tls_conn);
-+    cipher = SSL_get_current_cipher(obj->tls_conn);
-+    tls_cipher_name = SSL_CIPHER_get_name(cipher);
-+    tls_cipher_usebits = SSL_CIPHER_get_bits(cipher,
-+						 &tls_cipher_algbits);
-+
-+    if (layer!=NULL)
-+      *layer = tls_cipher_usebits;
-+
-+    if (authid!=NULL)
-+      *authid = tls_peer_CN;
-+
-+    /*    printf("TLS connection established: %s with cipher %s (%d/%d bits)\n",
-+	   tls_protocol, tls_cipher_name,
-+	   tls_cipher_usebits, tls_cipher_algbits);*/
-+    return 0;
-+}
-+
-+static int isieve_starttls(isieve_t *obj,
-+			     int verifydepth __attribute__((unused)),
-+			     char *var_tls_cert_file, 
-+			     char *var_tls_key_file,
-+			     int *layer __attribute__((unused)))
-+{
-+  int result;
-+  unsigned ssf;
-+  char *auth_id;
-+  
-+  result=tls_init_clientengine(obj, 10, var_tls_cert_file, var_tls_key_file);
-+  if (result!=0)
-+  {
-+    printf("[ TLS engine failed ]\n");
-+    return 1;
-+  } else {
-+    result=tls_start_clienttls(obj, &ssf, &auth_id, obj->sock);
-+    
-+    if (result!=0) {
-+      printf("[ TLS negotiation did not succeed ]\n");
-+      return 1;
-+    }
-+  }
-+
-+  /* turn non-blocking i/o back on */
-+
-+
-+  /* TLS negotiation succeeded */
-+
-+  auth_id=""; /* xxx this really should be peer_CN or
-+		 issuer_CN but I can't figure out which is
-+		 which at the moment */
-+
-+  /* tell SASL about the negotiated layer */
-+  result=sasl_setprop(obj->conn,
-+		      SASL_SSF_EXTERNAL,
-+		      &ssf);
-+  if (result!=SASL_OK) return 1;
-+  result=sasl_setprop(obj->conn,
-+		      SASL_AUTH_EXTERNAL,
-+		      auth_id);
-+  if (result!=SASL_OK) return 1;
-+
-+  prot_settls (obj->pin,  obj->tls_conn);
-+  prot_settls (obj->pout, obj->tls_conn);
-+
-+  return 0;
-+}
-+#endif /* HAVE_SSL */
-diff -urNad sarge-2.2.13/perl/sieve/lib/isieve.h /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.h
---- sarge-2.2.13/perl/sieve/lib/isieve.h	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/isieve.h	2007-03-08 16:42:22.312555748 +0100
-@@ -67,6 +67,7 @@
-     STAT_OK = 2
- } imt_stat;
- 
-+int auth_starttls(isieve_t *obj, char *tls_keyfile, char **mechlist, char **errstr);
- int auth_sasl(char *mechlist, isieve_t *obj, const char **mechusing, char **errstr);
- 
- int isieve_logout(isieve_t **obj);
-diff -urNad sarge-2.2.13/perl/sieve/lib/request.c /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.c
---- sarge-2.2.13/perl/sieve/lib/request.c	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.c	2007-03-08 16:42:22.313555649 +0100
-@@ -168,22 +168,24 @@
-       /* SASL response */
-       res = yylex(&state, pin);
-       if(res == ' ') {
--	  if (yylex(&state, pin) != '(')
--	      parseerror("expected LPAREN");
--	  
--	  if (yylex(&state, pin)==TOKEN_SASL) {
--	      if (yylex(&state, pin)!=' ')
--		  parseerror("expected space");
--	      if (yylex(&state, pin)!=STRING)
--		  parseerror("expected string");
-+	  res = yylex(&state, pin);
-+	  if (res == '(') {
-+	      if (yylex(&state, pin)==TOKEN_SASL) {
-+	          if (yylex(&state, pin)!=' ')
-+		      parseerror("expected space");
-+	          if (yylex(&state, pin)!=STRING)
-+		      parseerror("expected string");
- 
--	      *refer_to = xstrdup(string_DATAPTR(state.str));
-+	          *refer_to = xstrdup(string_DATAPTR(state.str));
- 
--	      if (yylex(&state, pin)!=')')
--		  parseerror("expected RPAREN");
--	  } else {
--	      parseerror("unexpected response code with OK response");
-+	          if (yylex(&state, pin) != ')')
-+		      parseerror("expected RPAREN");
-+		  res = yylex(&state, pin);
-+		  if (res == ' ') res = yylex(&state, pin);
-+	      }
- 	  }
-+	  if (res != STRING)
-+	      parseerror("unexpected response code with OK response");
-       } else if (version != OLD_VERSION && res == EOL) {
- 	  return r;
-       }
-@@ -637,3 +639,59 @@
-   return 0;
- 
- }
-+
-+
-+int starttls(int version, struct protstream *pout, struct protstream *pin,
-+	     char **refer_to, char **errstrp)
-+{
-+  lexstate_t state;
-+  int res;
-+  int ret;
-+  mystring_t *errstr;
-+
-+  prot_printf(pout, "STARTTLS\r\n");
-+  prot_flush(pout);
-+	    
-+  res = yylex(&state, pin);
-+
-+  ret = handle_response(res, version, pin, refer_to, &errstr);
-+
-+  /* if command failed */
-+  if(ret == -2 && *refer_to) {
-+      return -2;
-+  } else if (ret != 0) {
-+      *errstrp = malloc(128);
-+      snprintf(*errstrp, 127, 
-+	       "Starttls: %s",string_DATAPTR(errstr));
-+      return -1;
-+  }
-+  return 0;
-+}
-+
-+
-+int starttls(int version, struct protstream *pout, struct protstream *pin,
-+	     char **refer_to, char **errstrp)
-+{
-+  lexstate_t state;
-+  int res;
-+  int ret;
-+  mystring_t *errstr;
-+
-+  prot_printf(pout, "STARTTLS\r\n");
-+  prot_flush(pout);
-+	    
-+  res = yylex(&state, pin);
-+
-+  ret = handle_response(res, version, pin, refer_to, &errstr);
-+
-+  /* if command failed */
-+  if(ret == -2 && *refer_to) {
-+      return -2;
-+  } else if (ret != 0) {
-+      *errstrp = malloc(128);
-+      snprintf(*errstrp, 127, 
-+	       "Starttls: %s",string_DATAPTR(errstr));
-+      return -1;
-+  }
-+  return 0;
-+}
-diff -urNad sarge-2.2.13/perl/sieve/lib/request.h /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.h
---- sarge-2.2.13/perl/sieve/lib/request.h	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/lib/request.h	2007-03-08 16:42:22.313555649 +0100
-@@ -91,5 +91,7 @@
- 
- void parseerror(char *str);
- 
-+int starttls(int version, struct protstream *pout, struct protstream *pin,
-+	    char **refer_to, char **errstr);
- 
- #endif
-diff -urNad sarge-2.2.13/perl/sieve/managesieve/Makefile.PL /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/Makefile.PL
---- sarge-2.2.13/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/Makefile.PL	2007-03-08 16:42:22.313555649 +0100
-@@ -46,6 +46,7 @@
- my $SASL_LIB = $ENV{SASL_LIB} || "-lsasl2";
- my $OPENSSL_INC = $ENV{OPENSSL_INC};
- my $OPENSSL_LIB = $ENV{OPENSSL_LIB};
-+my $HAVE_SSL = $OPENSSL_LIB ? "-DHAVE_SSL" : '';
- my $BDB_INC = $ENV{BDB_INC};
- my $BDB_LIB = $ENV{BDB_LIB};
- 
-@@ -61,7 +62,7 @@
-     'VERSION_FROM' => 'managesieve.pm', # finds $VERSION
-     'MYEXTLIB'  => '../lib/isieve.o ../lib/lex.o ../lib/mystring.o ../lib/request.o ../../../lib/libcyrus.a ../../../lib/libcyrus_min.a',
-     'LIBS'	=> ["$BDB_LIB $SASL_LIB $OPENSSL_LIB $LIB_RT -lssl -lcrypto"], 
--    'DEFINE'	=> '-DPERL_POLLUTE',     # e.g., '-DHAVE_SOMETHING' 
-+    'DEFINE'	=> "-DPERL_POLLUTE $HAVE_SSL",     # e.g., '-DHAVE_SOMETHING' 
-     'INC'	=> "-I../lib/ -I../../../lib/ $SASL_INC $OPENSSL_INC",
-     'CC'	=> $ENV{CC},
-     'LD'	=> $ENV{CC}
-diff -urNad sarge-2.2.13/perl/sieve/managesieve/managesieve.xs /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/managesieve.xs
---- sarge-2.2.13/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:31:22.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/managesieve/managesieve.xs	2007-03-08 16:42:22.314555550 +0100
-@@ -211,12 +211,13 @@
- 
- 
- Sieveobj
--sieve_get_handle(servername, username_cb, authname_cb, password_cb, realm_cb)
-+sieve_get_handle(servername, username_cb, authname_cb, password_cb, realm_cb, tls_keyfile)
-   char *servername
-   SV *username_cb
-   SV *authname_cb
-   SV *password_cb
-   SV *realm_cb
-+  char *tls_keyfile
- 
-   PREINIT:
-   Sieveobj ret = NULL;
-@@ -249,6 +250,10 @@
-   callbacks[3].context = password_cb;
-   callbacks[4].id = SASL_CB_LIST_END;
- 
-+  if (!SvOK(ST(5))) tls_keyfile = NULL;
-+
-+  if (!SvOK(ST(5))) tls_keyfile = NULL;
-+
-   /* see if we have server:port (or IPv6, etc)*/
-   p = servername;
-   if (*servername == '[') {
-@@ -299,6 +304,16 @@
- 	XSRETURN_UNDEF;
-   }
- 
-+  if (auth_starttls(obj, tls_keyfile, &mlist, &ret->errstr) != 0) {
-+	globalerr = "starttls failed";
-+	XSRETURN_UNDEF;
-+  }
-+
-+  if (auth_starttls(obj, tls_keyfile, &mlist, &ret->errstr) != 0) {
-+	globalerr = "starttls failed";
-+	XSRETURN_UNDEF;
-+  }
-+
-   /* loop through all the mechanisms */
-   do {
-     mtried = NULL;
-diff -urNad sarge-2.2.13/perl/sieve/scripts/installsieve.pl /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/installsieve.pl
---- sarge-2.2.13/perl/sieve/scripts/installsieve.pl	2007-03-08 16:40:29.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/installsieve.pl	2007-03-08 16:42:22.315555451 +0100
-@@ -44,6 +44,7 @@
- use Getopt::Long;
- 
- $username = "";
-+$tls_keyfile = "";
- 
- print "NOTE: This program is deprecated. Please use sieveshell\n";
- print "\n";
-@@ -55,6 +56,8 @@
- 		  "a|activates:s" => \$activates,
- 		  "d|deletes:s" => \$deletes,
- #		  "m|mechanism:s" => \$mech,
-+    		  "t|tlskey:s" => \$tls_keyfile,
-+		  "n|notls" => \$notls,
- 		  "g|gets:s" => \$gets,
-                   "u|username:s" => \$username,
- #		  "w|password:s" => \$pass
-@@ -66,6 +69,14 @@
- 
- $acapserver = $ARGV[0];
- 
-+if ($notls) {
-+    $tls_keyfile = undef;
-+}
-+
-+if ($notls) {
-+    $tls_keyfile = undef;
-+}
-+
- sub list_cb {
- 
-   my($name, $isactive) = @_ ;
-@@ -113,11 +124,13 @@
-   print "  -g <name>    Get script <name> and save to disk\n";
-   print "  -u <user>    Userid/Authname to use\n";
- #  print "  -w <passwd>  Specify password (Should only be used for automated scripts)\n";
-+  print "  -t <keyfile> TLS keyfile to use\n";
-+  print "  -n           Don't use TLS\n";
-   print "\n";
- }
- 
- #main code
--my $obj = sieve_get_handle($acapserver,"prompt","prompt","prompt","prompt");
-+my $obj = sieve_get_handle($acapserver,"prompt","prompt","prompt","prompt", $tls_keyfile);
- 
- if (!defined $obj) {
-   die "Unable to connect to server";
-diff -urNad sarge-2.2.13/perl/sieve/scripts/sieveshell.pl /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/sieveshell.pl
---- sarge-2.2.13/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:40:31.000000000 +0100
-+++ /tmp/dpep.9n8yig/sarge-2.2.13/perl/sieve/scripts/sieveshell.pl	2007-03-08 16:42:22.316555352 +0100
-@@ -61,6 +61,8 @@
- my $authname = $ENV{USER};
- my $realm = "";
- my $password;
-+my $tls_keyfile = "";
-+my $notls = 0;
- my $ex = "";
- my $exfile = "";
- my $help = 0;
-@@ -71,6 +73,8 @@
-     "u|username:s" => \$username,
-     "r|realm:s" => \$realm,
-     "p|password:s" => \$password,
-+    "t|tlskey:s" => \$tls_keyfile,
-+    "n|notls" => \$notls,
-     "e|exec:s" => \$ex,
-     "f|execfile:s" => \$exfile,
-     "help|?" => \$help,
-@@ -84,6 +88,14 @@
- 
- my $acapserver = $ARGV[0];
- 
-+if ($notls) {
-+    $tls_keyfile = undef;
-+}
-+
-+if ($notls) {
-+    $tls_keyfile = undef;
-+}
-+
- my $filehandle;
- my $interactive;
- 
-@@ -156,7 +168,7 @@
- 
- sub show_help {
-   print "Usage:\n";
--  print "  sieveshell [-u username] [-a authname] [-r realm] <server>\n";
-+  print "  sieveshell [-u username] [-a authname] [-r realm] [-t keyfile] [-n] <server>\n";
-   print "\n";
-   print "help             - this screen\n";
-   print "list             - list scripts on server\n";
-@@ -173,7 +185,7 @@
- print "connecting to $acapserver\n";
- 
- my $obj = sieve_get_handle($acapserver,
--			   "prompt", "prompt", "prompt", "prompt");
-+			   "prompt", "prompt", "prompt", "prompt", $tls_keyfile);
- 
- if (!defined $obj) {
-     die "unable to connect to server";
-@@ -318,6 +330,7 @@
- 
- sieveshell [B<--user>=I<user>] [B<--authname>=I<authname>] 
- [B<--realm>=I<realm>] [B<--password>=I<password>]
-+[B<--tlskey>=I<keyfile>] [B<--notls>]
- [B<--exec>=I<script>] [B<--execfile>=I<file>] I<server>[B<:>I<port>]
- 
- sieveshell B<--help>
-@@ -362,6 +375,22 @@
- 
- The realm to attempt authentication in.
- 
-+=item B<-t> I<keyfile>, B<--tlskey>=I<keyfile>
-+
-+I<keyfile> contains the TLS public and private keys to use.
-+
-+=item B<-n>, B<--notls>
-+
-+Disable TLS.
-+
-+=item B<-t> I<keyfile>, B<--tlskey>=I<keyfile>
-+
-+I<keyfile> contains the TLS public and private keys to use.
-+
-+=item B<-n>, B<--notls>
-+
-+Disable TLS.
-+
- =item B<-p> I<password>, B<--password>=I<password>
- 
- The password to use when authenticating to server. Note that this




More information about the Pkg-Cyrus-imapd-Debian-devel mailing list