示例#1
0
        def test_structmeta(self):

            OpaqueUint8 = Opaque(size_t=Uint8)
            ListUint8OpaqueUint8 = List(size_t=Uint8,
                                        elem_t=Opaque(size_t=Uint8))

            @struct
            class Sample1(StructMeta):
                fieldA: Uint16
                fieldB: OpaqueUint8
                fieldC: ListUint8OpaqueUint8

            s = Sample1(fieldA=Uint16(0x1),
                        fieldB=OpaqueUint8(b'\xff'),
                        fieldC=ListUint8OpaqueUint8(
                            [OpaqueUint8(b'\xaa'),
                             OpaqueUint8(b'\xbb')]))

            self.assertTrue(hasattr(s, 'fieldA'))
            self.assertTrue(isinstance(s.fieldA, Uint16))
            self.assertTrue(hasattr(s, 'fieldB'))
            self.assertTrue(isinstance(s.fieldB, OpaqueUint8))
            self.assertTrue(hasattr(s, 'fieldC'))
            self.assertTrue(isinstance(s.fieldC, ListUint8OpaqueUint8))

            self.assertEqual(bytes(s), b'\x00\x01\x01\xff\x04\x01\xaa\x01\xbb')
            self.assertEqual(Sample1.from_bytes(bytes(s)), s)
示例#2
0
        def test_structmeta_keep_rest_bytes(self):
            import io

            OpaqueUint8 = Opaque(size_t=Uint8)
            ListUint8OpaqueUint8 = List(size_t=Uint8,
                                        elem_t=Opaque(size_t=Uint8))

            @struct
            class Sample1(StructMeta):
                fieldA: Uint16
                fieldB: OpaqueUint8
                fieldC: ListUint8OpaqueUint8

            s = Sample1(fieldA=Uint16(0x1),
                        fieldB=OpaqueUint8(b'\xff'),
                        fieldC=ListUint8OpaqueUint8(
                            [OpaqueUint8(b'\xaa'),
                             OpaqueUint8(b'\xbb')]))

            deadbeef = bytes.fromhex('deadbeef')
            fs = io.BytesIO(bytes(s) + deadbeef)

            s2 = Sample1.from_fs(fs)

            rest = fs.read()
            self.assertEqual(rest, deadbeef)
示例#3
0
        def test_structmeta_has_parent_ref(self):
            @struct
            class Sample1(StructMeta):
                child_field: Select('Sample3.parent_fieldA',
                                    cases={
                                        Uint8(0xaa): Uint8,
                                        Uint8(0xbb): Uint16,
                                    })

            @struct
            class Sample2(StructMeta):
                parent_fieldB: Uint8
                fragment: Sample1

            Sample2s = List(size_t=Uint8, elem_t=Sample2)

            @struct
            class Sample3(StructMeta):
                parent_fieldA: Uint8
                fragment: Sample2s

            s = Sample3(parent_fieldA=Uint8(0xbb),
                        fragment=Sample2s([
                            Sample2(
                                parent_fieldB=Uint8(0x12),
                                fragment=Sample1(child_field=Uint16(0x0101)))
                        ]))

            # コンストラクタで構造体を構築した場合
            target = s.fragment.get_array()[0].fragment  # 最下の子インスタンス
            self.assertTrue(isinstance(target, Sample1))
            self.assertTrue(isinstance(target.parent, Sample2))
            self.assertTrue(isinstance(target.parent.parent, Sample3))

            # バイト列から構造体を構築した場合
            s2 = Sample3.from_bytes(bytes(s))
            target = s.fragment.get_array()[0].fragment  # 最下の子インスタンス
            self.assertTrue(isinstance(target, Sample1))
            self.assertTrue(isinstance(target.parent, Sample2))
            self.assertTrue(isinstance(target.parent.parent, Sample3))
示例#4
0
    TLS_AES_128_CCM_8_SHA256 = Uint16(0x1305)
    TLS_EMPTY_RENEGOTIATION_INFO_SCSV = Uint16(0x00FF)

    @classmethod
    def get_cipher_class(cls, cipher_suite):
        ciphercuite2class = {
            CipherSuite.TLS_AES_128_GCM_SHA256: None,
            CipherSuite.TLS_AES_256_GCM_SHA384: None,
            CipherSuite.TLS_CHACHA20_POLY1305_SHA256: Chacha20Poly1305,
            CipherSuite.TLS_AES_128_CCM_SHA256: None,
            CipherSuite.TLS_AES_128_CCM_8_SHA256: None,
        }
        return ciphercuite2class.get(cipher_suite)

    @classmethod
    def get_hash_name(cls, cipher_suite):
        if cipher_suite == CipherSuite.TLS_AES_256_GCM_SHA384:
            return 'sha384'
        else:
            return 'sha256'

    @classmethod
    def get_hash_size(cls, cipher_suite):
        if cipher_suite == CipherSuite.TLS_AES_256_GCM_SHA384:
            return 48
        else:
            return 32


CipherSuites = List(size_t=Uint16, elem_t=CipherSuite)
示例#5
0
from type import Uint8, Uint16, List, Enum
import structmeta as meta

from protocol_types import HandshakeType

class ProtocolVersion(Enum):
    elem_t = Uint16

    SSL3  = Uint16(0x0300)
    TLS10 = Uint16(0x0301)
    TLS11 = Uint16(0x0302)
    TLS12 = Uint16(0x0303)
    TLS13 = Uint16(0x0304)

