HEX
Server: Apache
System: Linux scp1.abinfocom.com 5.4.0-216-generic #236-Ubuntu SMP Fri Apr 11 19:53:21 UTC 2025 x86_64
User: confeduphaar (1010)
PHP: 8.1.33
Disabled: exec,passthru,shell_exec,system
Upload Files
File: //usr/lib/python3/dist-packages/twisted/conch/ssh/__pycache__/keys.cpython-38.pyc
U

�`�[
��@s�dZddlmZmZddlZddlZddlmZmZddl	Z	ddl
mZddlm
Z
ddlmZmZddlmZmZmZmZdd	lmZmZdd
lmZzddlmZmZWn$ek
r�ddlmZm ZYnXdd
l!m"Z"m#Z#m$Z$ddl%m&Z&ddl'm(Z(ddl)m*Z+ddl)m,Z-ddl.m/Z/m0Z0ddl1m2Z2m3Z3ddl4m5Z5ddl6m7Z7m8Z8m9Z9m:Z:m;Z;m<Z<m=Z>m?Z@ddlAmBZBmCZCe�D�e�E�e�F�d�ZGdddd�ZHGdd�deI�ZJGdd�deI�ZKGd d!�d!eI�ZLGd"d#�d#eC�ZMGd$d%�d%eN�ZOd)d'd(�ZPdS)*z$
Handling of RSA, DSA, and EC keys.
�)�absolute_import�divisionN)�md5�sha256)�InvalidSignature)�default_backend)�hashes�
serialization)�dsa�rsa�padding�ec)�load_pem_private_key�load_ssh_public_key)�utils)�encode_dss_signature�decode_dss_signature)�encode_rfc6979_signature�decode_rfc6979_signature)�Cipher�
algorithms�modes)�PyAsn1Error)�univ)�decoder)�encoder)�common�sexpy)�int_from_bytes�int_to_bytes)�	randbytes)�	iterbytes�long�izip�nativeString�unicode�_PY3�_b64decodebytes�_b64encodebytes)�
NamedConstant�Names)secdsa-sha2-nistp256secdsa-sha2-nistp384secdsa-sha2-nistp521snistp256snistp384snistp521)s	secp256r1s	secp384r1s	secp521r1c@seZdZdZdS)�BadKeyErrorzj
    Raised when a key isn't what we expected from it.

    XXX: we really need to check for bad keys
    N��__name__�
__module__�__qualname__�__doc__�r1r1�8/usr/lib/python3/dist-packages/twisted/conch/ssh/keys.pyr+Asr+c@seZdZdZdS)�EncryptedKeyErrorzb
    Raised when an encrypted key is presented to fromString/fromFile without
    a password.
    Nr,r1r1r1r2r3Jsr3c@seZdZdZdS)�BadFingerPrintFormatzS
    Raises when unsupported fingerprint formats are presented to fingerprint.
    Nr,r1r1r1r2r4Rsr4c@seZdZdZe�Ze�ZdS)�FingerprintFormatsa�
    Constants representing the supported formats of key fingerprints.

    @cvar MD5_HEX: Named constant representing fingerprint format generated
        using md5[RFC1321] algorithm in hexadecimal encoding.
    @type MD5_HEX: L{twisted.python.constants.NamedConstant}

    @cvar SHA256_BASE64: Named constant representing fingerprint format
        generated using sha256[RFC4634] algorithm in base64 encoding
    @type SHA256_BASE64: L{twisted.python.constants.NamedConstant}
    N)r-r.r/r0r)�MD5_HEX�
SHA256_BASE64r1r1r1r2r5Ysr5c@sVeZdZdZedCdd��ZedDdd��Zedd��Zed	d
��Zedd��Z	ed
d��Z
edd��Zedd��Zedd��Z
edd��ZedEdd��ZedFdd��ZedGdd��Zdd�Zdd �Zd!d"�Zd#d$�Zd%d&�Zd'd(�Zejfd)d*�Zd+d,�Zd-d.�Zd/d0�Zd1d2�Zd3d4�Zd5d6�Z dHd7d8�Z!d9d:�Z"d;d<�Z#d=d>�Z$d?d@�Z%dAdB�Z&dS)I�Keyau
    An object representing a key.  A key can be either a public or
    private key.  A public key can verify a signature; a private key can
    create or verify a signature.  To generate a string that can be stored
    on disk, use the toString method.  If you have a private key, but want
    the string representation of the public key, use Key.public().toString().
    Nc
Cs4t|d�� }|�|��||�W5QR�SQRXdS)a�
        Load a key from a file.

        @param filename: The path to load key data from.

        @type type: L{str} or L{None}
        @param type: A string describing the format the key data is in, or
        L{None} to attempt detection of the type.

        @type passphrase: L{bytes} or L{None}
        @param passphrase: The passphrase the key is encrypted with, or L{None}
        if there is no encryption.

        @rtype: L{Key}
        @return: The loaded key.
        �rbN)�open�
fromString�read)�cls�filename�type�
passphrase�fr1r1r2�fromFilesszKey.fromFilecCs�t|t�r|�d�}t|t�r(|�d�}|dkr:|�|�}|dkrPtd|f��t|d|��fd�}|dkr|td|f��|jjdkr�|r�td��||�S|||�SdS)a
        Return a Key object corresponding to the string data.
        type is optionally the type of string, matching a _fromString_*
        method.  Otherwise, the _guessStringType() classmethod will be used
        to guess a type.  If the key is encrypted, passphrase is used as
        the decryption key.

        @type data: L{bytes}
        @param data: The key data.

        @type type: L{str} or L{None}
        @param type: A string describing the format the key data is in, or
        L{None} to attempt detection of the type.

        @type passphrase: L{bytes} or L{None}
        @param passphrase: The passphrase the key is encrypted with, or L{None}
        if there is no encryption.

        @rtype: L{Key}
        @return: The loaded key.
        �utf-8Nzcannot guess the type of %rz_fromString_%szno _fromString method for %s�zkey not encrypted)	�
isinstancer%�encode�_guessStringTyper+�getattr�upper�__code__�co_argcount)r=�datar?r@�methodr1r1r2r;�s 




zKey.fromStringc
Cs�t�|�\}}|dkr@t�|d�\}}}|t�||��t���S|dkr�t�|d�\}}}}	}|tj|	tj	|||d�d��t���S|t
kr�|tj�
t
|t�|d�d��t���Std|f��d	S)
a
        Return a public key object corresponding to this public key blob.
        The format of a RSA public key blob is::
            string 'ssh-rsa'
            integer e
            integer n

        The format of a DSA public key blob is::
            string 'ssh-dss'
            integer p
            integer q
            integer g
            integer y

        The format of ECDSA-SHA2-* public key blob is::
            string 'ecdsa-sha2-[identifier]'
            integer x
            integer y

            identifier is the standard NIST curve name.

        @type blob: L{bytes}
        @param blob: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the key type (the first string) is unknown.
        �ssh-rsarD�ssh-dss���p�q�g��y�parameter_numbers��unknown blob type: %sN)r�getNS�getMPr�RSAPublicNumbers�
public_keyrr
�DSAPublicNumbers�DSAParameterNumbers�_curveTabler
�EllipticCurvePublicNumbersZfrom_encoded_pointr+)
r=�blob�keyType�rest�e�nrRrSrTrVr1r1r2�_fromString_BLOB�s<�����
���zKey._fromString_BLOBcCs�t�|�\}}|dkrDt�|d�\}}}}}}	}|j|||||	d�S|dkrxt�|d�\}}	}
}}}|j||
||	|d�S|dd�tt���D�kr�t�|d	�\}}}
}|j||||
d
�St	d|f��dS)
aq
        Return a private key object corresponding to this private key blob.
        The blob formats are as follows:

        RSA keys::
            string 'ssh-rsa'
            integer n
            integer e
            integer d
            integer u
            integer p
            integer q

        DSA keys::
            string 'ssh-dss'
            integer p
            integer q
            integer g
            integer y
            integer x

        EC keys::
            string 'ecdsa-sha2-[identifier]'
            integer x
            integer y
            integer privateValue

            identifier is the standard NIST curve name.


        @type blob: L{bytes}
        @param blob: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the key type (the first string) is unknown.
        rN��rfre�drRrSrO��rVrTrRrS�xcSsg|]}|�qSr1r1)�.0�curver1r1r2�
<listcomp>sz0Key._fromString_PRIVATE_BLOB.<locals>.<listcomp>�)rmrVro�privateValuerYN)
rrZr[�_fromRSAComponents�_fromDSAComponents�listr`�keys�_fromECComponentsr+)r=rbrcrdrfrerj�urRrSrTrVrmrrr1r1r2�_fromString_PRIVATE_BLOB�s'
�zKey._fromString_PRIVATE_BLOBcCs4|�d�r|t|t���St|��d�}|�|�S)a�
        Return a public key object corresponding to this OpenSSH public key
        string.  The format of an OpenSSH public key string is::
            <key type> <base64-encoded public key blob>

        @type data: L{bytes}
        @param data: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the blob type is unknown.
        s
