def generate_pair(algorithm, bit_size=None, curve=None):
if algorithm not in set(['<STR_LIT>', '<STR_LIT>', '<STR_LIT>']):<EOL><INDENT>raise ValueError(pretty_message(<EOL>'''<STR_LIT>''',<EOL>repr(algorithm)<EOL>))<EOL><DEDENT>if algorithm == '<STR_LIT>':<EOL><INDENT>if bit_size not in set([<NUM_LIT>, <NUM_LIT>, <NUM_LIT>, <NUM_LIT>]):<EOL><INDENT>raise ValueError(pretty_message(<EOL>'''<STR_LIT>''',<EOL>repr(bit_size)<EOL>))<EOL><DEDENT><DEDENT>elif algorithm == '<STR_LIT>':<EOL><INDENT>if libcrypto_version_info < (<NUM_LIT:1>,):<EOL><INDENT>if bit_size != <NUM_LIT>:<EOL><INDENT>raise ValueError(pretty_message(<EOL>'''<STR_LIT>''',<EOL>repr(bit_size)<EOL>))<EOL><DEDENT><DEDENT>else:<EOL><INDENT>if bit_size not in set([<NUM_LIT>, <NUM_LIT>, <NUM_LIT>]):<EOL><INDENT>raise ValueError(pretty_message(<EOL>'''<STR_LIT>''',<EOL>repr(bit_size)<EOL>))<EOL><DEDENT><DEDENT><DEDENT>elif algorithm == '<STR_LIT>':<EOL><INDENT>if curve not in set(['<STR_LIT>', '<STR_LIT>', '<STR_LIT>']):<EOL><INDENT>raise ValueError(pretty_message(<EOL>'''<STR_LIT>''',<EOL>repr(curve)<EOL>))<EOL><DEDENT><DEDENT>if algorithm == '<STR_LIT>':<EOL><INDENT>rsa = None<EOL>exponent = None<EOL>try:<EOL><INDENT>rsa = libcrypto.RSA_new()<EOL>if is_null(rsa):<EOL><INDENT>handle_openssl_error(<NUM_LIT:0>)<EOL><DEDENT>exponent_pointer = new(libcrypto, '<STR_LIT>')<EOL>result = libcrypto.BN_dec2bn(exponent_pointer, b'<STR_LIT>')<EOL>handle_openssl_error(result)<EOL>exponent = unwrap(exponent_pointer)<EOL>result = libcrypto.RSA_generate_key_ex(rsa, bit_size, exponent, null())<EOL>handle_openssl_error(result)<EOL>buffer_length = libcrypto.i2d_RSAPublicKey(rsa, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2d_RSAPublicKey(rsa, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>public_key_bytes = bytes_from_buffer(buffer, buffer_length)<EOL>buffer_length = libcrypto.i2d_RSAPrivateKey(rsa, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2d_RSAPrivateKey(rsa, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>private_key_bytes = bytes_from_buffer(buffer, buffer_length)<EOL><DEDENT>finally:<EOL><INDENT>if rsa:<EOL><INDENT>libcrypto.RSA_free(rsa)<EOL><DEDENT>if exponent:<EOL><INDENT>libcrypto.BN_free(exponent)<EOL><DEDENT><DEDENT><DEDENT>elif algorithm == '<STR_LIT>':<EOL><INDENT>dsa = None<EOL>try:<EOL><INDENT>dsa = libcrypto.DSA_new()<EOL>if is_null(dsa):<EOL><INDENT>handle_openssl_error(<NUM_LIT:0>)<EOL><DEDENT>result = libcrypto.DSA_generate_parameters_ex(dsa, bit_size, null(), <NUM_LIT:0>, null(), null(), null())<EOL>handle_openssl_error(result)<EOL>result = libcrypto.DSA_generate_key(dsa)<EOL>handle_openssl_error(result)<EOL>buffer_length = libcrypto.i2d_DSA_PUBKEY(dsa, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2d_DSA_PUBKEY(dsa, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>public_key_bytes = bytes_from_buffer(buffer, buffer_length)<EOL>buffer_length = libcrypto.i2d_DSAPrivateKey(dsa, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2d_DSAPrivateKey(dsa, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>private_key_bytes = bytes_from_buffer(buffer, buffer_length)<EOL><DEDENT>finally:<EOL><INDENT>if dsa:<EOL><INDENT>libcrypto.DSA_free(dsa)<EOL><DEDENT><DEDENT><DEDENT>elif algorithm == '<STR_LIT>':<EOL><INDENT>ec_key = None<EOL>try:<EOL><INDENT>curve_id = {<EOL>'<STR_LIT>': LibcryptoConst.NID_X9_62_prime256v1,<EOL>'<STR_LIT>': LibcryptoConst.NID_secp384r1,<EOL>'<STR_LIT>': LibcryptoConst.NID_secp521r1,<EOL>}[curve]<EOL>ec_key = libcrypto.EC_KEY_new_by_curve_name(curve_id)<EOL>if is_null(ec_key):<EOL><INDENT>handle_openssl_error(<NUM_LIT:0>)<EOL><DEDENT>result = libcrypto.EC_KEY_generate_key(ec_key)<EOL>handle_openssl_error(result)<EOL>libcrypto.EC_KEY_set_asn1_flag(ec_key, LibcryptoConst.OPENSSL_EC_NAMED_CURVE)<EOL>buffer_length = libcrypto.i2o_ECPublicKey(ec_key, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2o_ECPublicKey(ec_key, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>public_key_point_bytes = bytes_from_buffer(buffer, buffer_length)<EOL>public_key = keys.PublicKeyInfo({<EOL>'<STR_LIT>': keys.PublicKeyAlgorithm({<EOL>'<STR_LIT>': '<STR_LIT>',<EOL>'<STR_LIT>': keys.ECDomainParameters(<EOL>name='<STR_LIT>',<EOL>value=curve<EOL>)<EOL>}),<EOL>'<STR_LIT>': public_key_point_bytes<EOL>})<EOL>public_key_bytes = public_key.dump()<EOL>buffer_length = libcrypto.i2d_ECPrivateKey(ec_key, null())<EOL>if buffer_length < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(buffer_length)<EOL><DEDENT>buffer = buffer_from_bytes(buffer_length)<EOL>result = libcrypto.i2d_ECPrivateKey(ec_key, buffer_pointer(buffer))<EOL>if result < <NUM_LIT:0>:<EOL><INDENT>handle_openssl_error(result)<EOL><DEDENT>private_key_bytes = bytes_from_buffer(buffer, buffer_length)<EOL><DEDENT>finally:<EOL><INDENT>if ec_key:<EOL><INDENT>libcrypto.EC_KEY_free(ec_key)<EOL><DEDENT><DEDENT><DEDENT>return (load_public_key(public_key_bytes), load_private_key(private_key_bytes))<EOL>
Generates a public/private key pair

:param algorithm:
    The key algorithm - "rsa", "dsa" or "ec"

:param bit_size:
    An integer - used for "rsa" and "dsa". For "rsa" the value maye be 1024,
    2048, 3072 or 4096. For "dsa" the value may be 1024, plus 2048 or 3072
    if OpenSSL 1.0.0 or newer is available.

:param curve:
    A unicode string - used for "ec" keys. Valid values include "secp256r1",
    "secp384r1" and "secp521r1".

:raises:
    ValueError - when any of the parameters contain an invalid value
    TypeError - when any of the parameters are of the wrong type
    OSError - when an error is returned by the OS crypto library

:return:
    A 2-element tuple of (PublicKey, PrivateKey). The contents of each key
    may be saved by calling .asn1.dump().