The London Perl and Raku Workshop takes place on 26th Oct 2024. If your company depends on Perl, please consider sponsoring and/or attending.

NAME

Crypt::PBC - OO interface for the Stanford PBC library

SYNOPSIS

    use Crypt::PBC;

    my $pairing = new Crypt::PBC("params_d.txt");
    my $G1      = $pairing->init_G1->random;
    my $G2      = $pairing->init_G2->random->double->square;
    my $GT      = $pairing->init_GT->pairing_apply( $G1, $G2 );

"Chapter 1. Overview"

The following text is the Overview chapter from the PBC library documentation:

    The PBC library is a free portable C library designed to make it
    easy to implement pairing-based cryptosystems. It provides an
    abstract interface to a cyclic group with a bilinear pairing, and
    the programmer does not need to worry about, or even know about
    elliptic curves.

    It is built on top of GMP, another C library which performs
    arbitrary precision arithmetic on integers, rationals and floats
    with strong emphasis on portability and speed.

    The PBC library homepage: http://crypto.stanford.edu/pbc/

    The GMP library homepage: http://www.swox.com/gmp/

Nomenclature

The documentation (and error messages) for these modules frequently refer to the LHS, the RHS, EXPO, and BASE. They are the left hand side, right hand side, exponent and base. In an algebraic equation: LHS=RHS and LHS=BASE^EXPO. In other words, the LHS is the element to which a value is being assigned. There may sometimes be more than one RHS, or it might be called the a1 or n1; but, there will only be one LHS.

Perl Module Methods

The Perl Module methods implement an OO interface that the author (Paul) highly recommends using. The only Perl Module OO function in the Crypt::PBC package is new(). Please see Crypt::PBC::Pairing and Crypt::PBC::Element for the guts of the intended OO interface.

Crypt::PBC::new()

Returns a new PBC pairing object. new() takes, as arguments, either the name of a file, a file stream (e.g., new Crypt::PBC(\*STDIN)), or the params for a curve as a string. Ben Lynn provides a zip file of d-type curves:

    MNT curve parameters for embedding degree 6 (which I
    call type D curves), for all D less than a million, and
    for subgroup sizes at least 80 bits and less than 300
    bits long. Generated using test programs bundled with
    PBC library.

    http://crypto.stanford.edu/pbc/download.html

XS Loaded Functions

This section is basically a listing of the PBC functions as they are imported. You can use them directly if you're already comfortable with the layout of PBC. If you're starting from scratch and aren't much of a C coder, you'll have an easier time using the Perl Module methods because they implement a little type-safety to protect perl coders from segfaults.

Mixing and matching direct calls with the Perl Module methods is a sure way to run into trouble, since the Perl Module methods tag the PBC elements with a type.

+++ NOTE +++

You can use these functions successfully, but the intended interface was described above. Crypt::PBC::Element describes that interface in detail.

+++ /NOTE +++

Pairing Functions

    # Initialize a pairing from an open file handle
    my $pairing = &Crypt::PBC::pairing_init_stream(\*STDIN);

    # Initialize a pairing from a a $string
    my $pairing = &Crypt::PBC::pairing_init_str($string);

    # Clear the memory malloced for the pairing
    &Crypt::PBC::pairing_clear($pairing);

    # Apply the pairing.  Be careful here.  If you pass the wrong type of
    # elements, GT = apply(G1, G2), this will segmentation fault!  Please
    # see the PBC documentation for further information:
    #   http://crypto.stanford.edu/pbc/manual/
    &Crypt::PBC::pairing_apply($LHS, $RHS1, $RHS2, $pairing);

Element Initializer and Assignment Functions

    my $element_in_G1 = &Crypt::PBC::element_init_G1($pairing);
    my $element_in_G2 = &Crypt::PBC::element_init_G2($pairing);
    my $element_in_GT = &Crypt::PBC::element_init_GT($pairing);
    my $element_in_Zr = &Crypt::PBC::element_init_Zr($pairing);

    # Do not forget to clear your memory!
    &Crypt::PBC::element_clear( $element ); # in any group

    # assign some random to $element
    # (uses /dev/urandom if possible, or rand() if necessary)
    &Crypt::PBC::element_random( $element );
    &Crypt::PBC::element_set0( $element ); # set to 0
    &Crypt::PBC::element_set1( $element ); # set to 1
    &Crypt::PBC::element_set( $a, $b );    # a=b
    &Crypt::PBC::element_set_si( $a, 5 );  # a=5

    &Crypt::PBC::element_set_mpz( $a, $bigint ); 
      # For this one, construct a Math::BigInt::GMP and pass that for
      # $bigint. Alternatively, you can construct a $i=Math::BigInt and
      # pass the $i->{value}.  (That interface is probably not well
      # supported but is the only one of which the author is aware.)

    &Crypt::PBC::element_from_hash( $element, $hash ); 
      # Set $element based on the bytes in $hash.  You must use some kind
      # of hashing algorithm (e.g., Digest::SHA1) to map data to an
      # element:
      #
      # "In general you cannot feed it plaintext. You should only give it
      # short strings of bytes (e.g. 160 bits if G1 has order around 2^160,
      # which is the case for most of the bundled pairing parameters)."
      # -- Lynn

    &Crypt::PBC::element_from_bytes( $element, $bytes ); 
      # Set $element based on the bytes in $bytes.  this probably isn't useful
      # unless $bytes is like $spewed_result from element_export() below.

