Пример #1
0
 def export(self, dbg_info: DebugInfo = DebugInfo.disabled()) -> bytes:
     """Export."""
     self._header.length = self.size
     raw_data = self._header.export()
     dbg_info.append_binary_section("header", raw_data)
     raw_data += self.data
     dbg_info.append_binary_section("data", self.data)
     return raw_data
Пример #2
0
    def export(self, padding8: Optional[bytes] = None, dbg_info: DebugInfo = DebugInfo.disabled()) -> bytes:
        """Serialization to binary form.

        :param padding8: 8 padding bytes used for in the header, None to use random bytes
                This value shall be used only for regression testing to generate same results
        :param dbg_info: class allowing to debug output from the export
        :return: Serialize object into bytes
        """
        major_version, minor_version = [int(v) for v in self.version.split('.')]
        product_version_words = [swap16(n) for n in self.product_version.nums]
        component_version_words = [swap16(n) for n in self.component_version.nums]
        signature2 = crypto_backend().random_bytes(4)
        padding = padding8 if padding8 else crypto_backend().random_bytes(8)

        if (major_version > 1) or ((major_version == 1) and (minor_version >= 2)):
            signature2 = self._SIGNATURE2

        dbg_info.append_section('SB-file-Header')

        result = pack(
            self._FORMAT,
            self.digest,
            self._SIGNATURE1,
            # header version
            major_version, minor_version,
            self.flags,
            self.image_blocks,
            self.first_boot_tag_block,
            self.first_boot_section_id,
            self.key_count,
            self.key_dictionary_block,
            self.header_blocks,
            self.section_count,
            self.section_header_size,
            padding[0:2],
            signature2,
            pack_timestamp(self.timestamp),
            # product version
            product_version_words[0], 0,
            product_version_words[1], 0,
            product_version_words[2], 0,
            # component version
            component_version_words[0], 0,
            component_version_words[1], 0,
            component_version_words[2], 0,
            self.drive_tag,
            padding[2:]
        )

        result = result[len(self.digest):]
        self.digest = crypto_backend().hash(result, 'sha1')

        dbg_info.append_binary_section('digest', self.digest)
        dbg_info.append_binary_section('attrs', result)

        return self.digest + result
Пример #3
0
def _log_test_output(dbg_info: DebugInfo) -> None:
    """Uses all methods of DebugInfo class to append data in different format

    :param dbg_info: instance used for logging
    """
    dbg_info.append_section("SECTION")
    dbg_info.append("-test-line-")
    dbg_info.append_binary_section("bin", b"\x00\x11\x22\xFF")
    dbg_info.append_binary_data("data", b"\x00\x11\x22")
    dbg_info.append_hex_data(b"\x00\x11\x22\x00\x11\x22\x00\x11\x22\x00\x11\x22")
Пример #4
0
def _log_test_output(dbg_info: DebugInfo) -> None:
    """Uses all methods of DebugInfo class to append data in different format

    :param dbg_info: instance used for logging
    """
    dbg_info.append_section('SECTION')
    dbg_info.append('-test-line-')
    dbg_info.append_binary_section('bin', b'\x00\x11\x22\xFF')
    dbg_info.append_binary_data('data', b'\x00\x11\x22')
    dbg_info.append_hex_data(
        b'\x00\x11\x22\x00\x11\x22\x00\x11\x22\x00\x11\x22')
Пример #5
0
    def export(self, dbg_info: DebugInfo = DebugInfo.disabled()) -> bytes:
        """Export into binary form (serialization).

        :param dbg_info: optional instance allowing to debug exported content
        :return: binary representation of the instance
        """
        self._header.length = self.size
        raw_data = self._header.export()
        dbg_info.append_binary_section("header", raw_data)
        for srk in self._keys:
            item_data = srk.export()
            raw_data += item_data
            dbg_info.append_binary_section("srk_item", item_data)
        return raw_data
