#!/usr/bin/env python3
# coding=utf-8

#
#   Copyright (c) 2020 Project CHIP Authors
#   Copyright (c) 2019-2020 Google LLC.
#   All rights reserved.
#
#   Licensed under the Apache License, Version 2.0 (the "License");
#   you may not use this file except in compliance with the License.
#   You may obtain a copy of the License at
#
#       http://www.apache.org/licenses/LICENSE-2.0
#
#   Unless required by applicable law or agreed to in writing, software
#   distributed under the License is distributed on an "AS IS" BASIS,
#   WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
#   See the License for the specific language governing permissions and
#   limitations under the License.
#

#
#   @file
#         This file contains definitions for working with data encoded in Chip TLV format
#


from __future__ import absolute_import, print_function

import struct
from collections import OrderedDict
from collections.abc import Mapping, Sequence
from enum import Enum

from .tlvlist import TLVList

TLV_TYPE_SIGNED_INTEGER = 0x00
TLV_TYPE_UNSIGNED_INTEGER = 0x04
TLV_TYPE_BOOLEAN = 0x08
TLV_TYPE_FLOATING_POINT_NUMBER = 0x0A
TLV_TYPE_UTF8_STRING = 0x0C
TLV_TYPE_BYTE_STRING = 0x10
TLV_TYPE_NULL = 0x14
TLV_TYPE_STRUCTURE = 0x15
TLV_TYPE_ARRAY = 0x16
TLV_TYPE_PATH = 0x17

TLV_TAG_CONTROL_ANONYMOUS = 0x00
TLV_TAG_CONTROL_CONTEXT_SPECIFIC = 0x20
TLV_TAG_CONTROL_COMMON_PROFILE_2Bytes = 0x40
TLV_TAG_CONTROL_COMMON_PROFILE_4Bytes = 0x60
TLV_TAG_CONTROL_IMPLICIT_PROFILE_2Bytes = 0x80
TLV_TAG_CONTROL_IMPLICIT_PROFILE_4Bytes = 0xA0
TLV_TAG_CONTROL_FULLY_QUALIFIED_6Bytes = 0xC0
TLV_TAG_CONTROL_FULLY_QUALIFIED_8Bytes = 0xE0

TLVBoolean_False = TLV_TYPE_BOOLEAN
TLVBoolean_True = TLV_TYPE_BOOLEAN + 1

TLVEndOfContainer = 0x18

INT8_MIN = -128
INT16_MIN = -32768
INT32_MIN = -2147483648
INT64_MIN = -9223372036854775808

INT8_MAX = 127
INT16_MAX = 32767
INT32_MAX = 2147483647
INT64_MAX = 9223372036854775807

UINT8_MAX = 255
UINT16_MAX = 65535
UINT32_MAX = 4294967295
UINT64_MAX = 18446744073709551615

ElementTypes = {
    0x00: "Signed Integer 1-byte value",
    0x01: "Signed Integer 2-byte value",
    0x02: "Signed Integer 4-byte value",
    0x03: "Signed Integer 8-byte value",
    0x04: "Unsigned Integer 1-byte value",
    0x05: "Unsigned Integer 2-byte value",
    0x06: "Unsigned Integer 4-byte value",
    0x07: "Unsigned Integer 8-byte value",
    0x08: "Boolean False",
    0x09: "Boolean True",
    0x0A: "Floating Point 4-byte value",
    0x0B: "Floating Point 8-byte value",
    0x0C: "UTF-8 String 1-byte length",
    0x0D: "UTF-8 String 2-byte length",
    0x0E: "UTF-8 String 4-byte length",
    0x0F: "UTF-8 String 8-byte length",
    0x10: "Byte String 1-byte length",
    0x11: "Byte String 2-byte length",
    0x12: "Byte String 4-byte length",
    0x13: "Byte String 8-byte length",
    0x14: "Null",
    0x15: "Structure",
    0x16: "Array",
    0x17: "Path",
    0x18: "End of Collection",
}

