Anonymous Monk has asked for the wisdom of the Perl Monks concerning the following question:

Sometime ago it occured to me that the CoreModule Digest::SHA could be used to en/decrypt data. So I wrote this Module (pc from perlcrypt):
package pc; use strict; use Digest::SHA qw(hmac_sha256 sha1 sha224 sha384); use Exporter "import"; use vars '@EXPORT_OK'; use bytes; sub step { my $i=shift; $_[$i->[0]]^= hmac_sha256(substr("op",abs($i->[0]),1) ,$i->[-1] ,$_[$i->[0]-$i->[1]].$_[$i->[0]+$i->[1]]); $i->[0]+=1; return ($i,$_[1],$_[-1],$_[0]) } sub block{ my ($key,$d,$s)=@_; return shift if @_==1; $key=[-1,1+-2*$d,$key]if!ref$key; my @r=reverse step step step $key,substr($s,0,32),substr($s,32,32),su +bstr($s,64,32); pop @r; return join"",@r } sub hash{ my $b=shift; return scalar reverse sha224($b).sha384($b).sha1($b) } sub test{my($k,$d)=@_; return $d eq round $k,1,round $k,0,$d } sub size(){96} sub encrypt{my($k,$d)=@_; return 1 if!@_; return([-1,-1,@_],1)if@_==1; my$o=(length$d)%size; my$b=hash $d; my$iv=$b; $b.=$d; my$r=$iv; my$x; for($x=size;$x+$o<length$b;$x+=size){ $iv=block$iv.$k,1,substr$b,$x,size; $r.=$iv } $r.=substr$d,$x- size,$o; $b=substr$r,$o; my$h=block$k.$b,1,hash$b; my$e=substr$r,0,$o; $e^=substr$h,0,$o; $iv=block$e.$k,1,hash$k.$e; for($x=$o;$x<length$r;$x+=size){ my$c=$iv.$k; $iv=substr$r,$x,size; $e.=block$c,0,$iv } return$e } sub decrypt{my($k,$e)=@_; return 0 if!@_; return([-1,1,@_],0)if@_==1; return undef if size>length$e; my$o=(length$e)%size; my$x=substr$e,0,$o; my$r=""; my$iv=block$x.$k,1,hash$k.$x; for($x=$o;$x<length$e;$x+=size){ $iv=block$iv.$k,1,substr$e,$x,size; $r.=$iv } my$h=block$k.$r,1,hash$r; my$b=substr$e,0,$o; $b^=substr$h,0,$o; my$d=""; $b.=$r; $e=$iv=substr$b,0,size; for($x=size;$x+$o<length$b;$x+=size){ my$c=$iv.$k; $iv=substr$b,$x,size; $d.=block$c,0,$iv } $d.=substr$b,-$o,$o; return undef if $e ne hash $d; return $d; } @EXPORT_OK=qw(encrypt decrypt block size hash);

It is made to be used conveniently. E.g. $enc= block encrypt($key),$data or $data= block($key,decrypt,$enc) for blockwise encryption (length is guaranteed to be the same) or simply  $enc=encrypt $key,$data for general strings (the length changes in the encryption process).

Now my Question: How can I make this module compatible to the more standard modules? The crypto should be compatible between equivalent uses "the standard way" and "the convenient way". Another question: encrypt and decrypt are very similar. Can I "compress" them into one function to make the module shorter?

Replies are listed 'Best First'.
Re: Convenient Crypto
by ikegami (Patriarch) on Feb 04, 2011 at 07:06 UTC

    Sometime ago it occured to me that the CoreModule Digest::SHA could be used to en/decrypt data.

    What? No. And don't invent your own encryption.

    It takes two lines of code to encrypt and decrypt properly.

    use Crypt::CBC qw( ); my $cipher = Crypt::CBC->new( -cipher => 'Blowfish', -key => 'my secret key', ); my $ciphertext = $cipher->encrypt("This data is hush hush"); my $plaintext = $cipher->decrypt($ciphertext);

    Crypt::CBC

      Isn't in core dist.
        Neither is the module that was posted. What's your point?
Re: Convenient Crypto
by dave_the_m (Monsignor) on Feb 03, 2011 at 23:13 UTC
    CanIAssumeThatYourCodeIsMoreSecureAndFasterBecauseYouHave EliminatedMostSuperfluousWhiteSpace?

    Dave.

Re: Convenient Crypto
by Anonymous Monk on Feb 04, 2011 at 06:29 UTC
    I don't know which is more frightening, your code or that you think you've done something wonderful.

    Your code is unreadable and you provide no documentation for how you intend others to use it.

    How is it that you can undo a one-way digest?

    What is round? You don't define it and it's not obvious that you imported it (or from where you imported). Goes back to lack of documentation.

    Why should you not be nominated for Schneier's DogHouse this month?

      round is now known as block. test was for - surprise - for testing.