ecdsa-sha2rX)�
startswithrr�decodebytes�splitrg)r=rLrbr1r1r2�_fromString_PUBLIC_OPENSSH%s
zKey._fromString_PUBLIC_OPENSSHcsZ|����}|ddd�}|d�d��r�|s8td��z,|d�dd�\}}|���d	d�\}�Wn&tk
r�td
|df��YnX|dkr�tj	}t
t
|�d�d�d
�}	t��dkr�td��n6|dkr�tj}d}	t��dkr�td��ntd|f��t
t�fdd�tdt��d�D���}
t||
dd
����}t|||
dd
����}||d|	�}
td�|dd���}t||
�t�|
�t�d���}|�|�|��}t|dd��}|d|�}nd�|dd��}t|�}zt�|�d}Wn2tk
�r.}ztd|f��W5d}~XYnX|dk�rL|t||t���S|dk�r�t|�dk�rl|d}t|�dk�r�td ��d!d�|dd"�D�\}}}}}}}}|t j!||||||t j"||d#�d$��#t���S|d%k�rHd&d�|dd�D�\}}}}}t|�dk�rtd'��|t$j%|t$j&|t$j'|||d(�d)�d*�j#t�d��Std+|f��dS),a
        Return a private key object corresponding to this OpenSSH private key
        string.  If the key is encrypted, passphrase MUST be provided.
        Providing a passphrase for an unencrypted key is an error.

        The format of an OpenSSH private key string is::
            -----BEGIN <key type> PRIVATE KEY-----
            [Proc-Type: 4,ENCRYPTED
            DEK-Info: DES-EDE3-CBC,<initialization value>]
            <base64-encoded ASN.1 structure>
            ------END <key type> PRIVATE KEY------

        The ASN.1 structure of a RSA key is::
            (0, n, e, d, p, q)

        The ASN.1 structure of a DSA key is::
            (0, p, q, g, y, x)

        The ASN.1 structure of a ECDSA key is::
            (ECParameters, OID, NULL)

        @type data: L{bytes}
        @param data: The key data.

        @type passphrase: L{bytes} or L{None}
        @param passphrase: The passphrase the key is encrypted with, or L{None}
        if it is not encrypted.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if
            * a passphrase is provided for an unencrypted key
            * the ASN.1 encoding is incorrect
        @raises EncryptedKeyError: if
            * a passphrase is not provided for an encrypted key
        r�i��rX�Proc-Type: 4,ENCRYPTEDz0Passphrase must be provided for an encrypted keyrD� �,zinvalid DEK-info %r)sAES-128-CBCsAES-256-CBC�-�� zAES encrypted key with a bad IVsDES-EDE3-CBC��zDES encrypted key with a bad IVzunknown encryption type %rcs"g|]}t�||d�d��qS)rDr�)�int�rn�i�Zivdatar1r2rp|s�z3Key._fromString_PRIVATE_OPENSSH.<locals>.<listcomp>N�rq�����backendz*Failed to decode key (Bad Passphrase?): %ssECsRSArhz!RSA key failed to decode properlycSsg|]}t|��qSr1�r"�rn�valuer1r1r2rp�s�	�rerf�rRrSrj�dmp1�dmq1�iqmp�public_numberssDSAcSsg|]}t|��qSr1r�r�r1r1r2rp�sz!DSA key failed to decode properlyrQrU�rmr��unknown key type %s)(�strip�
splitlinesrzr3r|�rstrip�
ValueErrorr+rZAESr��len�	TripleDES�bytes�	bytearray�ranger�digestr{�joinrr�CBCr�	decryptor�update�finalize�ord�
berDecoder�decoderrr�RSAPrivateNumbersr\�private_keyr
�DSAPrivateNumbersr^r_)r=rLr@�linesZkind�_ZcipherIVInfoZcipherZalgorithmClass�keySize�iv�ba�bbZdecKey�b64Datar��keyDataZ	removeLenZ
decodedKeyrerfrjrRrSr�r�r�rTrVrmr1r�r2�_fromString_PRIVATE_OPENSSH:s�&

�
�
�
�

����
 ���
��zKey._fromString_PRIVATE_OPENSSHcCs�t�t|dd���}|ddks&t�i}|ddd�D] \}}t�t�|��d||<q:|dddkr�|j|d|d|d	|d
d�S|dddkr�|j|d
|dd�St	d|ddf��dS)a
        Return a public key corresponding to this LSH public key string.
        The LSH public key string format is::
            <s-expression: ('public-key', (<key type>, (<name, <value>)+))>

        The names for a RSA (key type 'rsa-pkcs1-sha1') key are: n, e.
        The names for a DSA (key type 'dsa') key are: y, g, p, q.

        @type data: L{bytes}
        @param data: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the key type is unknown
        rXr�r�
