Subject: Developers of Sympa
List archive
- From: Christian Mock <address@concealed>
- To: address@concealed
- Subject: patches for S/MIME
- Date: Fri, 22 Jun 2001 17:26:53 +0200
hello,
using sympa for a project which relies on S/MIME signatures and encryption, I
created the following patchset.
it is against 3.1.1, as 3.2.1 came along only when the project was nearly
finished; I hope it is usable all the same.
the patch does the following:
- a new authentication method (for scenari) "smime_enc", which means that the
incoming mail is encrypted and signed with S/MIME
- smime_encrypt and some other stuff was broken -- apparently the definition
of the sub plus some invocations were changed, but not all, so I re-defined
the sub to be compatible with both kinds of usage.
- smtp::mailto had a problem with signed/encrypted mails, it tries to re-mail
the original encrypted mail, it's now called with "_ALTERED_".
- one austrian certification authority, a-sign.datakom.at, encodes the email
in the subject's CN instead of a separate /email= attribute, so tools.pl and
wwsympa.pl (for SSL client cert authentication) had to be changed
- what I've also done, but not included in the patch-set, is to change the
"mailto" URLs in the subscription auth messages so the auth command is sent
in
the body instead of the subject line -- this is needed with S/MIME auth as
the
subject is not signed and therefore commands in the subject are not accepted
(I'm not sure if the "body=" attribute in mailto: URLs is really a standard;
it works with netscape, which is enough for me ATM.
sympa is working in an initial setup with those patches and all the
functionality described, it's not in production use yet, so beware.
I also noticed that there are some traces in the code related to PGP -- is
anybody actively working on providing the same functionality with PGP as with
S/MIME in sympa?
ciao,
cm.
--- wwsympa/wwsympa.fcgi Tue Apr 24 15:01:49 2001
+++ /usr/local/cgi-bin/wwsympa.fcgi Tue Jun 12 14:21:43 2001
@@ -340,8 +343,16 @@
## Authentication
## use https client certificat information if define.
- if (($ENV{'SSL_CLIENT_S_DN_Email'}) && ($ENV{'SSL_CLIENT_VERIFY'} eq
'SUCCESS')) {
+ ## With some CAs, e.g. a-sign.datakom.at, SSL_CLIENT_S_DN_Email isn't
+ ## set, but SSL_CLIENT_S_DN_CN is like "Christian Mock
address@concealed"
+# if (($ENV{'SSL_CLIENT_S_DN_Email'}) && ($ENV{'SSL_CLIENT_VERIFY'} eq
'SUCCESS')) {
+ if (($ENV{'SSL_CLIENT_VERIFY'} eq 'SUCCESS') &&
+ ($ENV{'SSL_CLIENT_S_DN_Email'} || ($ENV{'SSL_CLIENT_S_DN_CN'} =~
/MAIL=/))) {
$param->{'user'}{'email'} = lc($ENV{'SSL_CLIENT_S_DN_Email'});
+ if(!$ENV{'SSL_CLIENT_S_DN_Email'}) {
+ $ENV{'SSL_CLIENT_S_DN_CN'} =~ /MAIL=(.*)$/;
+ $param->{'user'}{'email'} = lc($1);
+ }
$param->{'auth_method'} = 'smime';
$param->{'ssl_client_s_dn'} = $ENV{'SSL_CLIENT_S_DN'};
$param->{'ssl_client_v_end'} = $ENV{'SSL_CLIENT_V_END'};
diff -ru src/Commands.pm src/Commands.pm
--- src/Commands.pm Thu Apr 19 18:07:29 2001
+++ src/Commands.pm Tue Jun 12 16:20:33 2001
@@ -604,6 +604,8 @@
if ($sign_mod eq 'smime') {
$auth_method='smime';
+ } elsif ($sign_mod eq 'smime_enc') {
+ $auth_method = 'smime_enc';
}elsif ($auth ne '') {
if ($auth eq $list->compute_auth ($sender,'subscribe')) {
$auth_method='md5';
diff -ru src/List.pm src/List.pm
--- src/List.pm Mon Apr 23 16:50:44 2001
+++ src/List.pm Tue Jun 12 17:08:29 2001
@@ -1270,7 +1270,7 @@
print DESC "--$boundary\n" if ($method eq 'md5');
print DESC "Content-Type: message/rfc822\n\n" if ($method eq
'md5');
- my $cryptedmsg = &tools::smime_encrypt($msg,$recipient);
+ my $cryptedmsg = &tools::smime_encrypt($msg,undef,$recipient);
if ($cryptedmsg) {
$cryptedmsg->print(\*DESC);
}else{
@@ -1403,7 +1403,7 @@
## Archives
my $msgtostore = $msg;
if ($encrypt eq 'smime_crypted'){
- $msgtostore = &tools::smime_encrypt($msg,$self->{'name'},'list');
+ $msgtostore =
&tools::smime_encrypt($msg,undef,$self->{'name'},'list');
}
$self->archive_msg($msgtostore);
@@ -1546,7 +1546,12 @@
##Send message for normal reception mode
- my $total = smtp::mailto($msg, $from, $encrypt, $msg_file, @tabrcpt);
+ my $total;
+ if($encrypt eq "smime_crypted") {
+ $total = smtp::mailto($msg, $from, $encrypt, '_ALTERED_', @tabrcpt);
+ } else {
+ $total = smtp::mailto($msg, $from, $encrypt, $msg_file, @tabrcpt);
+ }
##Prepare and send message for notice reception mode
# my $notice_msg = $msg;
@@ -3055,13 +3060,13 @@
my $operation = shift;
my $auth_method = shift;
my $context = shift;
do_log('debug2', 'List::request_action %s,%s',$operation,$auth_method);
$context->{'sender'} ||= 'nobody' ;
$context->{'email'} ||= $context->{'sender'};
$context->{'remote_host'} ||= 'unknown_host' ;
- unless ( $auth_method =~ /^(smtp|md5|pgp|smime)/) {
+ unless ( $auth_method =~ /^(smtp|md5|pgp|smime|smime_enc)/) {
do_log ('info',"fatal error : unknown auth method $auth_method in
List::get_action");
return undef;
}
@@ -3189,7 +3198,7 @@
return undef;
}
- unless ( $auth_method =~ /^(smtp|md5|pgp|smime)/) {
+ unless ( $auth_method =~ /^(smtp|md5|pgp|smime|smime_enc)$/) {
do_log ('info',"fatal error : unknown auth method $auth_method in
List::get_action");
return undef;
}
@@ -3908,7 +3925,7 @@
}
# unless (/^\s*(.*)\s+(md5|pgp|smtp|smime)\s*->\s*(.*)\s*$/i) {
- unless
(/^\s*(.*)\s+(md5|pgp|smtp|smime)((\s*,\s*(md5|pgp|smtp|smime))*)\s*->\s*(.*)\s*$/i)
{
+ unless
(/^\s*(.*)\s+(md5|pgp|smtp|smime|smime_enc)((\s*,\s*(md5|pgp|smtp|smime|smime_enc))*)\s*->\s*(.*)\s*$/i)
{
do_log ('notice', "error rule syntaxe in scenario $function rule
line $. expected : <condition> <auth_mod> -> <action>");
do_log ('debug',"error parsing $rule");
return undef;
@@ -3917,15 +3934,16 @@
$rule->{auth_method}=$2 || 'smtp';
$rule->{action}=$6 ;
push(@scenario,$rule);
-# do_log ('debug2', "load rule 1: $rule->{'condition'}
$rule->{'auth_method'} ->$rule->{'action'}");
+ do_log ('debug2', "load rule 1: $rule->{'condition'}
$rule->{'auth_method'} ->$rule->{'action'}");
my $auth_list = $3 ;
- while ($auth_list =~
/\s*,\s*(md5|pgp|smtp|smime)((\s*,\s*(md5|pgp|smtp|smime))*)\s*/i) {
+ while ($auth_list =~
/^\s*,\s*(md5|pgp|smtp|smime|smime_enc)((\s*,\s*(md5|pgp|smtp|smime|smime_enc))*)\s*$/i)
{
+ do_log ('debug2', "auth_list <$auth_list>");
push(@scenario,{'condition' => $rule->{condition},
'auth_method' => $1,
'action' => $rule->{action}});
$auth_list = $2;
-# do_log ('debug2', "load rule ite: $rule->{'condition'} $1 ->
$rule->{'action'}");
+ do_log ('debug2', "load rule ite: $rule->{'condition'} $1 ->
$rule->{'action'}");
}
}
diff -ru src/smtp.pm src/smtp.pm
--- src/smtp.pm Wed Feb 28 14:49:07 2001
+++ src/smtp.pm Mon Jun 11 18:16:00 2001
@@ -143,7 +143,6 @@
exit 1; ## Should never get there.
}
-
sub sendto {
my($msg_header, $msg_body, $from, $rcpt, $encrypt) = @_;
do_log('debug2', 'smtp::sendto(%s, %s, %s)', $from, $rcpt, $encrypt);
@@ -162,7 +161,9 @@
}
$email = lc ($rcpt->[0]);
}
- $msg = &tools::smime_encrypt ($msg_header, $msg_body, ,$email);
+# do_log('debug2', 'smtp::sendto: msg_header = %s, msg_body = %s, email
= %s', $msg_header, $msg_body, $email);
+ $msg = &tools::smime_encrypt ($msg_header, $msg_body, $email);
+ $msg = $msg->as_string;
}else {
$msg = $msg_header->as_string . "\n" . $msg_body;
}
@@ -198,7 +199,7 @@
sub mailto {
my($msg, $from, $encrypt, $originalfile , @rcpt) = @_;
- do_log('debug2', 'smtp::mailto(from: %s, %s, %d rcpt)', $from, $encrypt,
$#rcpt);
+ do_log('debug2', 'smtp::mailto(from: %s, %s, %d rcpt)', $from, $encrypt,
$#rcpt+1);
my($i, $j, $nrcpt, $size, @sendto);
my $numsmtp = 0;
diff -ru src/sympa.pl src/sympa.pl
--- src/sympa.pl Tue Apr 24 11:16:40 2001
+++ src/sympa.pl Tue Jun 12 15:52:29 2001
@@ -798,7 +798,11 @@
my $action ;
if ($is_signed->{'body'}) {
- $action = &List::get_action ('send',$name,$sender,'smime',$hdr);
+ if($is_crypted eq 'smime_crypted') {
+ $action = &List::get_action
('send',$name,$sender,'smime_enc',$hdr);
+ } else {
+ $action = &List::get_action ('send',$name,$sender,'smime',$hdr);
+ }
}else{
$action = &List::get_action ('send',$name,$sender,'smtp',$hdr);
}
@@ -948,9 +952,12 @@
if ($i =~ /^(quit|end|stop|--)/io) {
last;
}
- &do_log('debug2',"is_signed->body $is_signed->{'body'}");
+ &do_log('debug2',"is_signed->body $is_signed->{'body'},
is_crypted $is_crypted");
- unless ($status = Commands::parse($sender, $i,
$is_signed->{'body'})) {
+ my $sign_mode = (($is_signed->{'body'} eq 'smime' &&
+ $is_crypted eq 'smime_crypted') ?
+ 'smime_enc' : $is_signed->{'body'});
+ unless ($status = Commands::parse($sender, $i, $sign_mode)) {
push @msg::report, sprintf Msg(4, 19, "Command not
understood: ignoring end of message.\n");
last;
}
diff -ru src/tools.pl src/tools.pl
--- src/tools.pl Wed Apr 4 13:18:39 2001
+++ src/tools.pl Mon Jun 11 18:08:08 2001
@@ -370,20 +370,21 @@
return undef ;
}
- unless (open MSG, $file) {
- do_log('err', 'Unable to open file %s: %s', $file, $!);
- return undef;
- }
+# unless (open MSG, $file) {
+# do_log('err', 'Unable to open file %s: %s', $file, $!);
+# return undef;
+# }
- print MSGDUMP <MSG>;
- close MSGDUMP; close MSG;
+# print MSGDUMP <MSG>;
+ $msg->print(\*MSGDUMP);
+ close MSGDUMP; #close MSG;
## second step is the message signer match the sender
## a better analyse should be performed to extract the signer email.
my $signer = `cat $temporary_file | $Conf{'openssl'} x509 -subject
-noout`;
- if ($signer =~ /email=$sender/i) {
+ if ($signer =~ /mail=$sender/i) {
do_log('debug', "S/MIME signed message, signature checked and sender
match signer(%s)",$signer);
## store the signer certificat
unless (-d $Conf{'ssl_cert_dir'}) {
@@ -420,15 +421,26 @@
# input : msg object, return a new message object encrypted
sub smime_encrypt {
- my $msg_header = shift;
+# my $msg_header = shift;
+# my $msg_body = shift;
+ my $msg = shift;
my $msg_body = shift;
my $email = shift ;
my $list = shift ;
my $usercert;
-
+ my $cryptedmsg;
+ my $head;
- &do_log('debug2', 'tools::smime_encrypt message msg from %s for %s
%s',$msg->head->get('from'),$list, $email);
+ if(ref($msg) eq "MIME::Entity") {
+ $head = $msg->head;
+ } elsif(ref($msg) eq "MIME::Head") {
+ $head = $msg;
+ } else {
+ die "tools::smime_encrypt: unknown type for \$msg";
+ }
+
+ &do_log('debug2', 'tools::smime_encrypt message msg from %s for %s
%s',$head->get('from'),$list, $email);
if ($list eq 'list') {
$usercert = "$Conf{'home'}/$email/cert.pem";
}else{
@@ -447,9 +459,11 @@
&do_log('info', 'Can\'t encrypt message for recipient %s',
$email);
}
$msg->print(\*MSGDUMP);
+ if($msg_body) {
+ print MSGDUMP "\n$msg_body";
+ }
close(MSGDUMP);
- my $cryptedmsg;
## Get as MIME object
open (NEWMSG, $temporary_file);
@@ -483,8 +497,9 @@
$predefined_headers->{$header} = 1
if ($cryptedmsg->head->get($header)) ;
}
- foreach my $header ($msg_header->tags) {
- $cryptedmsg->head->add($header,$msg_header->get($header))
+# foreach my $header ($msg_header->tags) {
+ foreach my $header ($head->tags) {
+ $cryptedmsg->head->add($header,$head->get($header))
unless $predefined_headers->{$header} ;
}
@@ -493,7 +508,8 @@
return undef;
}
- return $cryptedmsg->head->as_string . "\n" . $encrypted_body;
+# return $cryptedmsg->head->as_string . "\n" . $encrypted_body;
+ return $cryptedmsg;
}
# input : msg object for a list, return a new message object decrypted
@@ -530,6 +546,7 @@
# if password is define in sympa.conf pass the password to OpenSSL
using
$pass_option = "-passin file:$Conf{'tmpdir'}/pass.$$";
}
+ &do_log('debug2', "$Conf{'openssl'} smime -decrypt -in $temporary_file
-recip $certfile -inkey $keyfile $pass_option 2>&1 |");
open (NEWMSG, "$Conf{'openssl'} smime -decrypt -in $temporary_file
-recip $certfile -inkey $keyfile $pass_option 2>&1 |");
if ($Conf{'key_passwd'} ne '') {
unless (&POSIX::mkfifo("$Conf{'tmpdir'}/pass.$$",0600)) {
Christian Mock address@concealed
XSoft GmbH http://www.xsoft.at/
Modecenterstr. 14, 1030 Vienna, Austria Mobil: +43 (664) 4051628
Tel: +43 (1) 7963636-27 Fax: +43 (1) 7963636-18
Attachment:
pgpc1AHnT7_Fp.pgp
Description: PGP signature
-
patches for S/MIME,
Christian Mock, 06/22/2001
- Re: [sympa-dev] patches for S/MIME, Aumont, 06/25/2001
- Re: [sympa-dev] patches for S/MIME, Olivier Salaun, 06/29/2001
Archive powered by MHonArc 2.6.19+.