1# Copyright (C) 2021-2022 Intel Corporation. 2# 3# SPDX-License-Identifier: BSD-3-Clause 4# 5 6import ctypes 7import logging 8 9import inspectorlib.cdata as cdata 10from acpiparser._utils import TableHeader 11 12def tpm2_optional_data(data_len): 13 start_method_data_len = 0 14 has_log_area = False 15 if data_len <= 12: 16 start_method_data_len = data_len 17 elif data_len == 24: 18 start_method_data_len = 12 19 has_log_area = True 20 else: 21 start_method_data_len = 12 22 logging.debug(f"TPM2 data length: {data_len + 52} is greater than 64 bytes but less than 76 bytes.") 23 logging.debug(f"The TPM2 data is still processed but the 65 to {data_len + 52} bytes are discard.") 24 return start_method_data_len, has_log_area 25 26def tpm2_factory(start_method_data_len, has_log_area): 27 class TPM2(cdata.Struct): 28 _pack_ = 1 29 _fields_ = [ 30 ('header', TableHeader), 31 ('platform_class', ctypes.c_uint16), 32 ('reserved', ctypes.c_uint16), 33 ('address_of_control_area', ctypes.c_uint64), 34 ('start_method', ctypes.c_uint32), 35 ('start_method_specific_parameters', ctypes.c_ubyte * start_method_data_len), 36 ] + ([ 37 ('log_area_minimum_length', ctypes.c_uint32), 38 ('log_area_start_address', ctypes.c_uint64), 39 ] if has_log_area else []) 40 41 return TPM2 42 43def TPM2(val): 44 """Create class based on decode of a TPM2 table from filename.""" 45 if isinstance(val, str): 46 base_length = 52 47 data = open(val, mode='rb').read() 48 start_method_data_len, has_log_area = tpm2_optional_data(len(data) - base_length) 49 return tpm2_factory(start_method_data_len, has_log_area).from_buffer_copy(data) 50 elif isinstance(val, bytearray): 51 return tpm2_factory(12, True).from_buffer(val) if len(val) > 64 else tpm2_factory(12, False).from_buffer(val) 52