public-keyN�dsa�y�g�p�q�rVrTrRrS�rsa-pkcs1-sha1�n�e�rfre�unknown lsh key type %s)
r�parser{�AssertionErrorrr[�NSrtrsr+�r=rLZsexpZkd�namer1r1r2�_fromString_PUBLIC_LSH�s�zKey._fromString_PUBLIC_LSHcCs6t�|�}|ddkst�i}|ddd�D] \}}t�t�|��d||<q.|dddkr�t|�dksxtt|���|j|d|d|d	|d
|dd�S|ddd
k�rt|�dks�tt|���|d	|d
kr�|d
|d	|d	<|d
<|j|d|d|d|d	|d
d�St	d|ddf��dS)a+
        Return a private key corresponding to this LSH private key string.
        The LSH private key string format is::
            <s-expression: ('private-key', (<key type>, (<name>, <value>)+))>

        The names for a RSA (key type 'rsa-pkcs1-sha1') key are: n, e, d, p, q.
        The names for a DSA (key type 'dsa') key are: y, g, p, q, x.

        @type data: L{bytes}
        @param data: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the key type is unknown
        r�private-keyrXNr�rkr�r�r�r��xrl�	rsa-pkcs1r�r�r��drir�)
rr�r�rr[r�r�rtrsr+r�r1r1r2�_fromString_PRIVATE_LSH�s4
��zKey._fromString_PRIVATE_LSHcCs�t�|�\}}|dkrpt�|�\}}t�|�\}}t�|�\}}t�|�\}}t�|�\}}|j|||||d�S|dkr�t�|�\}}t�|�\}	}t�|�\}
}t�|�\}}t�|�\}}t�|�\}}|j|
||	|||d�Std|f��dS)a�
        Return a private key object corresponsing to the Secure Shell Key
        Agent v3 format.

        The SSH Key Agent v3 format for a RSA key is::
            string 'ssh-rsa'
            integer e
            integer d
            integer n
            integer u
            integer p
            integer q

        The SSH Key Agent v3 format for a DSA key is::
            string 'ssh-dss'
            integer p
            integer q
            integer g
            integer y
            integer x

        @type data: L{bytes}
        @param data: The key data.

        @return: A new key.
        @rtype: L{twisted.conch.ssh.keys.Key}
        @raises BadKeyError: if the key type (the first string) is unknown
        rOrlrN�rfrerjrRrSrxr�N)rrZr[rtrsr+)r=rLrcrRrSrTrVrmrerjrfrxr1r1r2�_fromString_AGENTV3s"zKey._fromString_AGENTV3cCs�|�d�s|�d�rdS|�d�r&dS|�d�r4dS|�d�rBd	S|�d
