Authen-SASL

 view release on metacpan or  search on metacpan

lib/Authen/SASL/Perl/DIGEST_MD5.pm  view on Meta::CPAN

use vars qw(@ISA $CNONCE $NONCE);
use Crypt::URandom qw(urandom);
use Digest::MD5 qw(md5_hex md5);
use Digest::HMAC_MD5 qw(hmac_md5);

warnings::warnif(
    'deprecated',
    'The DIGEST-MD5 SASL mechanism is deprecated by RFC6331 and should no longer be used'
    );

# TODO: complete qop support in server, should be configurable

@ISA = qw(Authen::SASL::Perl);

my %secflags = (
  noplaintext => 1,
  noanonymous => 1,
);

# some have to be quoted - some don't - sigh!
my (%cqdval, %sqdval);
@cqdval{qw(
  username authzid realm nonce cnonce digest-uri
)} = ();

## ...and server behaves different than client - double sigh!
@sqdval{keys %cqdval, qw(qop cipher)} = ();
#  username authzid realm nonce cnonce digest-uri qop cipher
#)} = ();

my %multi;
@{$multi{server}}{qw(realm auth-param)} = ();
@{$multi{client}}{qw()} = ();

my @server_required = qw(algorithm nonce);
my @client_required = qw(username nonce cnonce nc qop response);

# available ciphers
my @ourciphers = (
  {
    name  => 'rc4',
    ssf   => 128,
    bs    => 1,
    ks    => 16,
    pkg   => 'Crypt::RC4',
    key   => sub { $_[0] },
    iv    => sub {},
    fixup => sub {
      # retrofit the Crypt::RC4 module with standard subs
      *Crypt::RC4::encrypt   = *Crypt::RC4::decrypt =
        sub { goto &Crypt::RC4::RC4; };
      *Crypt::RC4::keysize   =  sub {128};
      *Crypt::RC4::blocksize =  sub {1};
    }
  },
  {
    name  => '3des',
    ssf   => 112,
    bs    => 8,
    ks    => 16,
    pkg   => 'Crypt::DES3',
    key   => sub {
      pack('B8' x 16,
        map { $_ . '0' }
        map { unpack('a7' x 16, $_); }
        unpack('B*', substr($_[0], 0, 14)) );
    },
    iv => sub { substr($_[0], -8, 8) },
  },
  {
    name  => 'des',
    ssf   => 56,
    bs    => 8,
    ks    => 16,
    pkg   => 'Crypt::DES',
    key   => sub {
      pack('B8' x 8,
        map { $_ . '0' }
        map { unpack('a7' x 8, $_); }
        unpack('B*',substr($_[0], 0, 7)) );
    },
    iv => sub { substr($_[0], -8, 8) },
  },
  {
    name  => 'rc4-56',
    ssf   => 56,
    bs    => 1,
    ks    => 7,
    pkg   => 'Crypt::RC4',
    key   => sub { $_[0] },
    iv    => sub {},
    fixup => sub {
      *Crypt::RC4::encrypt   = *Crypt::RC4::decrypt =
        sub { goto &Crypt::RC4::RC4; };
      *Crypt::RC4::keysize   =  sub {56};
      *Crypt::RC4::blocksize =  sub {1};
    }
  },
  {
    name  => 'rc4-40',
    ssf   => 40,
    bs    => 1,
    ks    => 5,
    pkg   => 'Crypt::RC4',
    key   => sub { $_[0] },
    iv    => sub {},
    fixup => sub {
      *Crypt::RC4::encrypt   = *Crypt::RC4::decrypt =
        sub { goto &Crypt::RC4::RC4; };
      *Crypt::RC4::keysize   =  sub {40};
      *Crypt::RC4::blocksize =  sub {1};
    }
  },
);

## The system we are on, might not be able to crypt the stream
our $NO_CRYPT_AVAILABLE = 1;
for (@ourciphers) {
    eval "require $_->{pkg}";
    unless ($@) {
        $NO_CRYPT_AVAILABLE = 0;
        last;
    }
}

sub _order { 3 }
sub _secflags {
  shift;
  scalar grep { $secflags{$_} } @_;
}

sub mechanism { 'DIGEST-MD5' }

sub _init {
  my ($pkg, $self) = @_;



( run in 0.719 second using v1.01-cache-2.11-cpan-0d23b851a93 )