scapy.layers.tls.keyexchange

TLS key exchange logic.

class scapy.layers.tls.keyexchange.ClientDiffieHellmanPublic(_pkt, /, *, dh_Yclen=None, dh_Yc=b'')[source]

Bases: _GenericTLSSessionInheritance

If the user provides a value for dh_Yc attribute, we assume he will set the pms and ms accordingly and trigger the key derivation on his own.

XXX As specified in 7.4.7.2. of RFC 4346, we should distinguish the needs for implicit or explicit value depending on availability of DH parameters in client certificate. For now we can only do ephemeral/explicit DH.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ClientDiffieHellmanPublic'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ClientDiffieHellmanPublic).dh_Yclen>, <StrLenField (ClientDiffieHellmanPublic).dh_Yc>]
fill_missing(**kwargs: Any) Any[source]
guess_payload_class(p)[source]
post_build(pkt, pay)[source]
post_dissection(m)[source]

First we update the client DHParams. Then, we try to update the server DHParams generated during Server*DHParams building, with the shared secret. Finally, we derive the session keys and update the context.

class scapy.layers.tls.keyexchange.ClientECDiffieHellmanPublic(_pkt, /, *, ecdh_Yclen=None, ecdh_Yc=b'')[source]

Bases: _GenericTLSSessionInheritance

Note that the ‘len’ field is 1 byte longer than with the previous class.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ClientECDiffieHellmanPublic'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ClientECDiffieHellmanPublic).ecdh_Yclen>, <StrLenField (ClientECDiffieHellmanPublic).ecdh_Yc>]
fill_missing(**kwargs: Any) Any[source]
post_build(pkt, pay)[source]
post_dissection(m)[source]
class scapy.layers.tls.keyexchange.ClientPSKIdentity(_pkt, /, *, psk_identity_len=None, psk_identity=b'')[source]

Bases: Packet

XXX We provide parsing abilities for ServerPSKParams, but the context operations have not been implemented yet. See RFC 4279. Note that we do not cover the (EC)DHE_PSK nor the RSA_PSK key exchange, which should contain either an EncryptedPMS or a ClientDiffieHellmanPublic.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ClientPSKIdentity'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ClientPSKIdentity).psk_identity_len>, <StrLenField (ClientPSKIdentity).psk_identity>]
class scapy.layers.tls.keyexchange.ECCurvePkt(_pkt, /, *, alen=None, a=b'', blen=None, b=b'')[source]

Bases: Packet

aliastypes = [<class 'scapy.layers.tls.keyexchange.ECCurvePkt'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ECCurvePkt).alen>, <StrLenField (ECCurvePkt).a>, <FieldLenField (ECCurvePkt).blen>, <StrLenField (ECCurvePkt).b>]
class scapy.layers.tls.keyexchange.ECPentanomialBasis(_pkt, /, *, k1len=None, k1=b'', k2len=None, k2=b'', k3len=None, k3=b'')[source]

Bases: Packet

aliastypes = [<class 'scapy.layers.tls.keyexchange.ECPentanomialBasis'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ECPentanomialBasis).k1len>, <StrLenField (ECPentanomialBasis).k1>, <FieldLenField (ECPentanomialBasis).k2len>, <StrLenField (ECPentanomialBasis).k2>, <FieldLenField (ECPentanomialBasis).k3len>, <StrLenField (ECPentanomialBasis).k3>]
guess_payload_class(p)[source]
val = 1
class scapy.layers.tls.keyexchange.ECTrinomialBasis(_pkt, /, *, klen=None, k=b'')[source]

Bases: Packet

aliastypes = [<class 'scapy.layers.tls.keyexchange.ECTrinomialBasis'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ECTrinomialBasis).klen>, <StrLenField (ECTrinomialBasis).k>]
guess_payload_class(p)[source]
val = 0
class scapy.layers.tls.keyexchange.EncryptedPreMasterSecret(_pkt, /, *, client_version=None, random=None)[source]

Bases: _GenericTLSSessionInheritance

Pay attention to implementation notes in section 7.4.7.1 of RFC 5246.

aliastypes = [<class 'scapy.layers.tls.keyexchange.EncryptedPreMasterSecret'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
classmethod dispatch_hook(_pkt=None, *args, **kargs)[source]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<_TLSClientVersionField (EncryptedPreMasterSecret).client_version>, <StrFixedLenField (EncryptedPreMasterSecret).random>]
guess_payload_class(p)[source]
post_build(pkt, pay)[source]

We encrypt the premaster secret (the 48 bytes) with either the server certificate or the temporary RSA key provided in a server key exchange message. After that step, we add the 2 bytes to provide the length, as described in implementation notes at the end of section 7.4.7.1.