�sV|�d�r�t�|�\}}d}|r�|d
7}t�|�\}}qh|dkr�dSdSdS)z�
        Guess the type of key in data.  The types map to _fromString_*
        methods.

        @type data: L{bytes}
        @param data: The key data.
        sssh-�ecdsa-sha2-Zpublic_opensshs
-----BEGINZprivate_openssh�{Z
public_lsh�(Zprivate_lshsssh-s
ecdsa-rrXrPZagentv3rbN)rzrrZr[)r=rLZignoredrd�countr1r1r2rG6s"	


zKey._guessStringTypec

Cshtj||d�}|dkr$|�t��}n<tj|||t�||�t�||�t�||�|d�}	|	�t��}||�S)a�
        Build a key from RSA numerical components.

        @type n: L{int}
        @param n: The 'n' RSA variable.

        @type e: L{int}
        @param e: The 'e' RSA variable.

        @type d: L{int} or L{None}
        @param d: The 'd' RSA variable (optional for a public key).

        @type p: L{int} or L{None}
        @param p: The 'p' RSA variable (optional for a public key).

        @type q: L{int} or L{None}
        @param q: The 'q' RSA variable (optional for a public key).

        @type u: L{int} or L{None}
        @param u: The 'u' RSA variable. Ignored, as its value is determined by
        p and q.

        @rtype: L{Key}
        @return: An RSA key constructed from the values as given.
        r�Nr�)	rr\r]rr�Zrsa_crt_dmp1Zrsa_crt_dmq1�rsa_crt_iqmpr�)
r=rfrerjrRrSrx�
publicNumbers�	keyObject�privateNumbersr1r1r2rsRs


�	zKey._fromRSAComponentsc	CsRtj|tj|||d�d�}|dkr0|�t��}ntj||d�}|�t��}||�S)a
        Build a key from DSA numerical components.

        @type y: L{int}
        @param y: The 'y' DSA variable.

        @type p: L{int}
        @param p: The 'p' DSA variable.

        @type q: L{int}
        @param q: The 'q' DSA variable.

        @type g: L{int}
        @param g: The 'g' DSA variable.

        @type x: L{int} or L{None}
        @param x: The 'x' DSA variable (optional for a public key)

        @rtype: L{Key}
        @return: A DSA key constructed from the values as given.
        rQrUNr�)r