Пример #6
0
    def export(
            self,
            header_padding8: Optional[bytes] = None,
            auth_padding: Optional[bytes] = None,
            dbg_info: DebugInfo = DebugInfo.disabled(),
    ) -> bytes:
        """Serialization to binary form.

        :param header_padding8: optional header padding, 8-bytes; recommended to use None to apply random value
        :param auth_padding: optional padding used after authentication; recommended to use None to apply random value
        :param dbg_info: instance allowing to debug generated output
        :return: serialize the instance into binary data
        :raises SPSDKError: Invalid section data
        :raises SPSDKError: Invalid padding length
        """
        self.update()
        self.validate()
        dbg_info.append_section("SB-FILE-1.x")
        data = self._header.export(padding8=header_padding8, dbg_info=dbg_info)
        # header table
        dbg_info.append_section("Sections-Header-Table")
        for sect_hdr in self._sections_hdr_table:
            sect_hdr_data = sect_hdr.export()
            dbg_info.append_binary_data("Section-Header-Item", sect_hdr_data)
            data += sect_hdr_data
        # sections
        dbg_info.append_section("Sections")
        for sect in self._sections:
            sect_data = sect.export(dbg_info)
            if len(sect_data) != sect.size:
                raise SPSDKError("Invalid section data")
            data += sect_data
        # authentication: SHA1
        auth_code = crypto_backend().hash(data, "sha1")
        dbg_info.append_binary_section("SHA1", auth_code)
        data += auth_code
        # padding
        padding_len = align(len(auth_code),
                            SecBootBlckSize.BLOCK_SIZE) - len(auth_code)
        if auth_padding is None:
            auth_padding = crypto_backend().random_bytes(padding_len)
        if padding_len != len(auth_padding):
            raise SPSDKError("Invalid padding length")
        data += auth_padding
        dbg_info.append_binary_section("padding", auth_padding)
        return data
Пример #7
0
    def export(
        self,
        header_padding8: Optional[bytes] = None,
        auth_padding: Optional[bytes] = None,
        dbg_info: DebugInfo = DebugInfo.disabled()
    ) -> bytes:
        """Serialization to binary form.

        :param header_padding8: optional header padding, 8-bytes; recommended to use None to apply random value
        :param auth_padding: optional padding used after authentication; recommended to use None to apply random value
        :param dbg_info: instance allowing to debug generated output
        :return: serialize the instance into binary data
        """
        self.update()
        self.validate()
        dbg_info.append_section('SB-FILE-1.x')
        data = self._header.export(padding8=header_padding8, dbg_info=dbg_info)
        # header table
        dbg_info.append_section('Sections-Header-Table')
        for sect_hdr in self._sections_hdr_table:
            sect_hdr_data = sect_hdr.export()
            dbg_info.append_binary_data('Section-Header-Item', sect_hdr_data)
            data += sect_hdr_data
        # sections
        dbg_info.append_section('Sections')
        for sect in self._sections:
            sect_data = sect.export(dbg_info)
            assert len(sect_data) == sect.size
            data += sect_data
        # authentication: SHA1
        auth_code = crypto_backend().hash(data, 'sha1')
        dbg_info.append_binary_section('SHA1', auth_code)
        data += auth_code
        # padding
        padding_len = align(len(auth_code),
                            SecBootBlckSize.BLOCK_SIZE) - len(auth_code)
        if auth_padding is None:
            auth_padding = crypto_backend().random_bytes(padding_len)
        assert padding_len == len(auth_padding)
        data += auth_padding
        dbg_info.append_binary_section('padding', auth_padding)
        return data
Пример #8
0
    def export(self, dbg_info: DebugInfo = DebugInfo.disabled()) -> bytes:
        """Serialization to binary representation.

        :param dbg_info: instance allowing to provide debug info about exported data
        :return: binary representation of the region (serialization).
        """
        result = super().export()
        # KIB
        kib_data = self._kib.export()
        dbg_info.append_binary_section("BEE-KIB (non-crypted)", kib_data)
        aes = AES.new(self._sw_key, AES.MODE_ECB)
        result += aes.encrypt(kib_data)
        # padding
        result = extend_block(result, self.PRDB_OFFSET)
        # PRDB
        prdb_data = self._prdb.export()
        dbg_info.append_binary_section("BEE-PRDB (non-crypted)", prdb_data)
        aes = AES.new(self._kib.kib_key, AES.MODE_CBC, self._kib.kib_iv)
        result += aes.encrypt(prdb_data)
        # padding
        return extend_block(result, self.SIZE)
Пример #9
0
 def export(self, dbg_info: DebugInfo = DebugInfo.disabled()) -> bytes:
     """Export command as binary."""
     self._update_data()
     result = super().export(dbg_info)
     dbg_info.append_binary_section("load-data", self.data)
     return result + self.data