File Coverage

blib/lib/Crypt/Solitaire.pm
Criterion Covered Total %
statement 37 53 69.8
branch 11 16 68.7
condition n/a
subroutine 5 8 62.5
pod 1 6 16.6
total 54 83 65.0


line stmt bran cond sub pod time code
1             #------------------------------------------------------------------------------#
2             # Crypt::Solitaire
3             #
4             # Solitaire cryptosystem, as used in Neal Stephenson's novel _Cryptonomicon_
5             # Designed by Bruce Schneier (President, Counterpane Systems)
6             # Original Perl Code by Ian Goldberg , 19980817
7             # Minor changes and module-ification by Kurt Kincaid
8             #
9             # Last Modified: 28-Nov-2001 04:20:10 PM
10             # Copyright(c) 2001, Kurt Kincaid. All Rights Reserved.
11             #
12             # This is free software and may be modified and/or redistributed under the
13             # same terms as perl itself.
14             #------------------------------------------------------------------------------#
15              
16             package Crypt::Solitaire;
17 1     1   616 use strict;
  1         3  
  1         180  
18 1     1   5 use vars qw($VERSION @ISA @EXPORT @EXPORT_OK $multFactor $k $D $c $v $Deck $text $passphrase $mode $class );
  1         2  
  1         2338  
19              
20             require Exporter;
21              
22             @ISA = qw(Exporter AutoLoader);
23             @EXPORT_OK = qw(Pontifex);
24              
25             $VERSION = "2.0";
26              
27             sub new {
28 0     0 0 0 ( $class, $passphrase ) = @_;
29 0         0 $passphrase =~ y/a-z/A-Z/;
30 0         0 $passphrase =~ s/[A-Z]/$k=ord($&)-64,&e/eg;
  0         0  
31 0         0 my $self = bless {}, $class;
32 0         0 return $self;
33             }
34              
35             sub encrypt {
36 0     0 0 0 my $self = shift;
37 0         0 ( $text, $passphrase ) = @_;
38 0         0 return Pontifex( $text, $passphrase, "e" );
39             }
40              
41             sub decrypt {
42 0     0 0 0 my $self = shift;
43 0         0 ( $text, $passphrase ) = @_;
44 0         0 return Pontifex( $text, $passphrase, "d" );
45             }
46              
47             sub Pontifex {
48 2 50   2 1 41 if ( ref $_[ 0 ] ) {
49 0         0 my $self = shift;
50             }
51 2         8 ( $text, $passphrase, $mode ) = @_;
52 2 100       12 if ( $mode =~ /^e/i ) {
    50          
53 1         4 $multFactor = 1;
54             } elsif ( $mode =~ /^d/i ) {
55 1         2 $multFactor = -1;
56             } else {
57 0         0 return undef;
58             }
59              
60 2         11 $Deck = pack( 'C*', 33 .. 86 );
61              
62 2         4 $k = 0;
63              
64 2         7 $text =~ y/a-z/A-Z/;
65 2         5 $text =~ y/A-Z//dc;
66 2 100       7 if ( $multFactor == 1 ) {
67 1         11 $text .= "X" while length( $text ) % 5;
68             }
69 2         7 $text =~ s/./chr((ord($&)-13+$multFactor*&e)%26+65)/eg;
  50         99  
70              
71 2 100       8 if ( $multFactor == -1 ) {
72 1         9 $text =~ s/X*$//;
73             }
74 2         18 $text =~ s/.{5}/$& /g;
75 2         6 return $text;
76             }
77              
78             sub v {
79 150     150 0 202 $v = ord( substr( $D, $_[ 0 ] ) ) - 32;
80 150 50       293 $v > 53 ? 53 : $v;
81             }
82              
83             sub e {
84 50     50 0 52 $D =~ s/(.*)U$/U$1/;
85 50         50 $D =~ s/U(.)/$1U/;
86              
87 50         45 $D =~ s/(.*)V$/V$1/;
88 50         46 $D =~ s/V(.)/$1V/;
89 50         46 $D =~ s/(.*)V$/V$1/;
90 50         46 $D =~ s/V(.)/$1V/;
91              
92 50         43 $D =~ s/(.*)([UV].*[UV])(.*)/$3$2$1/;
93              
94 50         72 $c = &v( 53 );
95 50         134 $D =~ s/(.{$c})(.*)(.)/$2$1$3/;
96              
97 50 50       133 if ( $k ) {
98 0         0 $D =~ s/(.{$k})(.*)(.)/$2$1$3/;
99 0         0 return;
100             }
101              
102 50         81 $c = &v( &v( 0 ) );
103              
104 50 50       200 $c > 52 ? &e : $c;
105             }
106              
107             1;
108             __END__