ProtocolVersions = List(size_t=Uint8, elem_t=ProtocolVersion)

@meta.struct
class SupportedVersions(meta.StructMeta):
    versions: meta.Select('Handshake.msg_type', cases={
        HandshakeType.client_hello: ProtocolVersions,
        HandshakeType.server_hello: ProtocolVersion,
    })


# ------------------------------------------------------------------------------
if __name__ == '__main__':

    from protocol_handshake import Handshake

    import unittest
    # Finite Field Groups (DHE)
    # https://tools.ietf.org/html/rfc7919#appendix-A
    ffdhe2048 = Uint16(0x0100)
    ffdhe3072 = Uint16(0x0101)
    ffdhe4096 = Uint16(0x0102)
    ffdhe6144 = Uint16(0x0103)
    ffdhe8192 = Uint16(0x0104)

    # Reserved Code Points
    #ffdhe_private_use = Uint16(0x01FC)..Uint16(0x01FF)
    #ecdhe_private_use = Uint16(0xFE00)..Uint16(0xFEFF)
    #obsolete_RESERVED = Uint16(0xFF01)..Uint16(0xFF02)


NamedGroups = List(size_t=Uint16, elem_t=NamedGroup)


@meta.struct
class NamedGroupList(meta.StructMeta):
    named_group_list: NamedGroups


if __name__ == '__main__':

    import unittest

    class TestUnit(unittest.TestCase):
        def test_namedgrouplist(self):

            ngl = NamedGroupList(named_group_list=NamedGroups([
示例#7
0
    ecdsa_secp512r1_sha512 = Uint16(0x0603)

    # RSASSA-PSS algorithms with public key OID rsaEncryption
    rsa_pss_rsae_sha256 = Uint16(0x0804)
    rsa_pss_rsae_sha384 = Uint16(0x0805)
    rsa_pss_rsae_sha512 = Uint16(0x0806)

    # EdDSA algorithms
    ed25519 = Uint16(0x0807)
    ed448 = Uint16(0x0808)

    # RSASSA-PSS algorithms with public key OID RSASSA-PSS
    rsa_pss_pss_sha256 = Uint16(0x0809)
    rsa_pss_pss_sha384 = Uint16(0x080a)
    rsa_pss_pss_sha512 = Uint16(0x080b)

    # Legacy algorithms
    rsa_pkcs1_sha1 = Uint16(0x0201)
    ecdsa_sha1 = Uint16(0x0203)

    # Reserved Code Points
    #private_use = Uint16(0xFE00)..Uint16(0xFFFF)


SignatureSchemes = List(size_t=Uint16, elem_t=SignatureScheme)


@meta.struct
class SignatureSchemeList(meta.StructMeta):
    supported_signature_algorithms: SignatureSchemes
示例#8
0
from protocol_ext_signature import SignatureScheme

# --- Certificate --------------------------------------------------------------

class CertificateType(Enum):
    elem_t = Uint8

    X509 = Uint8(0)
    RawPublicKey = Uint8(2)

@meta.struct
class CertificateEntry(meta.StructMeta):
    cert_data: OpaqueUint24
    extensions: Extensions

CertificateEntrys = List(size_t=Uint24, elem_t=CertificateEntry)

@meta.struct
class Certificate(meta.StructMeta):
    certificate_request_context: OpaqueUint8
    certificate_list: CertificateEntrys

@meta.struct
class CertificateVerify(meta.StructMeta):
    algorithm: SignatureScheme
    signature: OpaqueUint16

# --- Finished -----------------------------------------------------------------

class Hash:
    length = None
示例#9
0
    extension_type: ExtensionType
    length: Uint16 = lambda self: Uint16(len(bytes(self.extension_data)))
    extension_data: meta.Select('extension_type',
                                cases={
                                    ExtensionType.supported_versions:
                                    SupportedVersions,
                                    ExtensionType.supported_groups:
                                    NamedGroupList,
                                    ExtensionType.key_share: KeyShareHello,
                                    ExtensionType.signature_algorithms:
                                    SignatureSchemeList,
                                    meta.Otherwise: OpaqueLength,
                                })


Extensions = List(size_t=Uint16, elem_t=Extension)

# ------------------------------------------------------------------------------
# Server Parameters


@meta.struct
class EncryptedExtensions(meta.StructMeta):
    extensions: Extensions


# ------------------------------------------------------------------------------
if __name__ == '__main__':

    from protocol_ext_supportedgroups import NamedGroups, NamedGroup
示例#10
0
from type import Uint16, OpaqueUint16, List
import structmeta as meta

from protocol_types import HandshakeType
from protocol_ext_supportedgroups import NamedGroup


@meta.struct
class KeyShareEntry(meta.StructMeta):
    group: NamedGroup
    key_exchange: OpaqueUint16


KeyShareEntrys = List(size_t=Uint16, elem_t=KeyShareEntry)


@meta.struct
class KeyShareHello(meta.StructMeta):
    shares: meta.Select('Handshake.msg_type',
                        cases={
                            HandshakeType.client_hello: KeyShareEntrys,
                            HandshakeType.server_hello: KeyShareEntry,
                        })


# ------------------------------------------------------------------------------
if __name__ == '__main__':
    import unittest

    class TestUnit(unittest.TestCase):
        def test_keyshare_clienthello(self):