pre_dissect(m)[source]
class scapy.layers.tls.keyexchange.ServerDHParams(_pkt, /, *, dh_plen=None, dh_p=b'', dh_glen=None, dh_g=b'', dh_Yslen=None, dh_Ys=b'')[source]

Bases: _GenericTLSSessionInheritance

ServerDHParams for FFDH-based key exchanges, as defined in RFC 5246/7.4.3.

Either with .fill_missing() or .post_dissection(), the server_kx_privkey or server_kx_pubkey of the TLS context are updated according to the parsed/assembled values. It is the user’s responsibility to store and restore the original values if he wants to keep them. For instance, this could be done between the writing of a ServerKeyExchange and the receiving of a ClientKeyExchange (which includes secret generation).

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerDHParams'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ServerDHParams).dh_plen>, <StrLenField (ServerDHParams).dh_p>, <FieldLenField (ServerDHParams).dh_glen>, <StrLenField (ServerDHParams).dh_g>, <FieldLenField (ServerDHParams).dh_Yslen>, <StrLenField (ServerDHParams).dh_Ys>]
fill_missing(**kwargs: Any) Any[source]
guess_payload_class(p)[source]

The signature after the params gets saved as Padding. This way, the .getfield() which _TLSServerParamsField inherits from PacketField will return the signature remain as expected.

post_dissection(r)[source]
register_pubkey(**kwargs: Any) Any[source]
class scapy.layers.tls.keyexchange.ServerECDHExplicitChar2Params(_pkt, /, *, curve_type=2, m=None, basis_type=None, basis=<ECTrinomialBasis  |>, curve=<ECCurvePkt  |>, baselen=None, base=b'', order=None, cofactor=None, pointlen=None, point=b'')[source]

Bases: _GenericTLSSessionInheritance

We provide parsing abilities for Char2Params, but there is no support from the cryptography library, hence no context operations.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerECDHExplicitChar2Params'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<ByteEnumField (ServerECDHExplicitChar2Params).curve_type>, <ShortField (ServerECDHExplicitChar2Params).m>, <_ECBasisTypeField (ServerECDHExplicitChar2Params).basis_type>, <_ECBasisField (ServerECDHExplicitChar2Params).basis>, <PacketField (ServerECDHExplicitChar2Params).curve>, <FieldLenField (ServerECDHExplicitChar2Params).baselen>, <StrLenField (ServerECDHExplicitChar2Params).base>, <ByteField (ServerECDHExplicitChar2Params).order>, <ByteField (ServerECDHExplicitChar2Params).cofactor>, <FieldLenField (ServerECDHExplicitChar2Params).pointlen>, <StrLenField (ServerECDHExplicitChar2Params).point>]
fill_missing()[source]
guess_payload_class(p)[source]
class scapy.layers.tls.keyexchange.ServerECDHExplicitPrimeParams(_pkt, /, *, curve_type=1, plen=None, p=b'', curve=None, baselen=None, base=b'', orderlen=None, order=b'', cofactorlen=None, cofactor=b'', pointlen=None, point=b'')[source]

Bases: _GenericTLSSessionInheritance

We provide parsing abilities for ExplicitPrimeParams, but there is no support from the cryptography library, hence no context operations.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerECDHExplicitPrimeParams'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<ByteEnumField (ServerECDHExplicitPrimeParams).curve_type>, <FieldLenField (ServerECDHExplicitPrimeParams).plen>, <StrLenField (ServerECDHExplicitPrimeParams).p>, <PacketField (ServerECDHExplicitPrimeParams).curve>, <FieldLenField (ServerECDHExplicitPrimeParams).baselen>, <StrLenField (ServerECDHExplicitPrimeParams).base>, <FieldLenField (ServerECDHExplicitPrimeParams).orderlen>, <StrLenField (ServerECDHExplicitPrimeParams).order>, <FieldLenField (ServerECDHExplicitPrimeParams).cofactorlen>, <StrLenField (ServerECDHExplicitPrimeParams).cofactor>, <FieldLenField (ServerECDHExplicitPrimeParams).pointlen>, <StrLenField (ServerECDHExplicitPrimeParams).point>]
fill_missing()[source]

Note that if it is not set by the user, the cofactor will always be 1. It is true for most, but not all, TLS elliptic curves.

guess_payload_class(p)[source]
class scapy.layers.tls.keyexchange.ServerECDHNamedCurveParams(_pkt, /, *, curve_type=3, named_curve=None, pointlen=None, point=None)[source]

