Assimilate CGI 3.03
[p5sagit/p5-mst-13.2.git] / lib / Digest.pm
index 9727a1c..9353db1 100644 (file)
@@ -3,10 +3,13 @@ package Digest;
 use strict;
 use vars qw($VERSION %MMAP $AUTOLOAD);
 
-$VERSION = "1.00";
+$VERSION = "1.05";
 
 %MMAP = (
-  "SHA-1"      => "Digest::SHA1",
+  "SHA-1"      => ["Digest::SHA1", ["Digest::SHA", 1], ["Digest::SHA2", 1]],
+  "SHA-256"    => [["Digest::SHA", 256], ["Digest::SHA2", 256]],
+  "SHA-384"    => [["Digest::SHA", 384], ["Digest::SHA2", 384]],
+  "SHA-512"    => [["Digest::SHA", 512], ["Digest::SHA2", 512]],
   "HMAC-MD5"   => "Digest::HMAC_MD5",
   "HMAC-SHA-1" => "Digest::HMAC_SHA1",
 );
@@ -15,13 +18,27 @@ sub new
 {
     shift;  # class ignored
     my $algorithm = shift;
-    my $class = $MMAP{$algorithm} || "Digest::$algorithm";
-    no strict 'refs';
-    unless (exists ${"$class\::"}{"VERSION"}) {
-       eval "require $class";
-       die $@ if $@;
+    my $impl = $MMAP{$algorithm} || do {
+       $algorithm =~ s/\W+//;
+       "Digest::$algorithm";
+    };
+    $impl = [$impl] unless ref($impl);
+    my $err;
+    for  (@$impl) {
+       my $class = $_;
+       my @args;
+       ($class, @args) = @$class if ref($class);
+       no strict 'refs';
+       unless (exists ${"$class\::"}{"VERSION"}) {
+           eval "require $class";
+           if ($@) {
+               $err ||= $@;
+               next;
+           }
+       }
+       return $class->new(@args, @_);
     }
-    $class->new(@_);
+    die $err;
 }
 
 sub AUTOLOAD
@@ -37,15 +54,15 @@ __END__
 
 =head1 NAME
 
-Digest:: - Modules that calculate message digests
+Digest - Modules that calculate message digests
 
 =head1 SYNOPSIS
 
-  $md2 = Digest->MD2;
-  $md5 = Digest->MD5;
-
-  $sha1 = Digest->SHA1;
+  $md5  = Digest->new("MD5");
   $sha1 = Digest->new("SHA-1");
+  $sha256 = Digest->new("SHA-256");
+  $sha384 = Digest->new("SHA-384");
+  $sha512 = Digest->new("SHA-512");
 
   $hmac = Digest->HMAC_MD5($key);
 
@@ -55,7 +72,7 @@ The C<Digest::> modules calculate digests, also called "fingerprints"
 or "hashes", of some data, called a message.  The digest is (usually)
 some small/fixed size string.  The actual size of the digest depend of
 the algorithm used.  The message is simply a sequence of arbitrary
-bytes.
+bytes or bits.
 
 An important property of the digest algorithms is that the digest is
 I<likely> to change if the message change in some way.  Another
@@ -80,7 +97,7 @@ or embedding in places that can't handle arbitrary data.
 
 =item I<hex>
 
-A twice as long string of (lowercase) hexadecimal digits.
+A twice as long string of lowercase hexadecimal digits.
 
 =item I<base64>
 
@@ -129,21 +146,52 @@ reset the state the object to the state of a newly created object.  No
 new object is created in this case, and the return value is the
 reference to the object (i.e. $ctx).
 
+=item $other_ctx = $ctx->clone
+
+The clone method creates a copy of the digest state object and returns
+a reference to the copy.
+
 =item $ctx->reset
 
 This is just an alias for $ctx->new.
 
-=item $ctx->add($data,...)
+=item $ctx->add( $data, ... )
 
 The $data provided as argument are appended to the message we
 calculate the digest for.  The return value is the $ctx object itself.
 
-=item $ctx->addfile($io_handle)
+=item $ctx->addfile( $io_handle )
 
 The $io_handle is read until EOF and the content is appended to the
 message we calculate the digest for.  The return value is the $ctx
 object itself.
 
+=item $ctx->add_bits( $data, $nbits )
+
+=item $ctx->add_bits( $bitstring )
+
+The bits provided are appended to the message we calculate the digest
+for.  The return value is the $ctx object itself.
+
+The two argument form of add_bits() will add the first $nbits bits
+from data.  For the last potentially partial byte only the high order
+C<< $nbits % 8 >> bits are used.  If $nbits is greater than C<<
+length($data) * 8 >>, then this method would do the same as C<<
+$ctx->add($data) >>, i.e. $nbits is silently ignored.
+
+The one argument form of add_bits() takes a $bitstring of "1" and "0"
+chars as argument.  It's a shorthand for C<< $ctx->add_bits(pack("B*",
+$bitstring), length($bitstring)) >>.
+
+This example shows two calls that should have the same effect:
+
+   $ctx->add_bits("111100001010");
+   $ctx->add_bits("\xF0\xA0", 12);
+
+Most digest algorithms are byte based.  For those it is not possible
+to add bits that are not a multiple of 8, and the add_bits() method
+will croak if you try.
+
 =item $ctx->digest
 
 Return the binary digest for the message.
