Alt-Crypt-RSA-BigInt

 view release on metacpan or  search on metacpan

lib/Crypt/RSA.pm  view on Meta::CPAN


    return $cyphertext;

}


sub decrypt { 

    my ($self , %params) = @_;
    my $cyphertext       = $params{Cyphertext} || $params{Ciphertext};
    my $key              = $params{Key}; 

    return $self->error ($key->errstr, \%params, $key) unless $key->check();

    if ($params{Armour} || $params{Armor}) { 
        my $decoded = $self->{pp}->unarmour ($cyphertext) ||
            return $self->error ($self->{pp}->errstr());
        $cyphertext = $$decoded{Content}{Cyphertext}
    }

    my $plaintext;
    my $blocksize = blocksize ( $$self{es}->decryptblock (Key => $key),
                                length($cyphertext)
                              );

    return $self->error("Message too long.") if $blocksize <= 0;

    my @segments = steak ($cyphertext, $blocksize);
    for (@segments) {
        $plaintext .= $self->{es}->decrypt (Cyphertext=> $_, Key => $key)
            || return $self->error ($self->{es}->errstr, \$key, \%params);
    }

    return $plaintext;

}


sub sign { 

    my ($self, %params) = @_;
    my $signature = $self->{ss}->sign (%params) 
                 || return $self->error ($self->{ss}->errstr,
                        $params{Key}, \%params);

    if ($params{Armour} || $params{Armor}) { 
        $signature      = $self->{pp}->armour ( 
               Object   => "RSA SIGNATURE", 
               Headers  => {  
                    Scheme  => $$self{SS}{Module} || ${$KNOWNMAP{$$self{SS}{Name}}}{Module},
                    Version => $self->{ss}->version() }, 
               Content  => { Signature => $signature },
        );
    }

    return $signature;

} 


sub verify { 

    my ($self, %params) = @_;

    if ($params{Armour} || $params{Armor}) { 
        my $decoded  = $self->{pp}->unarmour ($params{Signature}) ||
            return $self->error ($self->{pp}->errstr());
        $params{Signature} = $$decoded{Content}{Signature}
    }

    my $verify = $self->{ss}->verify (%params) || 
        return $self->error ($self->{ss}->errstr, $params{Key}, \%params);

    return $verify;

}


sub blocksize { 

    my ($blocksize, $ptsize) = @_;
    return $ptsize if $blocksize == -1;
    return 0 if $blocksize < 1;
    return $blocksize;
        
}

1; 

=pod

=encoding utf8

=head1 NAME

Crypt::RSA - RSA public-key cryptosystem.

=head1 SYNOPSIS

    my $rsa = new Crypt::RSA; 

    my ($public, $private) = 
        $rsa->keygen ( 
            Identity  => 'Lord Macbeth <macbeth@glamis.com>',
            Size      => 1024,  
            Password  => 'A day so foul & fair', 
            Verbosity => 1,
        ) or die $rsa->errstr();


    my $cyphertext = 
        $rsa->encrypt ( 
            Message    => $message,
            Key        => $public,
            Armour     => 1,
        ) || die $rsa->errstr();


    my $plaintext = 
        $rsa->decrypt ( 
            Cyphertext => $cyphertext, 
            Key        => $private,
            Armour     => 1,
        ) || die $rsa->errstr();


    my $signature = 
        $rsa->sign ( 
            Message    => $message, 
            Key        => $private
        ) || die $rsa->errstr();


    my $verify = 
        $rsa->verify (
            Message    => $message, 
            Signature  => $signature, 
            Key        => $public
        ) || die $rsa->errstr();

=head1 NOTE

This manual assumes familiarity with public-key cryptography and the RSA
algorithm. If you don't know what these are or how they work, please refer
to the sci.crypt FAQ[15]. A formal treatment of RSA can be found in [1].

=head1 DESCRIPTION

Crypt::RSA is a pure-perl, cleanroom implementation of the RSA public-key
cryptosystem.

Crypt::RSA provides arbitrary size key-pair generation, plaintext-aware
encryption (OAEP) and digital signatures with appendix (PSS). For
compatibility with SSLv3, RSAREF2, PGP and other applications that follow
the PKCS #1 v1.5 standard, it also provides PKCS #1 v1.5 encryption and
signatures.

Crypt::RSA is structured as bundle of modules that encapsulate different
parts of the RSA cryptosystem. The RSA algorithm is implemented in
Crypt::RSA::Primitives(3). Encryption schemes, located under
Crypt::RSA::ES, and signature schemes, located under Crypt::RSA::SS, use
the RSA algorithm to build encryption/signature schemes that employ secure
padding. (See the note on Security of Padding Schemes.)

The key generation engine and other functions that work on both components
of the key-pair are encapsulated in Crypt::RSA::Key(3).
Crypt::RSA::Key::Public(3) & Crypt::RSA::Key::Private(3) provide
mechanisms for storage & retrieval of keys from disk, decoding & encoding
of keys in certain formats, and secure representation of keys in memory.
Finally, the Crypt::RSA module provides a convenient, DWIM wrapper around
the rest of the modules in the bundle.