r^r_r]rr�r�)	r=rVrRrSrTrmr�r�r�r1r1r2rts��zKey._fromDSAComponentscCsLtj||t|d�}|dkr*|�t��}ntj||d�}|�t��}||�S)a�
        Build a key from EC components.

        @param x: The affine x component of the public point used for verifying.
        @type x: L{int}

        @param y: The affine y component of the public point used for verifying.
        @type y: L{int}

        @param curve: NIST name of elliptic curve.
        @type curve: L{bytes}

        @param privateValue: The private value.
        @type privateValue: L{int}
        �rmrVroN)�
private_valuer�)r
rar`r]rZEllipticCurvePrivateNumbersr�)r=rmrVrorrr�r�r�r1r1r2rw�s��zKey._fromECComponentscCs
||_dS)z�
        Initialize with a private or public
        C{cryptography.hazmat.primitives.asymmetric} key.

        @param keyObject: Low level key.
        @type keyObject: C{cryptography.hazmat.primitives.asymmetric} key.
        N)�
_keyObject)�selfr�r1r1r2�__init__�szKey.__init__cCs8t|�t|�kr0|��|��ko.|��|��kStSdS)zN
        Return True if other represents an object with the same key.
        N)r?rL�NotImplemented)r��otherr1r1r2�__eq__�s z
Key.__eq__cCs|�|�}|tkr|S|S)zO
        Return True if other represents anything other than this key.
        )r�r�)r�r��resultr1r1r2�__ne__�s
z
Key.__ne__cCs�|��dkr�|��}|d�d�}|��r>d|dd�f}nd|dd�f}t|���D]4\}}tr�|dkr�|d|f7}q\|d	||f7}q\|d
Sdt|���|��r�dp�d
|jj	fg}t|�����D]�\}}|�
d|f�t�|�dd�}|r�|dd�}|dd�}d}	t
|�D]}
|	dt|
�f}	�q$t|�dk�rX|	dd�}	|�
d|	�q�q�|dd|d<d�|�SdS)z@
        Return a pretty representation of this object.
        �ECrorCz$<Elliptic Curve Public Key (%s bits)���Nz%<Elliptic Curve Private Key (%s bits)z
curve:
	%sz
%s:
	%sz>
z<%s %s (%s bits)z
Public KeyzPrivate Keyzattr %s:rP��z%02x:r��	�>�
)r?rLr��isPublic�sorted�itemsr&r$r��key_size�appendr�MPr!r�r�r�)r�rLr��out�k�vr�Zby�m�o�cr1r1r2�__repr__�s>
��zKey.__repr__cCst|jtjtjtjf�S)zl
        Check if this instance is a public key.

        @return: C{True} if this is a public key.
        )rEr�r�RSAPublicKeyr
�DSAPublicKeyr
�EllipticCurvePublicKey�r�r1r1r2r�s�zKey.isPubliccCs|��r|St|j���SdS)z�
        Returns a version of this key containing only the public key data.
        If this is a public key, this may or may not be the same object
        as self.

        @rtype: L{Key}
        @return: A public key.
        N)r�r8r�r]r�r1r1r2�publics	z
Key.publiccCsh|tjkr$tt�t|�������S|tjkrVtd�	dd�t
t|������D���Std|f��dS)aO
        The fingerprint of a public key consists of the output of the
        message-digest algorithm in the specified format.
        Supported formats include L{FingerprintFormats.MD5_HEX} and
        L{FingerprintFormats.SHA256_BASE64}

        The input to the algorithm is the public key data as specified by [RFC4253].

        The output of sha256[RFC4634] algorithm is presented to the
        user in the form of base64 encoded sha256 hashes.
        Example: C{US5jTUa0kgX5ZxdqaGF0yGRu8EgKXHNmoT8jHKo1StM=}

        The output of the MD5[RFC1321](default) algorithm is presented to the user as
        a sequence of 16 octets printed as hexadecimal with lowercase letters
        and separated by colons.
        Example: C{c1:b1:30:29:d7:b8:de:6c:97:77:10:d7:46:41:63:87}

        @param format: Format for fingerprint generation. Consists
            hash function and representation format.
            Default is L{FingerprintFormats.MD5_HEX}

        @since: 8.2

        @return: the user presentation of this L{Key}'s fingerprint, as a
        string.

        @rtype: L{str}
        �:cSsg|]}t�|��qSr1)�binasciiZhexlify�rnrmr1r1r2rp?s�z#Key.fingerprint.<locals>.<listcomp>z"Unsupported fingerprint format: %sN)
r5r7r$�base64Z	b64encoderrbr�r6r�r!rr4)r��formatr1r1r2�fingerprints
�

���zKey.fingerprintcCs\t|jtjtjf�rdSt|jtjtjf�r0dSt|jtj	tj
f�rHdStd|jf��dS)z�
        Return the type of the object we wrap.  Currently this can only be
        'RSA', 'DSA', or 'EC'.

        @rtype: L{str}
        @raises RuntimeError: If the object type is unknown.
        �RSA�DSAr�zunknown type of object: %rN)rEr�rr��
RSAPrivateKeyr
r��
DSAPrivateKeyr
r��EllipticCurvePrivateKey�RuntimeErrorr�r1r1r2r?Es$
�
�
�
�zKey.typecCs:|��dkr$dt|jjj�d�Sddd�|��SdS)aK
        Get the type of the object we wrap as defined in the SSH protocol,
        defined in RFC 4253, Section 6.6. Currently this can only be b'ssh-rsa',
        b'ssh-dss' or b'ecdsa-sha2-[identifier]'.

        identifier is the standard NIST curve name

        @return: The key type format.
        @rtype: L{bytes}
        r�r��asciirNrO)rrN)r?�
_secToNistr�ror�rFr�r1r1r2�sshTypeZszKey.sshTypecCs,|jdkrdS|��dkr$|jjjS|jjS)zv
        Return the size of the object we wrap.

        @return: The size of the key.
        @rtype: L{int}
        Nrr�)r�r?ror�r�r1r1r2�sizejs


zKey.sizec	CsVt|jtj�r&|j��}|j|jd�St|jtj�rj|j��}|jj|jj|j	|j
|jt�|j|j
�d�St|jt
j�r�|j��}|j|jj|jj
|jjd�St|jt
j�r�|j��}|j|jj|jjj|jjj
|jjjd�St|jtj��r|j��}|j|j|��d�St|jtj��rB|j��}|jj|jj|j|��d�Std|jf��dS)	z_
        Return the values of the public key as a dictionary.

        @rtype: L{dict}
        r�r�r�)rmrVrTrRrSr�)rmrVrrrozUnexpected key type: %sN)rEr�rr�r�rfrerZprivate_numbersrjrRrSr�r
r�rVrWrTrrmr
r�rrr�r)r�Znumbersr1r1r2rLwsV
�
�	
�
�
�
�zKey.datacCs�|��}|��}|dkr>t�d�t�|d�t�|d�S|dkr�t�d�t�|d�t�|d�t�|d	�t�|d
�S|jjjdd}t�|d
�t�|d
dd��t�dt�	|d|�t�	|d
|��SdS)aG
        Return the public key blob for this key. The blob is the
        over-the-wire format for public keys.

        SECSH-TRANS RFC 4253 Section 6.6.

        RSA keys::
            string 'ssh-rsa'
            integer e
            integer n

        DSA keys::
            string 'ssh-dss'
            integer p
            integer q
            integer g
            integer y

        EC keys::
            string 'ecdsa-sha2-[identifier]'
            integer x
            integer y

            identifier is the standard NIST curve name

        @rtype: L{bytes}
        rrNrerfrrOrRrSrTrV�r�roi����N�rm)
r?rLrr�r�r�ror�rr)r�r?rLZ
byteLengthr1r1r2rb�s(����"��zKey.blobcCs
|��}|��}|dkrvt�d�t�|d�t�|d�t�|d�t�|d�t�|d�t�|d�S|d	kr�t�d
�t�|d�t�|d�t�|d�t�|d�t�|d
�St�|d�t�|d
�t�|d�t�|d�SdS)a�
        Return the private key blob for this key. The blob is the
        over-the-wire format for private keys:

        Specification in OpenSSH PROTOCOL.agent

        RSA keys::
            string 'ssh-rsa'
            integer n
            integer e
            integer d
            integer u
            integer p
            integer q

        DSA keys::
            string 'ssh-dss'
            integer p
            integer q
            integer g
            integer y
            integer x

        EC keys::
            string 'ecdsa-sha2-[identifier]'
            integer x
            integer y
            integer privateValue

            identifier is the NIST standard curve name.
        rrNrfrerjrxrRrSrrOrTrVrmrorrN)r?rLrr�r�)r�r?rLr1r1r2�privateBlob�s: �����������zKey.privateBlobcCs^t|t�r|�d�}t|d|��fd�}|dkr@td|f��|jjdkrT||�S|�SdS)a�
        Create a string representation of this key.  If the key is a private
        key and you want the representation of its public key, use
        C{key.public().toString()}.  type maps to a _toString_* method.

        @param type: The type of string to emit.  Currently supported values
            are C{'OPENSSH'}, C{'LSH'}, and C{'AGENTV3'}.
        @type type: L{str}

        @param extra: Any extra data supported by the selected format which
            is not part of the key itself.  For public OpenSSH keys, this is
            a comment.  For private OpenSSH keys, this is a passphrase to
            encrypt with.
        @type extra: L{bytes} or L{unicode} or L{None}

        @rtype: L{bytes}
        rCz_toString_%sNzunknown key type: %srD)rEr%rFrHrIr+rJrK)r�r?�extrarMr1r1r2�toString
s

zKey.toStringc
s�|��}|��r~|��dkrF|s$d}|j�tjjtjj�d|�	�St
|����dd��|sbd}|�
�d�d|�	�S|��dkr�|s�t��}n
t�|�}|j�tjjtjj|�Sd�d|���d�df�g}|��dk�r6|d	|d
}}d|d|d
|d|||d|d|d|d|df	}n$d|d	|d
|d|d|df}t��}tt��|�D]\}	}
|�|	t�|
���qpt�|�}|�rrt�d�}d�dd�t |�D��}
|
�d�}
|�!d�|�!d|
d�t"||��#�}t"|||��#�}||dd�}dt$|�d}|t%|�|�d�7}t&t'�(|�t)�*|�t+�d��,�}|�-|�|�.�}t
|��dd��|�fdd�t/dt$��d�D�7}|�!d�d|���d�df��d�|�SdS) a�
        Return a public or private OpenSSH string.  See
        _fromString_PUBLIC_OPENSSH and _fromString_PRIVATE_OPENSSH for the
        string formats.  If extra is present, it represents a comment for a
        public key, or a passphrase for a private key.

        @param extra: Comment for a public key or passphrase for a
            private key
        @type extra: L{bytes}

        @rtype: L{bytes}
        r�r�r��
s-----BEGIN r	s PRIVATE KEY-----rrRrSrrfrerjrXrxrTrVrmr�r�cSsg|]}dt|�f�qS)z%02X)r�r�r1r1r2rpcsz)Key._toString_OPENSSH.<locals>.<listcomp>rsDEK-Info: DES-EDE3-CBC,Nr�r�csg|]}�||d��qS)�@r1r��r�r1r2rpvsrs	-----END )0rLr�r?r�Zpublic_bytesr	�EncodingZOpenSSHZPublicFormatr��encodebytesrb�replacer�NoEncryptionZBestAvailableEncryption�
private_bytes�PEM�
PrivateFormat�TraditionalOpenSSLr�rFr�Sequencer#�	itertoolsr�ZsetComponentByPositionZInteger�
berEncoderr ZsecureRandomr!r�rr�r��chrrrr�rr�r�	encryptorr�r�r�)r�rrLr!r�rRrSZobjDataZasn1Sequence�indexr�Zasn1Datar�Zhexivr�r�ZencKeyZpadLenr1rr2�_toString_OPENSSH)s�
���

����



�
"�zKey._toString_OPENSSHcCs�|��}|��}|���r|dkrft�dddt�|d�dd�gdt�|d	�dd�gggg�}n�|d
kr�t�dddt�|d
�dd�gdt�|d�dd�gdt�|d�dd�gdt�|d�dd�gggg�}ntd|f��dt|��	dd�dS|dk�r�|d
|d}}t�dddt�|d�dd�gdt�|d	�dd�gdt�|d�dd�gdt�|�dd�gdt�|�dd�gdt�|d|d�dd�gdt�|d|d�dd�gd t�|d!�dd�gg	gg�S|d
k�r�t�dddt�|d
�dd�gdt�|d�dd�gdt�|d�dd�gdt�|d�dd�gd"t�|d#�dd�gggg�Std$|f��dS)%z�
        Return a public or private LSH key.  See _fromString_PUBLIC_LSH and
        _fromString_PRIVATE_LSH for the key formats.

        @rtype: L{bytes}
        rr�r�r�rfrPNr�rerr�r�rRr�rSr�rTr�rVr�r�rr��}r�r�r�rj�arX�b�crxr�rmzunknown key type %s')
rLr?r�rZpackrr�r+rr)r�rLr?r�rRrSr1r1r2�
_toString_LSH{sp
��
��
�
������
��zKey._toString_LSHcCs�|��}|��s�|��dkrF|d|d|d|d|d|df}n.|��dkrt|d|d|d	|d
|df}t�|���d�ttj|��Sd
S)z�
        Return a private Secure Shell Agent v3 key.  See
        _fromString_AGENTV3 for the key format.

        @rtype: L{bytes}
        rrerjrfrxrRrSrrTrVrmr�N)	rLr�r?rr�rr��mapr�)r�rL�valuesr1r1r2�_toString_AGENTV3�s��zKey._toString_AGENTV3cCs�|��}|dkr6|j�|t��t���}t�|�}�n>|dkrx|j�|t���}t	|�\}}t�t
|d�t
|d��}n�|dk�rt|��}|dkr�t��}n|dkr�t�
�}nt��}|j�|t�|��}	t	|	�\}}t
|�}
t
|�}t|
d�tk�rt|
d�}n|
d}|d@�r d	|
}
t|d�tk�r@t|d�}
n|d}
|
d@�rZd	|}t�t�|
�t�|��}t�|���|S)
z�
        Sign some data with this key.

        SECSH-TRANS RFC 4253 Section 6.6.

        @type data: L{bytes}
        @param data: The data to sign.

        @rtype: L{bytes}
        @return: A signature for the given data.
        rr�r���r��)r?r��signr�PKCS1v15r�SHA1rr�rrr�SHA256�SHA384�SHA512r
�ECDSA�strr�r)r�rLrcZsigZret�r�sr��hashSize�	signaturer9ZsbZrcompZscompr1r1r2r1�s>




zKey.signcCs�t|�dkrdt�|�}}nt�|�\}}||��kr<dS|��}|dkr�|j}|��sb|��}t�|�d|t	�
�t��f}�n|dkr�t�|�d}t
|dd�d	�}t
|dd�d	�}	t||	�}|j}|��s�|��}||t��f}n�|d
k�r�t�|�d}t�|d�\}
}}t
|
d	�}t
|d	�}	t||	�}|j}|���sN|��}|��}
|
dk�rjt��}n|
d
k�r~t��}nt��}||t�|�f}z|j|�Wntk
�r�YdSXdSdS)a
        Verify a signature using this key.

        @type signature: L{bytes}
        @param signature: The signature to verify.

        @type data: L{bytes}
        @param data: The signed data.

        @rtype: L{bool}
        @return: C{True} if the signature is valid.
        �(rOFrrrNr,Zbigr�rDr-r.T)r�rr�rZrr?r�r�r]rr2rr3rrrr4r5r6r
r7�verifyr)r�r<rLZ
signatureTypercr��argsZconcatenatedSignaturer9r:ZrstrZsstrrdr�r;r1r1r2r>�sZ
�









z
Key.verify)NN)NN)NNNN)N)N)N)'r-r.r/r0�classmethodrBr;rgryr}r�r�r�r�rGrsrtrwr�r�r�r�r�r�r5r6rr?rrrLrbrrr#r(r+r1r>r1r1r1r2r8js^)
:
6



#
0
,"
		)
(
;,/
R4?r8�c
Cs�|��jdd�|��sPtjd|t�d�}|jtjj	tj
jt��d�}|�
|�|�d��,}tj|��dt�d�}t|�W5QR�SQRXdS)	a�
    This function returns a persistent L{Key}.

    The key is loaded from a PEM file in C{location}. If it does not exist, a
    key with the key size of C{keySize} is generated and saved.

    @param location: Where the key is stored.
    @type location: L{twisted.python.filepath.FilePath}

    @param keySize: The size of the key, if it needs to be generated.
    @type keySize: L{int}

    @returns: A persistent key.
    @rtype: L{Key}
    T)ZignoreExistingDirectoryi)Zpublic_exponentr�r�)�encodingrZencryption_algorithmr9N)Zpasswordr�)�parent�makedirs�existsrZgenerate_private_keyrrr	rrrrrZ
setContentr:rr<r8)�locationr�Z
privateKeyZpemZkeyFiler1r1r2�_getPersistentRSAKeyFs(��
�rG)rA)Qr0Z
__future__rrr�rZhashlibrrrZcryptography.exceptionsrZcryptography.hazmat.backendsrZcryptography.hazmat.primitivesrr	Z)cryptography.hazmat.primitives.asymmetricr
rrr
Z,cryptography.hazmat.primitives.serializationrrZcryptographyrZ/cryptography.hazmat.primitives.asymmetric.utilsrr�ImportErrorrrZ&cryptography.hazmat.primitives.ciphersrrrZpyasn1.errorrZpyasn1.typerZpyasn1.codec.berrr�rrZtwisted.conch.sshrrZtwisted.conch.ssh.commonrrZtwisted.pythonr Ztwisted.python.compatr!r"r#r$r%r&r'r{r(rZtwisted.python.constantsr)r*Z	SECP256R1Z	SECP384R1Z	SECP521R1r`r
�	Exceptionr+r3r4r5�objectr8rGr1r1r1r2�<module>s`(��
	e