TagControls = {
    0x00: "Anonymous",
    0x20: "Context 1-byte",
    0x40: "Common Profile 2-byte",
    0x60: "Common Profile 4-byte",
    0x80: "Implicit Profile 2-byte",
    0xA0: "Implicit Profile 4-byte",
    0xC0: "Fully Qualified 6-byte",
    0xE0: "Fully Qualified 8-byte",
}


class uint(int):
    '''
    NewType will not return a class until Python 3.10, as Python 3.10 is not widely used,
    we still need to construct a class so it can work as a type.
    '''

    def __init__(self, val: int):
        if (val < 0):
            raise TypeError(
                'expecting positive value, got negative value of %d instead' % val)


class float32(float):
    ''' A type for single precision floats distinct from the double precision 'float'
        type offered by default in Python. This type distinction is present in the Matter
        data model types so we need it here as well.

        It is backed by an ordinary float, which means there will be precision loss at the time
        the value is converted to TLV.
    '''
    pass


class TLVWriter(object):
    def __init__(self, encoding=None, implicitProfile=None):
        self._encoding = encoding if encoding is not None else bytearray()
        self._implicitProfile = implicitProfile
        self._containerStack = []

    @property
    def encoding(self):
        """The object into which encoded TLV data is written.

        By default this is a bytearray object.
        """
        return self._encoding

    @encoding.setter
    def encoding(self, val):
        self._encoding = val

    @property
    def implicitProfile(self):
        """The Chip profile id used when encoding implicit profile tags.

        Setting this value will result in an implicit profile tag being encoded
        whenever the profile of the tag to be encoded matches the specified implicit
        profile id.

        Setting this value to None (the default) disabled encoding of implicit
        profile tags.
        """
        return self._implicitProfile

    @implicitProfile.setter
    def implicitProfile(self, val):
        self._implicitProfile = val

    def put(self, tag, val):
        """Write a value in TLV format with the specified TLV tag.

        val can be a Python object which will be encoded as follows:
        - Python bools, floats and strings are encoded as their respective TLV types.
        - Python ints are encoded as unsigned TLV integers if zero or positive; signed TLV
          integers if negative.
        - None is encoded as a TLV Null.
        - bytes and bytearray objects are encoded as TVL byte strings.
        - Mapping-like objects (e.g. dict) are encoded as TLV structures.  The keys of the
          map object are expected to be tag values, as described below for the tag argument.
          Map values are encoded recursively, using the same rules as defined for the val
          argument. The encoding order of elements depends on the type of the map object.
          Elements within a dict are automatically encoded tag numerical order. Elements
          within other forms of mapping object (e.g. OrderedDict) are encoded in the
          object's natural iteration order.
        - Sequence-like objects (e.g. arrays) are written as TLV arrays. Elements within
          the array are encoded recursively, using the same rules as defined for the val
          argument.

        tag can be a small int (0-255), a tuple of two integers, or None.
        If tag is an integer, it is encoded as a TLV context-specific tag.
        If tag is a two-integer tuple, it is encoded as a TLV profile-specific tag, with
          the first integer encoded as the profile id and the second as the tag number.
        If tag is None, it is encoded as a TLV anonymous tag.
        """
        if val is None:
            self.putNull(tag)
        elif isinstance(val, Enum):
            self.putUnsignedInt(tag, val)
        elif isinstance(val, bool):
            self.putBool(tag, val)
        elif isinstance(val, uint):
            self.putUnsignedInt(tag, val)
        elif isinstance(val, int):
            self.putSignedInt(tag, val)
        elif isinstance(val, float32):
            self.putFloat(tag, val)
        elif isinstance(val, float):
            self.putDouble(tag, val)
        elif isinstance(val, str):
            self.putString(tag, val)
        elif isinstance(val, bytes) or isinstance(val, bytearray):
            self.putBytes(tag, val)
        elif isinstance(val, Mapping):
            self.startStructure(tag)
            if type(val) is dict:
                val = OrderedDict(
                    sorted(val.items(),
                           key=lambda item: tlvTagToSortKey(item[0]))
                )
            for containedTag, containedVal in val.items():
                self.put(containedTag, containedVal)
            self.endContainer()
        elif isinstance(val, TLVList):
            self.startPath(tag)
            for containedTag, containedVal in val:
                self.put(containedTag, containedVal)
            self.endContainer()
        elif isinstance(val, Sequence):
            self.startArray(tag)
            for containedVal in val:
                self.put(None, containedVal)
            self.endContainer()
        else:
            raise ValueError("Attempt to TLV encode unsupported value")

    def putSignedInt(self, tag, val):
        """Write a value as a TLV signed integer with the specified TLV tag."""
        if val >= INT8_MIN and val <= INT8_MAX:
            format = "<b"
        elif val >= INT16_MIN and val <= INT16_MAX:
            format = "<h"
        elif val >= INT32_MIN and val <= INT32_MAX:
            format = "<l"
        elif val >= INT64_MIN and val <= INT64_MAX:
            format = "<q"
        else:
            raise ValueError("Integer value out of range")
        val = struct.pack(format, val)
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_SIGNED_INTEGER, tag, lenOfLenOrVal=len(val)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(val)

    def putUnsignedInt(self, tag, val):
        """Write a value as a TLV unsigned integer with the specified TLV tag."""
        val = self._encodeUnsignedInt(val)
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_UNSIGNED_INTEGER, tag, lenOfLenOrVal=len(val)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(val)

    def putFloat(self, tag, val):
        """Write a value as a TLV float with the specified TLV tag."""
        val = struct.pack("f", val)
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_FLOATING_POINT_NUMBER, tag, lenOfLenOrVal=len(val)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(val)

    def putDouble(self, tag, val):
        """Write a value as a TLV double with the specified TLV tag."""
        val = struct.pack("d", val)
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_FLOATING_POINT_NUMBER, tag, lenOfLenOrVal=len(val)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(val)

    def putString(self, tag, val):
        """Write a value as a TLV string with the specified TLV tag."""
        val = val.encode("utf-8")
        valLen = self._encodeUnsignedInt(len(val))
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_UTF8_STRING, tag, lenOfLenOrVal=len(valLen)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(valLen)
        self._encoding.extend(val)

    def putBytes(self, tag, val):
        """Write a value as a TLV byte string with the specified TLV tag."""
        valLen = self._encodeUnsignedInt(len(val))
        controlAndTag = self._encodeControlAndTag(
            TLV_TYPE_BYTE_STRING, tag, lenOfLenOrVal=len(valLen)
        )
        self._encoding.extend(controlAndTag)
        self._encoding.extend(valLen)
        self._encoding.extend(val)

    def putBool(self, tag, val):
        """Write a value as a TLV boolean with the specified TLV tag."""
        if val:
            type = TLVBoolean_True
        else:
            type = TLVBoolean_False
        controlAndTag = self._encodeControlAndTag(type, tag)
        self._encoding.extend(controlAndTag)

    def putNull(self, tag):
        """Write a TLV null with the specified TLV tag."""
        controlAndTag = self._encodeControlAndTag(TLV_TYPE_NULL, tag)
        self._encoding.extend(controlAndTag)

    def startContainer(self, tag, containerType):
        """Start writing a TLV container with the specified TLV tag.

        containerType can be one of TLV_TYPE_STRUCTURE, TLV_TYPE_ARRAY or
        TLV_TYPE_PATH.
        """
        self._verifyValidContainerType(containerType)
        controlAndTag = self._encodeControlAndTag(containerType, tag)
        self._encoding.extend(controlAndTag)
        self._containerStack.insert(0, containerType)

    def startStructure(self, tag):
        """Start writing a TLV structure with the specified TLV tag."""
        self.startContainer(tag, containerType=TLV_TYPE_STRUCTURE)

    def startArray(self, tag):
        """Start writing a TLV array with the specified TLV tag."""
        self.startContainer(tag, containerType=TLV_TYPE_ARRAY)

    def startPath(self, tag):
        """Start writing a TLV path with the specified TLV tag."""
        self.startContainer(tag, containerType=TLV_TYPE_PATH)

    def endContainer(self):
        """End writing the current TLV container."""
        self._containerStack.pop(0)
        controlAndTag = self._encodeControlAndTag(TLVEndOfContainer, None)
        self._encoding.extend(controlAndTag)

    def _encodeControlAndTag(self, type, tag, lenOfLenOrVal=0):
        controlByte = type
        if lenOfLenOrVal == 2:
            controlByte |= 1
        elif lenOfLenOrVal == 4:
            controlByte |= 2
        elif lenOfLenOrVal == 8:
            controlByte |= 3
        if tag is None:
            if (
                type != TLVEndOfContainer
                and len(self._containerStack) != 0
                and self._containerStack[0] == TLV_TYPE_STRUCTURE
            ):
                raise ValueError(
                    "Attempt to encode anonymous tag within TLV structure")
            controlByte |= TLV_TAG_CONTROL_ANONYMOUS
            return struct.pack("<B", controlByte)
        if isinstance(tag, int):
            if tag < 0 or tag > UINT8_MAX:
                raise ValueError(
                    "Context-specific TLV tag number out of range")
            if len(self._containerStack) == 0:
                raise ValueError(
                    "Attempt to encode context-specific TLV tag at top level"
                )
            if self._containerStack[0] == TLV_TYPE_ARRAY:
                raise ValueError(
                    "Attempt to encode context-specific tag within TLV array"
                )
            controlByte |= TLV_TAG_CONTROL_CONTEXT_SPECIFIC
            return struct.pack("<BB", controlByte, tag)
        if isinstance(tag, tuple):
            (profile, tagNum) = tag
            if not isinstance(tagNum, int):
                raise ValueError("Invalid object given for TLV tag")
            if tagNum < 0 or tagNum > UINT32_MAX:
                raise ValueError("TLV tag number out of range")
            if profile is not None:
                if not isinstance(profile, int):
                    raise ValueError("Invalid object given for TLV profile id")
                if profile < 0 or profile > UINT32_MAX:
                    raise ValueError("TLV profile id value out of range")
            if (
                len(self._containerStack) != 0
                and self._containerStack[0] == TLV_TYPE_ARRAY
            ):
                raise ValueError(
                    "Attempt to encode profile-specific tag within TLV array"
                )
            if profile is None or profile == self._implicitProfile:
                if tagNum <= UINT16_MAX:
                    controlByte |= TLV_TAG_CONTROL_IMPLICIT_PROFILE_2Bytes
                    return struct.pack("<BH", controlByte, tagNum)
                else:
                    controlByte |= TLV_TAG_CONTROL_IMPLICIT_PROFILE_4Bytes
                    return struct.pack("<BL", controlByte, tagNum)
            elif profile == 0:
                if tagNum <= UINT16_MAX:
                    controlByte |= TLV_TAG_CONTROL_COMMON_PROFILE_2Bytes
                    return struct.pack("<BH", controlByte, tagNum)
                else:
                    controlByte |= TLV_TAG_CONTROL_COMMON_PROFILE_4Bytes
                    return struct.pack("<BL", controlByte, tagNum)
            else:
                vendorId = (profile >> 16) & 0xFFFF
                profileNum = (profile >> 0) & 0xFFFF
                if tagNum <= UINT16_MAX:
                    controlByte |= TLV_TAG_CONTROL_FULLY_QUALIFIED_6Bytes
                    return struct.pack("<BHHH", controlByte, vendorId, profileNum, tagNum)
                else:
                    controlByte |= TLV_TAG_CONTROL_FULLY_QUALIFIED_8Bytes
                    return struct.pack("<BHHL", controlByte, vendorId, profileNum, profile, tagNum)
        raise ValueError("Invalid object given for TLV tag")

    @staticmethod
    def _encodeUnsignedInt(val):
        if val < 0:
            raise ValueError("Integer value out of range")
        if val <= UINT8_MAX:
            format = "<B"
        elif val <= UINT16_MAX:
            format = "<H"
        elif val <= UINT32_MAX:
            format = "<L"
        elif val <= UINT64_MAX:
            format = "<Q"
        else:
            raise ValueError("Integer value out of range")
        return struct.pack(format, val)

    @staticmethod
    def _verifyValidContainerType(containerType):
        if (
            containerType != TLV_TYPE_STRUCTURE
            and containerType != TLV_TYPE_ARRAY
            and containerType != TLV_TYPE_PATH
        ):
            raise ValueError("Invalid TLV container type")