=head1 SECURITY OF PADDING SCHEMES

It has been conclusively shown that textbook RSA is insecure[3,7]. Secure
RSA requires that plaintext is padded in a specific manner before
encryption and signing. There are four main standards for padding: PKCS
#1 v1.5 encryption & signatures, and OAEP encryption & PSS signatures.
Crypt::RSA implements these as four modules that 
provide overloaded encrypt(), decrypt(), sign() and verify() methods that
add padding functionality to the basic RSA operations.

Crypt::RSA::ES::PKCS1v15(3) implements PKCS #1 v1.5 encryption,
Crypt::RSA::SS::PKCS1v15(3) implements PKCS #1 v1.5 signatures,
Crypt::RSA::ES::OAEP(3) implements Optimal Asymmetric Encryption and
Crypt::RSA::SS::PSS(3) Probabilistic Signatures.

PKCS #1 v1.5 schemes are older and hence more widely deployed, but PKCS #1
v1.5 encryption has certain flaws that make it vulnerable to
chosen-cyphertext attacks[9]. Even though Crypt::RSA works around these
vulnerabilities, it is recommended that new applications use OAEP and PSS,
both of which are provably secure[13]. In any event,
Crypt::RSA::Primitives (without padding) should never be used directly.

That said, there exists a scheme called Simple RSA[16] that provides
security without padding. However, Crypt::RSA doesn't implement this
scheme yet.

=head1 METHODS

=over 4

=item B<new()>

The constructor. When no arguments are provided, new() returns an object
loaded with default values. This object can be customized by specifying
encryption & signature schemes, key formats and post processors. For
details see the section on B<Customizing the Crypt::RSA
object> later in this manpage.

=item B<keygen()>

keygen() generates and returns an RSA key-pair of specified bitsize.
keygen() is a synonym for Crypt::RSA::Key::generate(). Parameters and
return values are described in the Crypt::RSA::Key(3) manpage.

=item B<encrypt()>

encrypt() performs RSA encryption on a string of arbitrary length with a
public key using the encryption scheme bound to the object. The default
scheme is OAEP. encrypt() returns cyphertext (a string) on success and
undef on failure. It takes a hash as argument with following keys:

=over 4

=item B<Message>

An arbitrary length string to be encrypted.

=item B<Key>

Public key of the recipient, a Crypt::RSA::Key::Public(3) or
compatible object.

=item B<Armour>

A boolean parameter that forces cyphertext through a post processor after
encryption. The default post processor is Convert::ASCII::Armour(3) that
encodes binary octets in 6-bit clean ASCII messages. The cyphertext is
returned as-is, when the Armour key is not present.

=back

=item B<decrypt()>

decrypt() performs RSA decryption with a private key using the encryption
scheme bound to the object. The default scheme is OAEP. decrypt() returns
plaintext on success and undef on failure. It takes a hash as argument
with following keys:

=over 4

=item B<Cyphertext>

Cyphertext of arbitrary length. 

=item B<Key>

Private key, a Crypt::RSA::Key::Private(3) or compatible object.

=item B<Armour> 

Boolean parameter that specifies whether the Cyphertext is encoded with a
post processor.

=back

=item B<sign()>

sign() creates an RSA signature on a string with a private key using the
signature scheme bound to the object. The default scheme is
PSS. sign() returns a signature on success and undef on failure. It takes
a hash as argument with following keys:

=over 4

=item B<Message>

A string of arbitrary length to be signed.

=item B<Key>

Private key of the sender, a Crypt::RSA::Key::Private(3) or
compatible object.

=item B<Armour>

A boolean parameter that forces the computed signature to be post
processed.

=back

=item B<verify()>

verify() verifies an RSA signature with a public key using the signature
scheme bound to the object. The default scheme is PSS. verify() returns a
true value on success and undef on failure. It takes a hash as argument
with following keys:

=over 4 

=item B<Message>

A signed message, a string of arbitrary length. 

=item B<Key>

Public key of the signer, a Crypt::RSA::Key::Public(3) or
compatible object.

=item B<Sign> 

A signature computed with sign().

=item B<Armour>

Boolean parameter that specifies whether the Signature has been 
post processed.

=back

=back

=head1 MODULES

Apart from Crypt::RSA, the following modules are intended for application
developer and end-user consumption:

=over 4

=item B<Crypt::RSA::Key>

RSA key pair generator.

=item B<Crypt::RSA::Key::Public>

RSA Public Key Management.

=item B<Crypt::RSA::Key::Private>

RSA Private Key Management.

=item B<Crypt::RSA::ES::OAEP>

Plaintext-aware encryption with RSA.

=item B<Crypt::RSA::SS::PSS>

Probabilistic Signature Scheme based on RSA.

=item B<Crypt::RSA::ES::PKCS1v15>

PKCS #1 v1.5 encryption scheme. 

=item B<Crypt::RSA::SS::PKCS1v15>



( run in 0.710 second using v1.01-cache-2.11-cpan-13bb782fe5a )