SPF: use $conn->relay_client instead of duplicated

is_in_relayclients method. Expects relay plugin to have set relay_client, a reasonable assumption.
This commit is contained in:
Matt Simerson 2012-11-14 23:21:20 -05:00
parent eb154f2069
commit 78cab52582
4 changed files with 27 additions and 47 deletions

View File

@ -1,12 +1,14 @@
# used by plugins/relay
# Format is IP, or IP part with trailing dot
# IPv4 format is IP, or IP part with trailing dot
# e.g. "127.0.0.1", or "192.168."
127.0.0.1
# leading/trailing whitespace is ignored
192.0.
#
# IPv6 formats ends in a nibble (not a netmask, prefixlen, or colon)
# RFC 3849 example
2001:DB8
# IPv6 formats can be compressed or expanded, may include a prefixlen,
# and can end on any nibble boundary. Nibble boundaries must be expressed
# in expanded format. (RFC 3849 example)
2001:0DB8
2001:DB8::1
2001:DB8::1/32
2001:0DB8:0000:0000:0000:0000:0000:0001

View File

@ -37,12 +37,12 @@ Each line in I<relayclients> is one of:
- partial IP address terminated by a dot or colon for matching whole networks
192.168.42.
fdda:b13d:e431:ae06:
2001:db8:e431:ae06:
...
- a network/mask, aka a CIDR block
10.1.0.0/24
fdda:b13d:e431:ae06::/64
2001:db8:e431:ae06::/64
...
=head2 morerelayclients
@ -175,15 +175,20 @@ sub is_octet_match {
my $self = shift;
my $ip = $self->qp->connection->remote_ip;
$ip =~ s/::/:/;
if ( $ip eq ':1' ) {
if ( $ip eq '::1' ) {
$self->log(LOGINFO, "pass, octet matched localhost ($ip)");
return 1;
};
my $more_relay_clients = $self->qp->config('morerelayclients', 'map');
my $ipv6 = $ip =~ /:/ ? 1 : 0;
if ( $ipv6 && $ip =~ /::/ ) { # IPv6 compressed notation
$ip = Net::IP::ip_expand_address($ip,6);
};
while ($ip) {
if ( exists $self->{_octets}{$ip} ) {
$self->log(LOGINFO, "pass, octet match in relayclients ($ip)");
@ -194,7 +199,15 @@ sub is_octet_match {
$self->log(LOGINFO, "pass, octet match in morerelayclients ($ip)");
return 1;
};
$ip =~ s/(\d|\w)+(:|\.)?$// or last; # strip off another 8 bits
# added IPv6 support (Michael Holzt - 2012-11-14)
if ( $ipv6 ) {
$ip =~ s/[0-9a-f]:?$//; # strip off another nibble
chop $ip if ':' eq substr($ip, -1, 1);
}
else {
$ip =~ s/\d+\.?$// or last; # strip off another 8 bits
}
}
$self->log(LOGDEBUG, "no octet match" );

View File

@ -59,8 +59,6 @@ use warnings;
#use Mail::SPF 2.000; # eval'ed in ->register
use Qpsmtpd::Constants;
use Net::IP;
sub register {
my ($self, $qp, %args) = @_;
eval 'use Mail::SPF';
@ -92,8 +90,8 @@ sub mail_handler {
return (DECLINED, "SPF - null sender");
};
if ( $self->is_in_relayclients() ) {
$self->log( LOGINFO, "skip, in relayclients" );
if ( $self->qp->connection->relay_client ) {
$self->log( LOGINFO, "skip, relay_client" );
return (DECLINED, "SPF - relaying permitted");
};
@ -231,39 +229,6 @@ sub data_post_handler {
return DECLINED;
}
sub is_in_relayclients {
my $self = shift;
my $client_ip = $self->qp->connection->remote_ip;
my @relay_clients = $self->qp->config('relayclients');
my $more_relay_clients = $self->qp->config('morerelayclients', 'map');
my %relay_clients = map { $_ => 1 } @relay_clients;
my $ipv6 = $client_ip =~ /:/ ? 1 : 0;
if ( $ipv6 && $client_ip =~ /::/ ) { # IPv6 compressed notation
$client_ip = Net::IP::ip_expand_address($client_ip,6);
};
while ($client_ip) {
if ( exists $relay_clients{$client_ip} ||
exists $more_relay_clients->{$client_ip} ) {
$self->log( LOGDEBUG, "skip, IP in relayclients" );
return 1;
};
# added IPv6 support (Michael Holzt - 2012-11-14)
if ( $ipv6 ) {
$client_ip =~ s/[0-9a-f]:*$//; # strip off another nibble
chop $client_ip if ':' eq substr($client_ip, -1, 1);
}
else {
$client_ip =~ s/\d+\.?$// or last; # strip off another 8 bits
}
}
return;
};
sub is_special_recipient {
my ($self, $rcpt) = @_;

View File

@ -26,7 +26,7 @@ is($smtpd->config('me'), 'some.host.example.org', 'config("me")');
# line with both)
my $relayclients = join ",", sort $smtpd->config('relayclients');
is($relayclients,
'127.0.0.1,192.0.,2001:0DB8:0000:0000:0000:0000:0000:0001,2001:DB8,2001:DB8::1',
'127.0.0.1,192.0.,2001:0DB8:0000:0000:0000:0000:0000:0001,2001:DB8::1/32,2001:DB8,2001:DB8::1',
'config("relayclients") are trimmed');
foreach my $f ( @mes ) {