class TLVReader(object):
    def __init__(self, tlv):
        self._tlv = tlv
        self._bytesRead = 0
        self._decodings = []

    @property
    def decoding(self):
        return self._decodings

    def get(self):
        """Get the dictionary representation of tlv data"""
        out = {}
        self._get(self._tlv, self._decodings, out)
        return out

    def _decodeControlByte(self, tlv, decoding):
        (controlByte,) = struct.unpack(
            "<B", tlv[self._bytesRead: self._bytesRead + 1])
        controlTypeIndex = controlByte & 0xE0
        decoding["tagControl"] = TagControls[controlTypeIndex]
        elementtypeIndex = controlByte & 0x1F
        decoding["type"] = ElementTypes[elementtypeIndex]
        self._bytesRead += 1

    def _decodeControlAndTag(self, tlv, decoding):
        """The control byte specifies the type of a TLV element and how its tag, length and value fields are encoded.
        The control byte consists of two subfields: an element type field which occupies the lower 5 bits,
        and a tag control field which occupies the upper 3 bits. The element type field encodes the element’s type
        as well as how the corresponding length and value fields are encoded.  In the case of Booleans and the
        null value, the element type field also encodes the value itself."""

        self._decodeControlByte(tlv, decoding)

        if decoding["tagControl"] == "Anonymous":
            decoding["tag"] = None
            decoding["tagLen"] = 0
        elif decoding["tagControl"] == "Context 1-byte":
            (decoding["tag"],) = struct.unpack(
                "<B", tlv[self._bytesRead: self._bytesRead + 1]
            )
            decoding["tagLen"] = 1
            self._bytesRead += 1
        elif decoding["tagControl"] == "Common Profile 2-byte":
            profile = 0
            (tag,) = struct.unpack(
                "<H", tlv[self._bytesRead: self._bytesRead + 2])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 2
            self._bytesRead += 2
        elif decoding["tagControl"] == "Common Profile 4-byte":
            profile = 0
            (tag,) = struct.unpack(
                "<L", tlv[self._bytesRead: self._bytesRead + 4])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 4
            self._bytesRead += 4
        elif decoding["tagControl"] == "Implicit Profile 2-byte":
            profile = None
            (tag,) = struct.unpack(
                "<H", tlv[self._bytesRead: self._bytesRead + 2])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 2
            self._bytesRead += 2
        elif decoding["tagControl"] == "Implicit Profile 4-byte":
            profile = None
            (tag,) = struct.unpack(
                "<L", tlv[self._bytesRead: self._bytesRead + 4])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 4
            self._bytesRead += 4
        elif decoding["tagControl"] == "Fully Qualified 6-byte":
            (vendorId, profileNum) = struct.unpack(
                "<HH", tlv[self._bytesRead: self._bytesRead + 4])
            profile = (vendorId << 16) | profileNum
            (tag,) = struct.unpack(
                "<H", tlv[self._bytesRead + 4: self._bytesRead + 6])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 2
            self._bytesRead += 6
        elif decoding["tagControl"] == "Fully Qualified 8-byte":
            (vendorId, profileNum) = struct.unpack(
                "<HH", tlv[self._bytesRead: self._bytesRead + 4])
            profile = (vendorId << 16) | profileNum
            (tag,) = struct.unpack(
                "<L", tlv[self._bytesRead + 4: self._bytesRead + 8])
            decoding["profileTag"] = (profile, tag)
            decoding["tagLen"] = 4
            self._bytesRead += 8

    def _decodeStrLength(self, tlv, decoding):
        """UTF-8 or Byte StringLength fields are encoded in 0, 1, 2 or 4 byte widths, as specified by
        the element type field. If the element type needs a length field grab the next bytes as length"""
        if "length" in decoding["type"]:
            if "1-byte" in decoding["type"]:
                (decoding["strDataLen"],) = struct.unpack(
                    "<B", tlv[self._bytesRead: self._bytesRead + 1]
                )
                decoding["strDataLenLen"] = 1
                self._bytesRead += 1
            elif "2-byte" in decoding["type"]:
                (decoding["strDataLen"],) = struct.unpack(
                    "<H", tlv[self._bytesRead: self._bytesRead + 2]
                )
                decoding["strDataLenLen"] = 2
                self._bytesRead += 2
            elif "4-byte" in decoding["type"]:
                (decoding["strDataLen"],) = struct.unpack(
                    "<L", tlv[self._bytesRead: self._bytesRead + 4]
                )
                decoding["strDataLenLen"] = 4
                self._bytesRead += 4
            elif "8-byte" in decoding["type"]:
                (decoding["strDataLen"],) = struct.unpack(
                    "<Q", tlv[self._bytesRead: self._bytesRead + 8]
                )
                decoding["strDataLenLen"] = 8
                self._bytesRead += 8
        else:
            decoding["strDataLen"] = 0
            decoding["strDataLenLen"] = 0

    def _decodeVal(self, tlv, decoding):
        """decode primitive tlv value to the corresponding python value, tlv array and path are decoded as
        python list, tlv structure is decoded as python dictionary"""
        if decoding["type"] == "Structure":
            decoding["value"] = {}
            decoding["Structure"] = []
            self._get(tlv, decoding["Structure"], decoding["value"])
        elif decoding["type"] == "Array":
            decoding["value"] = []
            decoding["Array"] = []
            self._get(tlv, decoding["Array"], decoding["value"])
        elif decoding["type"] == "Path":
            decoding["value"] = TLVList()
            decoding["Path"] = []
            self._get(tlv, decoding["Path"], decoding["value"])
        elif decoding["type"] == "Null":
            decoding["value"] = None
        elif decoding["type"] == "End of Collection":
            decoding["value"] = None
        elif decoding["type"] == "Boolean True":
            decoding["value"] = True
        elif decoding["type"] == "Boolean False":
            decoding["value"] = False
        elif decoding["type"] == "Unsigned Integer 1-byte value":
            (decoding["value"],) = struct.unpack(
                "<B", tlv[self._bytesRead: self._bytesRead + 1]
            )
            decoding["value"] = uint(decoding["value"])
            self._bytesRead += 1
        elif decoding["type"] == "Signed Integer 1-byte value":
            (decoding["value"],) = struct.unpack(
                "<b", tlv[self._bytesRead: self._bytesRead + 1]
            )
            self._bytesRead += 1
        elif decoding["type"] == "Unsigned Integer 2-byte value":
            (decoding["value"],) = struct.unpack(
                "<H", tlv[self._bytesRead: self._bytesRead + 2]
            )
            decoding["value"] = uint(decoding["value"])
            self._bytesRead += 2
        elif decoding["type"] == "Signed Integer 2-byte value":
            (decoding["value"],) = struct.unpack(
                "<h", tlv[self._bytesRead: self._bytesRead + 2]
            )
            self._bytesRead += 2
        elif decoding["type"] == "Unsigned Integer 4-byte value":
            (decoding["value"],) = struct.unpack(
                "<L", tlv[self._bytesRead: self._bytesRead + 4]
            )
            decoding["value"] = uint(decoding["value"])
            self._bytesRead += 4
        elif decoding["type"] == "Signed Integer 4-byte value":
            (decoding["value"],) = struct.unpack(
                "<l", tlv[self._bytesRead: self._bytesRead + 4]
            )
            self._bytesRead += 4
        elif decoding["type"] == "Unsigned Integer 8-byte value":
            (decoding["value"],) = struct.unpack(
                "<Q", tlv[self._bytesRead: self._bytesRead + 8]
            )
            decoding["value"] = uint(decoding["value"])
            self._bytesRead += 8
        elif decoding["type"] == "Signed Integer 8-byte value":
            (decoding["value"],) = struct.unpack(
                "<q", tlv[self._bytesRead: self._bytesRead + 8]
            )
            self._bytesRead += 8
        elif decoding["type"] == "Floating Point 4-byte value":
            (decoding["value"],) = struct.unpack(
                "<f", tlv[self._bytesRead: self._bytesRead + 4]
            )
            decoding["value"] = float32(decoding["value"])
            self._bytesRead += 4
        elif decoding["type"] == "Floating Point 8-byte value":
            (decoding["value"],) = struct.unpack(
                "<d", tlv[self._bytesRead: self._bytesRead + 8]
            )
            self._bytesRead += 8
        elif "UTF-8 String" in decoding["type"]:
            (val,) = struct.unpack(
                "<%ds" % decoding["strDataLen"],
                tlv[self._bytesRead: self._bytesRead + decoding["strDataLen"]],
            )
            try:
                decoding["value"] = str(val, "utf-8")
            except Exception:
                decoding["value"] = val
            self._bytesRead += decoding["strDataLen"]
        elif "Byte String" in decoding["type"]:
            (val,) = struct.unpack(
                "<%ds" % decoding["strDataLen"],
                tlv[self._bytesRead: self._bytesRead + decoding["strDataLen"]],
            )

            decoding["value"] = val
            self._bytesRead += decoding["strDataLen"]
        else:
            raise ValueError("Attempt to decode unsupported TLV type")

    def _get(self, tlv, decodings, out):
        endOfEncoding = False

        while len(tlv[self._bytesRead:]) > 0 and endOfEncoding is False:
            decoding = {}
            self._decodeControlAndTag(tlv, decoding)
            self._decodeStrLength(tlv, decoding)
            self._decodeVal(tlv, decoding)
            decodings.append(decoding)

            if decoding["type"] == "End of Collection":
                endOfEncoding = True
            else:
                if "profileTag" in list(decoding.keys()):
                    out[decoding["profileTag"]] = decoding["value"]
                elif "tag" in list(decoding.keys()):
                    if isinstance(out, Mapping):
                        tag = decoding["tag"] if decoding["tag"] is not None else "Any"
                        out[tag] = decoding["value"]
                    elif isinstance(out, TLVList):
                        tag = decoding["tag"] if decoding["tag"] is not None else None
                        out.append(tag, decoding["value"])
                    else:
                        out.append(decoding["value"])
                else:
                    raise ValueError("Attempt to decode unsupported TLV tag")


def tlvTagToSortKey(tag):
    if tag is None:
        return -1
    if isinstance(tag, int):
        majorOrder = 0
    elif isinstance(tag, tuple):
        (profileId, tag) = tag
        if profileId is None:
            majorOrder = 1
        else:
            majorOrder = profileId + 2
    else:
        raise ValueError("Invalid TLV tag")
    return (majorOrder << 32) + tag


if __name__ == "__main__":
    val = dict(
        [
            (1, 0),
            (2, 65536),
            (3, True),
            (4, None),
            (5, "Hello!"),
            (6, bytearray([0xDE, 0xAD, 0xBE, 0xEF])),
            (7, ["Goodbye!", 71024724507, False]),
            ((0x235A0000, 42), "FOO"),
            ((None, 42), "BAR"),
        ]
    )

    writer = TLVWriter()
    encodedVal = writer.put(None, val)

    reader = TLVReader(writer.encoding)
    out = reader.get()

    print("TLVReader input: " + str(val))
    print("TLVReader output: " + str(out["Any"]))

    if val == out["Any"]:
        print("Test Success")
    else:
        print("Test Failure")