Arithmetic Functions

    # lhs=rhs1+rhs2 -- make sure these are all the same type ...
    &Crypt::PBC::element_add($lhs, $rhs1, $rhs2);
    &Crypt::PBC::element_sub($lhs, $rhs1, $rhs2); # lhs=rhs1-rhs2
    &Crypt::PBC::element_mul($lhs, $rhs1, $rhs2);
    &Crypt::PBC::element_div($lhs, $rhs1, $rhs2);

    # (whatever these mean is in the context of the $pairing)
    &Crypt::PBC::element_double($lhs, $rhs); # lhs = 2*rhs 
    &Crypt::PBC::element_halve( $lhs, $rhs); # lhs = rhs/2
    &Crypt::PBC::element_square($lhs, $rhs); # lhs = rhs^2
    &Crypt::PBC::element_neg(   $lhs, $rhs); # (please see the PBC docs)
    &Crypt::PBC::element_invert($lhs, $rhs); # lhs = 1/rhs

    # Here's a few other choices for mul
    &Crypt::PBC::element_mul_zn( $lhs, $rhs1, $rhs2 );
      # $rhs1 and $lhs should be of the same type, but here $rhs2 should be
      # in Zr instead of being in the same group like in element_mul()
      # above 

    &Crypt::PBC::element_mul_mpz( $lhs, $rhs1, $rhs2 );
      # For this one, construct a Math::BigInt::GMP and pass that for
      # $rhs2 or pass $i->{value} from a Math::BigInt.

    &Crypt::PBC::element_mul_si( $lhs, $rhs1, $rhs2 );
      # Here, $rhs2 is a regular old integer...

    &Crypt::PBC::element_pow_zn( $lhs, $a, $n); # lhs = a^n
    &Crypt::PBC::element_pow2_zn($lhs, $a1, $n1, $a2, $n2); # a1^n1 * a2^n2
    &Crypt::PBC::element_pow3_zn($lhs, $a1, $n1, $a2, $n2, $a3, $n3);
      # in the above, the lhs and a\d+ should be in the same group, n\d+ in Zr

    &Crypt::PBC::element_pow_mpz( $lhs, $a, $n);
    &Crypt::PBC::element_pow2_mpz($lhs, $a1, $n1, $a2, $n2);
    &Crypt::PBC::element_pow3_mpz($lhs, $a1, $n1, $a2, $n2, $a3, $n3);
      # like the _zn functions, but n\d+ should be Math::BigInt::GMP
      # or pass $i->{value} from a Math::BigInt.

Comparison Functions

    &Crypt::PBC::element_is0( $a );    # 1 when $a is 0
    &Crypt::PBC::element_is1( $a );    # 1 when $a is 1
    &Crypt::PBC::element_cmp( $a,$b ); # paradoxically, false when $a == $b
    &Crypt::PBC::element_is_sqr( $a ); # 1 when $a is a perfect square ...
     # see the PBC docs for words like "residue"

Export and Output

    # Please check the PBC docs ...
    &Crypt::PBC::element_fprintf(\*OUTFILE, $format, $element);
    &Crypt::PBC::element_fprintf(\*STDOUT, "example element=\%B\n", $element);
    # (You may be surprised how many bigints are in these group elements.)

    my $spewed_result = &Crypt::PBC::export_element($element);
    # These are bytes, dumped from the $element, that can be used to
    # reconstruct the element or used for interacting with real life data.

    # Example:
    my $cipher = new Crypt::CBC({
        header => "randomiv", 
        key    => &Crypt::PBC::export_element($element), 
        cipher => 'Blowfish', # hehe
    });

    my $big = &Crypt::PBC::element_to_mpz( $element );
    # Returns a Math::BigInt::GMP, not a Math::BigInt!  WARNING: the
    # DESTROY() method from Math::BigInt::GMP will be missing unless you
    # require that package into your program.  You'll want to do that or you'll
    # have a memory leak...  Lastly, this is really only useful for elements in
    # Zr -- element_fprintf() to see what I mean.

XS AUTHOR

Paul Miller jettero@cpan.org

Paul is using this software in his own projects... If you find bugs, please please please let him know. :) Actually, let him know if you find it handy at all. Half the fun of releasing this stuff is knowing that people use it.

Additionally, he is aware that the documentation sucks. Should you email him for help, he will most likely try to give it.

COPYRIGHT

GPL! (and/or whatever license the gnu regex engine is under)

Though, additionally, I will say that I'll be tickled if you were to include this package in any commercial endeavor. Also, any thoughts to the effect that using this module will somehow make your commercial package GPL should be washed away.

I hereby release you from any such silly conditions -- if possible while still matching the license from libpbc.

This package and any modifications you make to it must remain GPL. Any programs you (or your company) write shall remain yours (and under whatever copyright you choose) even if you use this package's intended and/or exported interfaces in them.

Lastly, having said all the above, there may be certain restrictions from the PBC library itself that I cannot amend or take away!

SPECIAL THANKS

Without the direction of Dr. Leszek T. Lilien (http://www.cs.wmich.edu/~llilien/), I never would have heard of IBE/PBC -- much less develop any interest in it. Crypto is not his specialty, but like any good professor, he's interested in everything.

SEE ALSO

    http://crypto.stanford.edu/pbc/

    http://groups.google.com/group/pbc-devel

perl(1), Crypt::PBC::Pairing, Crypt::PBC::Element