Bases: _GenericTLSSessionInheritance

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerECDHNamedCurveParams'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<ByteEnumField (ServerECDHNamedCurveParams).curve_type>, <ShortEnumField (ServerECDHNamedCurveParams).named_curve>, <FieldLenField (ServerECDHNamedCurveParams).pointlen>, <StrLenField (ServerECDHNamedCurveParams).point>]
fill_missing(**kwargs: Any) Any[source]
guess_payload_class(p)[source]
post_dissection(r)[source]
register_pubkey(**kwargs: Any) Any[source]
class scapy.layers.tls.keyexchange.ServerPSKParams(_pkt, /, *, psk_identity_hint_len=None, psk_identity_hint=b'')[source]

Bases: Packet

XXX We provide some parsing abilities for ServerPSKParams, but the context operations have not been implemented yet. See RFC 4279. Note that we do not cover the (EC)DHE_PSK key exchange, which should contain a Server*DHParams after ‘psk_identity_hint’.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerPSKParams'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ServerPSKParams).psk_identity_hint_len>, <StrLenField (ServerPSKParams).psk_identity_hint>]
fill_missing()[source]
guess_payload_class(p)[source]
post_dissection(pkt)[source]
class scapy.layers.tls.keyexchange.ServerRSAParams(_pkt, /, *, rsamodlen=None, rsamod=b'', rsaexplen=None, rsaexp=b'')[source]

Bases: _GenericTLSSessionInheritance

Defined for RSA_EXPORT kx : it enables servers to share RSA keys shorter than their principal {>512}-bit key, when it is not allowed for kx.

This should not appear in standard RSA kx negotiation, as the key has already been advertised in the Certificate message.

aliastypes = [<class 'scapy.layers.tls.keyexchange.ServerRSAParams'>, <class 'scapy.layers.tls.session._GenericTLSSessionInheritance'>, <class 'scapy.packet.Packet'>]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<FieldLenField (ServerRSAParams).rsamodlen>, <StrLenField (ServerRSAParams).rsamod>, <FieldLenField (ServerRSAParams).rsaexplen>, <StrLenField (ServerRSAParams).rsaexp>]
fill_missing(**kwargs: Any) Any[source]
guess_payload_class(p)[source]
post_dissection(pkt)[source]
register_pubkey(**kwargs: Any) Any[source]
class scapy.layers.tls.keyexchange.SigAndHashAlgField(name: str, default: I | None, enum: Dict[I, str] | Dict[str, I] | List[str] | DADict[I, str] | Type[Enum] | Tuple[Callable[[I], str], Callable[[str], I]], fmt: str = 'H')[source]

Bases: EnumField

Used in _TLSSignature.

addfield()[source]
getfield()[source]
phantom_value = None
class scapy.layers.tls.keyexchange.SigAndHashAlgsField(name: str, default: List[AnyField] | None, field: AnyField, length_from: Callable[[Packet], int] | None = None, count_from: Callable[[Packet], int] | None = None, max_count: int | None = None)[source]

Bases: FieldListField

Used in TLS_Ext_SignatureAlgorithms and TLSCertificateResquest.

addfield()[source]
getfield()[source]
phantom_value = []
class scapy.layers.tls.keyexchange.SigAndHashAlgsLenField(name: str, default: Optional[Any], length_of: Optional[str] = None, fmt: str = 'H', count_of: Optional[str] = None, adjust: Callable[[Packet, int], int] = <function FieldLenField.<lambda>>)[source]

Bases: FieldLenField

Used in TLS_Ext_SignatureAlgorithms and TLSCertificateResquest.

addfield()[source]
getfield()[source]
phantom_value = 0
class scapy.layers.tls.keyexchange.SigLenField(name: str, default: Optional[Any], length_of: Optional[str] = None, fmt: str = 'H', count_of: Optional[str] = None, adjust: Callable[[Packet, int], int] = <function FieldLenField.<lambda>>)[source]

Bases: FieldLenField

There is a trick for SSLv2, which uses implicit lengths…

addfield(pkt, s, val)[source]

With SSLv2 you will never be able to add a sig_len.

getfield(pkt, s)[source]
class scapy.layers.tls.keyexchange.SigValField(name: str, default: bytes, length_from: Callable[[Packet], int] | None = None, max_length: Any | None = None)[source]

Bases: StrLenField

There is a trick for SSLv2, which uses implicit lengths…

getfield(pkt, m)[source]
scapy.layers.tls.keyexchange.phantom_decorate(f, get_or_add)[source]

Decorator for version-dependent fields. If get_or_add is True (means get), we return s, self.phantom_value. If it is False (means add), we return s.

scapy.layers.tls.keyexchange.phantom_mode(pkt)[source]

We expect this. If tls_version is not set, this means we did not process any complete ClientHello, so we’re most probably reading/building a signature_algorithms extension, hence we cannot be in phantom_mode. However, if the tls_version has been set, we test for TLS 1.2.