@@ -151,7 +199,8 @@ Return the binary digest for the message.
 Note that the C<digest> operation is effectively a destructive,
 read-once operation. Once it has been performed, the $ctx object is
 automatically C<reset> and can be used to calculate another digest
-value.
+value.  Call $ctx->clone->digest if you want to calculate the digest
+without reseting the digest state.
 
 =item $ctx->hexdigest
 
@@ -164,9 +213,41 @@ string.
 
 =back
 
+=head1 Digest speed
+
+This table should give some indication on the relative speed of
+different algorithms.  It is sorted by throughput based on a benchmark
+done with of some implementations of this API:
+
+ Algorithm     Size    Implementation                  MB/s
+
+ MD4           128     Digest::MD4 v1.1                24.9
+ MD5           128     Digest::MD5 v2.30               18.7
+ Haval-256     256     Digest::Haval256 v1.0.4         17.0
+ SHA-1         160     Digest::SHA1 v2.06              15.3
+ SHA-1         160     Digest::SHA v4.0.0              10.1
+ SHA-256       256     Digest::SHA2 v1.0.0              7.6
+ SHA-256       256     Digest::SHA v4.0.0               6.5
+ SHA-384       384     Digest::SHA2 v1.0.0              2.7
+ SHA-384       384     Digest::SHA v4.0.0               2.7
+ SHA-512       512     Digest::SHA2 v1.0.0              2.7
+ SHA-512       512     Digest::SHA v4.0.0               2.7
+ Whirlpool     512     Digest::Whirlpool v1.0.2         1.4
+ MD2           128     Digest::MD2 v2.03                1.1
+
+ Adler-32       32     Digest::Adler32 v0.03            0.2
+ MD5           128     Digest::Perl::MD5 v1.5           0.1
+
+These numbers was achieved Nov 2003 with ActivePerl-5.8.1 running
+under Linux on a P-II 350 MHz CPU.  The last 2 entries differ by being
+pure perl implementations of the algorithms, which explains why they
+are so slow.
+
 =head1 SEE ALSO
 
-L<Digest::MD5>, L<Digest::SHA1>, L<Digest::HMAC>, L<Digest::MD2>
+L<Digest::Adler32>, L<Digest::Haval256>, L<Digest::HMAC>, L<Digest::MD2>, L<Digest::MD4>, L<Digest::MD5>, L<Digest::SHA>, L<Digest::SHA1>, L<Digest::SHA2>, L<Digest::Whirlpool>
+
+New digest implementations should consider subclassing from L<Digest::base>.
 
 L<MIME::Base64>
 
@@ -177,4 +258,10 @@ Gisle Aas <gisle@aas.no>
 The C<Digest::> interface is based on the interface originally
 developed by Neil Winton for his C<MD5> module.
 
+This library is free software; you can redistribute it and/or
+modify it under the same terms as Perl itself.
+
+    Copyright 1998-2001,2003 Gisle Aas.
+    Copyright 1995-1996 Neil Winton.
+
 =cut