/* SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later */
#include "array.h"

#include <libpldm/base.h>
#include <libpldm/bios.h>
#include <libpldm/bios_table.h>
#include <libpldm/utils.h>

#include <assert.h>
#include <endian.h>
#include <limits.h>
#include <stdbool.h>
#include <stdint.h>
#include <stdlib.h>
#include <string.h>

#define POINTER_CHECK(pointer)                                                 \
	do {                                                                   \
		if ((pointer) == NULL)                                         \
			return PLDM_ERROR_INVALID_DATA;                        \
	} while (0)

#define ATTR_TYPE_EXPECT(type, expected)                                       \
	do {                                                                   \
		if ((type) != (expected) && (type) != ((expected) | 0x80))     \
			return PLDM_ERROR_INVALID_DATA;                        \
	} while (0)

#define BUFFER_SIZE_EXPECT(current_size, expected_size)                        \
	do {                                                                   \
		if ((current_size) < (expected_size))                          \
			return PLDM_ERROR_INVALID_LENGTH;                      \
	} while (0)

#define MEMBER_SIZE(type, member) sizeof(((struct type *)0)->member)

static void set_errmsg(const char **errmsg, const char *msg)
{
	if (errmsg != NULL) {
		*errmsg = msg;
	}
}

static int get_bios_string_handle(uint16_t *val)
{
	static uint16_t handle = 0;
	assert(handle != UINT16_MAX);
	if (handle == UINT16_MAX) {
		return PLDM_ERROR_INVALID_DATA;
	}

	*val = handle++;
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_string_entry_encode_length(uint16_t string_length)
{
	return sizeof(struct pldm_bios_string_table_entry) -
	       MEMBER_SIZE(pldm_bios_string_table_entry, name) + string_length;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_string_entry_encode(void *entry, size_t entry_length,
					const char *str, uint16_t str_length)
{
	if (str_length == 0) {
		return PLDM_ERROR_INVALID_DATA;
	}
	POINTER_CHECK(entry);
	POINTER_CHECK(str);
	size_t length = pldm_bios_table_string_entry_encode_length(str_length);
	BUFFER_SIZE_EXPECT(entry_length, length);
	struct pldm_bios_string_table_entry *string_entry = entry;
	uint16_t handle;
	int rc = get_bios_string_handle(&handle);
	if (rc != PLDM_SUCCESS) {
		return rc;
	}
	string_entry->string_handle = htole16(handle);
	string_entry->string_length = htole16(str_length);
	memcpy(string_entry->name, str, str_length);
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_string_entry_decode_handle(
	const struct pldm_bios_string_table_entry *entry)
{
	return le16toh(entry->string_handle);
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_string_entry_decode_string_length(
	const struct pldm_bios_string_table_entry *entry)
{
	return le16toh(entry->string_length);
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_string_entry_decode_string(
	const struct pldm_bios_string_table_entry *entry, char *buffer,
	size_t size)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(buffer);
	if (size == 0) {
		return PLDM_ERROR_INVALID_LENGTH;
	}
	size_t length =
		pldm_bios_table_string_entry_decode_string_length(entry);
	length = length < (size - 1) ? length : (size - 1);
	memcpy(buffer, entry->name, length);
	buffer[length] = 0;
	return PLDM_SUCCESS;
}

static ssize_t string_table_entry_length(const void *table_entry)
{
	const struct pldm_bios_string_table_entry *entry = table_entry;
	size_t len = sizeof(*entry) - sizeof(entry->name) +
		     pldm_bios_table_string_entry_decode_string_length(entry);
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

static int get_bios_attr_handle(uint16_t *val)
{
	static uint16_t handle = 0;
	assert(handle != UINT16_MAX);
	if (handle == UINT16_MAX) {
		return PLDM_ERROR_INVALID_DATA;
	}

	*val = handle++;
	return PLDM_SUCCESS;
}

static int attr_table_entry_encode_header(void *entry, size_t length,
					  uint8_t attr_type,
					  uint16_t string_handle)
{
	struct pldm_bios_attr_table_entry *attr_entry = entry;

	assert(sizeof(*attr_entry) <= length);
	if (sizeof(*attr_entry) > length) {
		return PLDM_ERROR_INVALID_LENGTH;
	}

	uint16_t handle;
	int rc = get_bios_attr_handle(&handle);
	if (rc != PLDM_SUCCESS) {
		return rc;
	}

	attr_entry->attr_handle = htole16(handle);
	attr_entry->attr_type = attr_type;
	attr_entry->string_handle = htole16(string_handle);

	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_entry_decode_attribute_handle(
	const struct pldm_bios_attr_table_entry *entry)
{
	return le16toh(entry->attr_handle);
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_entry_decode_attribute_type(
	const struct pldm_bios_attr_table_entry *entry)
{
	return entry->attr_type;
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_entry_decode_string_handle(
	const struct pldm_bios_attr_table_entry *entry)
{
	return le16toh(entry->string_handle);
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_entry_enum_encode_length(uint8_t pv_num,
						     uint8_t def_num)
{
	return sizeof(struct pldm_bios_attr_table_entry) -
	       MEMBER_SIZE(pldm_bios_attr_table_entry, metadata) +
	       sizeof(pv_num) + pv_num * sizeof(uint16_t) + sizeof(def_num) +
	       def_num;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_enum_encode(
	void *entry, size_t entry_length,
	const struct pldm_bios_table_attr_entry_enum_info *info)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(info);
	size_t length = pldm_bios_table_attr_entry_enum_encode_length(
		info->pv_num, info->def_num);
	BUFFER_SIZE_EXPECT(entry_length, length);
	uint8_t attr_type = info->read_only ? PLDM_BIOS_ENUMERATION_READ_ONLY :
					      PLDM_BIOS_ENUMERATION;
	int rc = attr_table_entry_encode_header(entry, entry_length, attr_type,
						info->name_handle);
	if (rc != PLDM_SUCCESS) {
		return rc;
	}
	struct pldm_bios_attr_table_entry *attr_entry = entry;
	attr_entry->metadata[0] = info->pv_num;
	uint16_t *pv_hdls =
		(uint16_t *)(attr_entry->metadata + 1 /* sizeof(pv num) */);
	size_t i;
	for (i = 0; i < info->pv_num; i++) {
		pv_hdls[i] = htole16(info->pv_handle[i]);
	}
	attr_entry->metadata[1 + info->pv_num * sizeof(uint16_t)] =
		info->def_num;
	memcpy(attr_entry->metadata + 1 /* sizeof(pv num) */ +
		       info->pv_num * sizeof(uint16_t) + 1 /* sizeof(def num)*/,
	       info->def_index, info->def_num);
	return PLDM_SUCCESS;
}

#define ATTR_TYPE_EXPECT(type, expected)                                       \
	do {                                                                   \
		if ((type) != (expected) && (type) != ((expected) | 0x80))     \
			return PLDM_ERROR_INVALID_DATA;                        \
	} while (0)

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_enum_decode_pv_num(
	const struct pldm_bios_attr_table_entry *entry, uint8_t *pv_num)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(pv_num);
	ATTR_TYPE_EXPECT(entry->attr_type, PLDM_BIOS_ENUMERATION);
	*pv_num = entry->metadata[0];
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_enum_decode_def_num(
	const struct pldm_bios_attr_table_entry *entry, uint8_t *def_num)
{
	uint8_t pv_num;

	POINTER_CHECK(entry);
	POINTER_CHECK(def_num);
	ATTR_TYPE_EXPECT(entry->attr_type, PLDM_BIOS_ENUMERATION);
	pv_num = entry->metadata[0];
	*def_num = entry->metadata[sizeof(uint8_t) + sizeof(uint16_t) * pv_num];
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_enum_decode_pv_hdls(
	const struct pldm_bios_attr_table_entry *entry, uint16_t *pv_hdls,
	uint8_t pv_num)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(pv_hdls);
	ATTR_TYPE_EXPECT(entry->attr_type, PLDM_BIOS_ENUMERATION);
	uint8_t num = entry->metadata[0];
	num = num < pv_num ? num : pv_num;
	size_t i;
	for (i = 0; i < num; i++) {
		uint16_t *hdl = (uint16_t *)(entry->metadata + sizeof(uint8_t) +
					     i * sizeof(uint16_t));
		pv_hdls[i] = le16toh(*hdl);
	}
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_entry_enum_decode_def_indices(
	const struct pldm_bios_attr_table_entry *entry, uint8_t *def_indices,
	uint8_t def_num)
{
	uint8_t num = 0;

	/* TODO: Fix the API to propagate errors */
	pldm_bios_table_attr_entry_enum_decode_def_num(entry, &num);
	num = num < def_num ? num : def_num;
	uint8_t pv_num = entry->metadata[0];
	const uint8_t *p = entry->metadata +
			   sizeof(uint8_t) /* number of possible values*/
			   + pv_num * sizeof(uint16_t) /* possible values */
			   + sizeof(uint8_t); /* number of default values */
	memcpy(def_indices, p, num);
	return num;
}

/** @brief Get length of an enum attribute entry
 */
static ssize_t attr_table_entry_length_enum(const void *arg)
{
	const struct pldm_bios_attr_table_entry *entry = arg;
	uint8_t pv_num = entry->metadata[0];
	uint8_t def_num = 0;

	/* TODO: Fix the API to propagate errors */
	pldm_bios_table_attr_entry_enum_decode_def_num(entry, &def_num);
	size_t len =
		pldm_bios_table_attr_entry_enum_encode_length(pv_num, def_num);
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

struct attr_table_string_entry_fields {
	uint8_t string_type;
	uint16_t min_length;
	uint16_t max_length;
	uint16_t def_length;
	uint8_t def_string[1];
} __attribute__((packed));

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_entry_string_encode_length(uint16_t def_str_len)
{
	return sizeof(struct pldm_bios_attr_table_entry) -
	       MEMBER_SIZE(pldm_bios_attr_table_entry, metadata) +
	       sizeof(struct attr_table_string_entry_fields) -
	       MEMBER_SIZE(attr_table_string_entry_fields, def_string) +
	       def_str_len;
}

#define PLDM_STRING_TYPE_MAX	5
#define PLDM_STRING_TYPE_VENDOR 0xff

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_string_info_check(
	const struct pldm_bios_table_attr_entry_string_info *info,
	const char **errmsg)
{
	if (info->min_length > info->max_length) {
		set_errmsg(errmsg, "MinimumStingLength should not be greater "
				   "than MaximumStringLength");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->min_length == info->max_length &&
	    info->def_length != info->min_length) {
		set_errmsg(errmsg, "Wrong DefaultStringLength");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->def_length > info->max_length ||
	    info->def_length < info->min_length) {
		set_errmsg(errmsg, "Wrong DefaultStringLength");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->string_type > PLDM_STRING_TYPE_MAX &&
	    info->string_type != PLDM_STRING_TYPE_VENDOR) {
		set_errmsg(errmsg, "Wrong StringType");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->def_string && info->def_length != strlen(info->def_string)) {
		set_errmsg(errmsg, "Length of DefaultString should be equal to "
				   "DefaultStringLength");
		return PLDM_ERROR_INVALID_DATA;
	}

	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_string_encode(
	void *entry, size_t entry_length,
	const struct pldm_bios_table_attr_entry_string_info *info)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(info);
	size_t length = pldm_bios_table_attr_entry_string_encode_length(
		info->def_length);
	BUFFER_SIZE_EXPECT(entry_length, length);
	if (pldm_bios_table_attr_entry_string_info_check(info, NULL) !=
	    PLDM_SUCCESS) {
		return PLDM_ERROR_INVALID_DATA;
	}
	uint8_t attr_type = info->read_only ? PLDM_BIOS_STRING_READ_ONLY :
					      PLDM_BIOS_STRING;
	int rc = attr_table_entry_encode_header(entry, entry_length, attr_type,
						info->name_handle);
	if (rc != PLDM_SUCCESS) {
		return rc;
	}
	struct pldm_bios_attr_table_entry *attr_entry = entry;
	struct attr_table_string_entry_fields *attr_fields =
		(struct attr_table_string_entry_fields *)attr_entry->metadata;
	attr_fields->string_type = info->string_type;
	attr_fields->min_length = htole16(info->min_length);
	attr_fields->max_length = htole16(info->max_length);
	attr_fields->def_length = htole16(info->def_length);
	if (info->def_length != 0 && info->def_string != NULL) {
		memcpy(attr_fields->def_string, info->def_string,
		       info->def_length);
	}
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_string_decode_def_string_length(
	const struct pldm_bios_attr_table_entry *entry,
	uint16_t *def_string_length)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(def_string_length);
	ATTR_TYPE_EXPECT(entry->attr_type, PLDM_BIOS_STRING);
	struct attr_table_string_entry_fields *fields =
		(struct attr_table_string_entry_fields *)entry->metadata;
	*def_string_length = le16toh(fields->def_length);
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_entry_string_decode_string_type(
	const struct pldm_bios_attr_table_entry *entry)
{
	struct attr_table_string_entry_fields *fields =
		(struct attr_table_string_entry_fields *)entry->metadata;
	return fields->string_type;
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_entry_string_decode_max_length(
	const struct pldm_bios_attr_table_entry *entry)
{
	struct attr_table_string_entry_fields *fields =
		(struct attr_table_string_entry_fields *)entry->metadata;
	return le16toh(fields->max_length);
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_entry_string_decode_min_length(
	const struct pldm_bios_attr_table_entry *entry)
{
	struct attr_table_string_entry_fields *fields =
		(struct attr_table_string_entry_fields *)entry->metadata;
	return le16toh(fields->min_length);
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_entry_string_decode_def_string(
	const struct pldm_bios_attr_table_entry *entry, char *buffer,
	size_t size)
{
	uint16_t length = 0;
	int rc;

	if (!entry || !buffer || size == 0) {
		return 0;
	}

	/* TODO: Rework the API to propagate the error */
	rc = pldm_bios_table_attr_entry_string_decode_def_string_length(
		entry, &length);
	if (rc != PLDM_SUCCESS) {
		return 0;
	}

	length = length < (size - 1) ? length : (size - 1);
	struct attr_table_string_entry_fields *fields =
		(struct attr_table_string_entry_fields *)entry->metadata;
	memcpy(buffer, fields->def_string, length);
	buffer[length] = 0;
	return length;
}

/** @brief Get length of a string attribute entry
 */
static ssize_t attr_table_entry_length_string(const void *entry)
{
	uint16_t def_str_len = 0;

	/* TODO: Rework the API to propagate the error */
	pldm_bios_table_attr_entry_string_decode_def_string_length(
		entry, &def_str_len);
	size_t len =
		pldm_bios_table_attr_entry_string_encode_length(def_str_len);
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

struct attr_table_integer_entry_fields {
	uint64_t lower_bound;
	uint64_t upper_bound;
	uint32_t scalar_increment;
	uint64_t default_value;
} __attribute__((packed));

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_entry_integer_encode_length(void)
{
	return sizeof(struct pldm_bios_attr_table_entry) - 1 +
	       sizeof(struct attr_table_integer_entry_fields);
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_integer_info_check(
	const struct pldm_bios_table_attr_entry_integer_info *info,
	const char **errmsg)
{
	if (info->lower_bound == info->upper_bound) {
		if (info->default_value != info->lower_bound) {
			set_errmsg(errmsg, "Wrong DefaultValue");
			return PLDM_ERROR_INVALID_DATA;
		}
		if (info->scalar_increment != 0) {
			set_errmsg(errmsg, "Wrong ScalarIncrement");
			return PLDM_ERROR_INVALID_DATA;
		}
		return PLDM_SUCCESS;
	}
	if (info->lower_bound > info->upper_bound) {
		set_errmsg(errmsg,
			   "LowerBound should not be greater than UpperBound");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->default_value > info->upper_bound ||
	    info->default_value < info->lower_bound) {
		set_errmsg(errmsg, "Wrong DefaultValue");
		return PLDM_ERROR_INVALID_DATA;
	}
	if (info->scalar_increment == 0) {
		set_errmsg(errmsg, "ScalarIncrement should not be zero when "
				   "lower_bound != upper_bound");
		return PLDM_ERROR_INVALID_DATA;
	}
	if ((info->default_value - info->lower_bound) %
		    info->scalar_increment !=
	    0) {
		set_errmsg(errmsg, "Wrong DefaultValue or ScalarIncrement");
		return PLDM_ERROR_INVALID_DATA;
	}
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_entry_integer_encode(
	void *entry, size_t entry_length,
	const struct pldm_bios_table_attr_entry_integer_info *info)
{
	POINTER_CHECK(entry);
	POINTER_CHECK(info);
	size_t length = pldm_bios_table_attr_entry_integer_encode_length();
	BUFFER_SIZE_EXPECT(entry_length, length);
	if (pldm_bios_table_attr_entry_integer_info_check(info, NULL) !=
	    PLDM_SUCCESS) {
		return PLDM_ERROR_INVALID_DATA;
	}
	uint8_t attr_type = info->read_only ? PLDM_BIOS_INTEGER_READ_ONLY :
					      PLDM_BIOS_INTEGER;
	int rc = attr_table_entry_encode_header(entry, entry_length, attr_type,
						info->name_handle);
	if (rc != PLDM_SUCCESS) {
		return rc;
	}
	struct pldm_bios_attr_table_entry *attr_entry = entry;
	struct attr_table_integer_entry_fields *attr_fields =
		(struct attr_table_integer_entry_fields *)attr_entry->metadata;
	attr_fields->lower_bound = htole64(info->lower_bound);
	attr_fields->upper_bound = htole64(info->upper_bound);
	attr_fields->scalar_increment = htole32(info->scalar_increment);
	attr_fields->default_value = htole64(info->default_value);
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
void pldm_bios_table_attr_entry_integer_decode(
	const struct pldm_bios_attr_table_entry *entry, uint64_t *lower,
	uint64_t *upper, uint32_t *scalar, uint64_t *def)
{
	struct attr_table_integer_entry_fields *fields =
		(struct attr_table_integer_entry_fields *)entry->metadata;
	*lower = le64toh(fields->lower_bound);
	*upper = le64toh(fields->upper_bound);
	*scalar = le32toh(fields->scalar_increment);
	*def = le64toh(fields->default_value);
}

static ssize_t attr_table_entry_length_integer(const void *entry)
{
	(void)entry;
	size_t len = pldm_bios_table_attr_entry_integer_encode_length();
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

struct table_entry_length {
	uint8_t attr_type;
	ssize_t (*entry_length_handler)(const void *);
};

static const struct table_entry_length *
find_table_entry_length_by_type(uint8_t attr_type,
				const struct table_entry_length *handlers,
				size_t count)
{
	size_t i;
	for (i = 0; i < count; i++) {
		if (attr_type == handlers[i].attr_type) {
			return &handlers[i];
		}
	}
	return NULL;
}

static const struct table_entry_length attr_table_entries[] = {
	{ .attr_type = PLDM_BIOS_ENUMERATION,
	  .entry_length_handler = attr_table_entry_length_enum },
	{ .attr_type = PLDM_BIOS_ENUMERATION_READ_ONLY,
	  .entry_length_handler = attr_table_entry_length_enum },
	{ .attr_type = PLDM_BIOS_STRING,
	  .entry_length_handler = attr_table_entry_length_string },
	{ .attr_type = PLDM_BIOS_STRING_READ_ONLY,
	  .entry_length_handler = attr_table_entry_length_string },
	{ .attr_type = PLDM_BIOS_INTEGER,
	  .entry_length_handler = attr_table_entry_length_integer },
	{ .attr_type = PLDM_BIOS_INTEGER_READ_ONLY,
	  .entry_length_handler = attr_table_entry_length_integer },
};

static ssize_t attr_table_entry_length(const void *table_entry)
{
	const struct pldm_bios_attr_table_entry *entry = table_entry;
	const struct table_entry_length *attr_table_entry =
		find_table_entry_length_by_type(entry->attr_type,
						attr_table_entries,
						ARRAY_SIZE(attr_table_entries));
	assert(attr_table_entry != NULL);
	if (!attr_table_entry) {
		return -1;
	}
	assert(attr_table_entry->entry_length_handler != NULL);
	if (!attr_table_entry->entry_length_handler) {
		return -1;
	}

	return attr_table_entry->entry_length_handler(entry);
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_value_entry_decode_attribute_handle(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	return le16toh(entry->attr_handle);
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_value_entry_decode_attribute_type(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	return entry->attr_type;
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_value_entry_encode_enum_length(uint8_t count)
{
	return sizeof(struct pldm_bios_attr_val_table_entry) - 1 +
	       sizeof(count) + count;
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_value_entry_enum_decode_number(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	return entry->value[0];
}

LIBPLDM_ABI_STABLE
uint8_t pldm_bios_table_attr_value_entry_enum_decode_handles(
	const struct pldm_bios_attr_val_table_entry *entry, uint8_t *handles,
	uint8_t number)
{
	uint8_t curr_num =
		pldm_bios_table_attr_value_entry_enum_decode_number(entry);
	curr_num = number < curr_num ? number : curr_num;
	memcpy(handles, &entry->value[1], curr_num);

	return curr_num;
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_value_entry_encode_enum(
	void *entry, size_t entry_length, uint16_t attr_handle,
	uint8_t attr_type, uint8_t count, const uint8_t *handles)
{
	struct pldm_bios_attr_val_table_entry *table_entry;

	POINTER_CHECK(entry);
	POINTER_CHECK(handles);
	if (count != 0 && handles == NULL) {
		return PLDM_ERROR_INVALID_DATA;
	}
	ATTR_TYPE_EXPECT(attr_type, PLDM_BIOS_ENUMERATION);
	BUFFER_SIZE_EXPECT(entry_length, sizeof(*table_entry));
	table_entry = entry;
	table_entry->attr_handle = htole16(attr_handle);
	table_entry->attr_type = attr_type;
	table_entry->value[0] = count;
	if (entry_length - sizeof(*table_entry) < count) {
		return PLDM_ERROR_INVALID_LENGTH;
	}
	memcpy(&table_entry->value[1], handles, count);
	return PLDM_SUCCESS;
}

static ssize_t attr_value_table_entry_length_enum(const void *entry)
{
	uint8_t number =
		pldm_bios_table_attr_value_entry_enum_decode_number(entry);
	size_t len =
		pldm_bios_table_attr_value_entry_encode_enum_length(number);
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

LIBPLDM_ABI_STABLE
size_t
pldm_bios_table_attr_value_entry_encode_string_length(uint16_t string_length)
{
	return sizeof(struct pldm_bios_attr_val_table_entry) - 1 +
	       sizeof(string_length) + string_length;
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_value_entry_string_decode_length(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	uint16_t str_length = 0;
	memcpy(&str_length, entry->value, sizeof(str_length));
	return le16toh(str_length);
}

LIBPLDM_ABI_STABLE
void pldm_bios_table_attr_value_entry_string_decode_string(
	const struct pldm_bios_attr_val_table_entry *entry,
	struct variable_field *current_string)
{
	current_string->length =
		pldm_bios_table_attr_value_entry_string_decode_length(entry);
	current_string->ptr =
		entry->value + sizeof(uint16_t); // sizeof(CurrentStringLength)
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_value_entry_encode_string(
	void *entry, size_t entry_length, uint16_t attr_handle,
	uint8_t attr_type, uint16_t str_length, const char *str)
{
	struct pldm_bios_attr_val_table_entry *table_entry;

	POINTER_CHECK(entry);
	if (str_length != 0 && str == NULL) {
		return PLDM_ERROR_INVALID_DATA;
	}
	ATTR_TYPE_EXPECT(attr_type, PLDM_BIOS_STRING);
	BUFFER_SIZE_EXPECT(entry_length,
			   (sizeof(*table_entry) - 1 + sizeof(str_length)));
	table_entry = entry;
	table_entry->attr_handle = htole16(attr_handle);
	table_entry->attr_type = attr_type;
	if (entry_length - (sizeof(*table_entry) - 1 + sizeof(str_length)) <
	    str_length) {
		return PLDM_ERROR_INVALID_LENGTH;
	}
	memcpy(table_entry->value + sizeof(str_length), str, str_length);
	str_length = htole16(str_length);
	memcpy(table_entry->value, &str_length, sizeof(str_length));
	return PLDM_SUCCESS;
}

static ssize_t attr_value_table_entry_length_string(const void *entry)
{
	uint16_t str_length =
		pldm_bios_table_attr_value_entry_string_decode_length(entry);
	size_t len = pldm_bios_table_attr_value_entry_encode_string_length(
		str_length);
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_value_entry_encode_integer_length(void)
{
	return sizeof(struct pldm_bios_attr_val_table_entry) - 1 +
	       sizeof(uint64_t);
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_value_entry_encode_integer(void *entry,
						    size_t entry_length,
						    uint16_t attr_handle,
						    uint8_t attr_type,
						    uint64_t cv)
{
	POINTER_CHECK(entry);
	size_t length =
		pldm_bios_table_attr_value_entry_encode_integer_length();
	ATTR_TYPE_EXPECT(attr_type, PLDM_BIOS_INTEGER);
	BUFFER_SIZE_EXPECT(entry_length, length);
	struct pldm_bios_attr_val_table_entry *table_entry = entry;
	table_entry->attr_handle = htole16(attr_handle);
	table_entry->attr_type = attr_type;
	cv = htole64(cv);
	memcpy(table_entry->value, &cv, sizeof(uint64_t));
	return PLDM_SUCCESS;
}

LIBPLDM_ABI_STABLE
uint64_t pldm_bios_table_attr_value_entry_integer_decode_cv(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	uint64_t cv = 0;
	memcpy(&cv, entry->value, sizeof(cv));
	cv = le64toh(cv);
	return cv;
}

static ssize_t attr_value_table_entry_length_integer(const void *entry)
{
	(void)entry;
	size_t len = pldm_bios_table_attr_value_entry_encode_integer_length();
	if (len > SSIZE_MAX) {
		return -1;
	}
	return (ssize_t)len;
}

static const struct table_entry_length attr_value_table_entries[] = {
	{ .attr_type = PLDM_BIOS_ENUMERATION,
	  .entry_length_handler = attr_value_table_entry_length_enum },
	{ .attr_type = PLDM_BIOS_ENUMERATION_READ_ONLY,
	  .entry_length_handler = attr_value_table_entry_length_enum },
	{ .attr_type = PLDM_BIOS_STRING,
	  .entry_length_handler = attr_value_table_entry_length_string },
	{ .attr_type = PLDM_BIOS_STRING_READ_ONLY,
	  .entry_length_handler = attr_value_table_entry_length_string },
	{ .attr_type = PLDM_BIOS_INTEGER,
	  .entry_length_handler = attr_value_table_entry_length_integer },
	{ .attr_type = PLDM_BIOS_INTEGER_READ_ONLY,
	  .entry_length_handler = attr_value_table_entry_length_integer },
};

static ssize_t attr_value_table_entry_length(const void *table_entry)
{
	const struct pldm_bios_attr_val_table_entry *entry = table_entry;
	const struct table_entry_length *entry_length =
		find_table_entry_length_by_type(
			entry->attr_type, attr_value_table_entries,
			ARRAY_SIZE(attr_value_table_entries));
	assert(entry_length != NULL);
	if (!entry_length) {
		return -1;
	}
	assert(entry_length->entry_length_handler != NULL);
	if (!entry_length->entry_length_handler) {
		return -1;
	}

	return entry_length->entry_length_handler(entry);
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_attr_value_entry_length(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	return attr_value_table_entry_length(entry);
}

LIBPLDM_ABI_STABLE
uint16_t pldm_bios_table_attr_value_entry_decode_handle(
	const struct pldm_bios_attr_val_table_entry *entry)
{
	return le16toh(entry->attr_handle);
}

static size_t pad_size_get(size_t size_without_pad)
{
	return (4 - (size_without_pad % 4)) % 4;
}

static uint8_t *pad_append(uint8_t *table_end, size_t pad_size)
{
	while (pad_size--) {
		*table_end++ = 0;
	}

	return table_end;
}

static uint8_t *checksum_append(uint8_t *table_end, uint32_t checksum)
{
	checksum = htole32(checksum);
	memcpy(table_end, &checksum, sizeof(checksum));

	return table_end + sizeof(checksum);
}

LIBPLDM_ABI_STABLE
size_t pldm_bios_table_pad_checksum_size(size_t size_without_pad)
{
	return pad_size_get(size_without_pad) + sizeof(uint32_t);
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_append_pad_checksum(void *table, size_t capacity,
					size_t *size)
{
	if (!table || !size) {
		return PLDM_ERROR_INVALID_DATA;
	}

	size_t pad_checksum_size = pldm_bios_table_pad_checksum_size(*size);

	if (SIZE_MAX - pad_checksum_size < *size) {
		return PLDM_ERROR_INVALID_LENGTH;
	}

	size_t total_length = *size + pad_checksum_size;
	if (capacity < total_length) {
		return PLDM_ERROR_INVALID_LENGTH;
	}

	if (UINTPTR_MAX - *size < (uintptr_t)table) {
		return PLDM_ERROR_INVALID_LENGTH;
	}
	uint8_t *table_end = (uint8_t *)table + *size;
	size_t pad_size = pad_size_get(*size);
	table_end = pad_append(table_end, pad_size);

	uint32_t checksum = crc32(table, *size + pad_size);
	checksum_append(table_end, checksum);
	*size = total_length;

	return PLDM_SUCCESS;
}

struct pldm_bios_table_iter {
	const uint8_t *table_data;
	size_t table_len;
	size_t current_pos;
	ssize_t (*entry_length_handler)(const void *table_entry);
};

LIBPLDM_ABI_STABLE
struct pldm_bios_table_iter *
pldm_bios_table_iter_create(const void *table, size_t length,
			    enum pldm_bios_table_types type)
{
	struct pldm_bios_table_iter *iter = malloc(sizeof(*iter));
	assert(iter != NULL);
	if (!iter) {
		return NULL;
	}
	iter->table_data = table;
	iter->table_len = length;
	iter->current_pos = 0;
	iter->entry_length_handler = NULL;
	switch (type) {
	case PLDM_BIOS_STRING_TABLE:
		iter->entry_length_handler = string_table_entry_length;
		break;
	case PLDM_BIOS_ATTR_TABLE:
		iter->entry_length_handler = attr_table_entry_length;
		break;
	case PLDM_BIOS_ATTR_VAL_TABLE:
		iter->entry_length_handler = attr_value_table_entry_length;
		break;
	}

	return iter;
}

LIBPLDM_ABI_STABLE
void pldm_bios_table_iter_free(struct pldm_bios_table_iter *iter)
{
	free(iter);
}

#define pad_and_check_max 7
LIBPLDM_ABI_STABLE
bool pldm_bios_table_iter_is_end(const struct pldm_bios_table_iter *iter)
{
	ssize_t len;

	if (!iter) {
		return true;
	}

	if (iter->table_len - iter->current_pos <= pad_and_check_max) {
		return true;
	}

	len = iter->entry_length_handler(iter->table_data + iter->current_pos);

	return len < 0;
}

LIBPLDM_ABI_STABLE
void pldm_bios_table_iter_next(struct pldm_bios_table_iter *iter)
{
	if (pldm_bios_table_iter_is_end(iter)) {
		return;
	}
	const void *entry = iter->table_data + iter->current_pos;
	ssize_t rc = iter->entry_length_handler(entry);
	/* Prevent bad behaviour by acting as if we've hit the end of the iterator */
	if (rc < 0) {
		return;
	}
	iter->current_pos += rc;
}

LIBPLDM_ABI_STABLE
const void *pldm_bios_table_iter_value(struct pldm_bios_table_iter *iter)
{
	return iter->table_data + iter->current_pos;
}

typedef bool (*equal_handler)(const void *entry, const void *key);

static const void *
pldm_bios_table_entry_find_by_iter(struct pldm_bios_table_iter *iter,
				   const void *key, equal_handler equal)
{
	const void *entry;
	while (!pldm_bios_table_iter_is_end(iter)) {
		entry = pldm_bios_table_iter_value(iter);
		if (equal(entry, key)) {
			return entry;
		}
		pldm_bios_table_iter_next(iter);
	}
	return NULL;
}

static const void *
pldm_bios_table_entry_find_from_table(const void *table, size_t length,
				      enum pldm_bios_table_types type,
				      equal_handler equal, const void *key)
{
	struct pldm_bios_table_iter *iter =
		pldm_bios_table_iter_create(table, length, type);
	const void *entry =
		pldm_bios_table_entry_find_by_iter(iter, key, equal);
	pldm_bios_table_iter_free(iter);
	return entry;
}

static bool string_table_handle_equal(const void *entry, const void *key)
{
	const struct pldm_bios_string_table_entry *string_entry = entry;
	uint16_t handle = *(uint16_t *)key;
	if (pldm_bios_table_string_entry_decode_handle(string_entry) ==
	    handle) {
		return true;
	}
	return false;
}

LIBPLDM_ABI_STABLE
const struct pldm_bios_string_table_entry *
pldm_bios_table_string_find_by_handle(const void *table, size_t length,
				      uint16_t handle)
{
	return pldm_bios_table_entry_find_from_table(table, length,
						     PLDM_BIOS_STRING_TABLE,
						     string_table_handle_equal,
						     &handle);
}

struct string_equal_arg {
	uint16_t str_length;
	const char *str;
};

static bool string_table_string_equal(const void *entry, const void *key)
{
	const struct pldm_bios_string_table_entry *string_entry = entry;
	const struct string_equal_arg *arg = key;
	if (arg->str_length !=
	    pldm_bios_table_string_entry_decode_string_length(string_entry)) {
		return false;
	}
	if (memcmp(string_entry->name, arg->str, arg->str_length) != 0) {
		return false;
	}
	return true;
}

LIBPLDM_ABI_STABLE
const struct pldm_bios_string_table_entry *
pldm_bios_table_string_find_by_string(const void *table, size_t length,
				      const char *str)
{
	uint16_t str_length = strlen(str);
	struct string_equal_arg arg = { str_length, str };
	return pldm_bios_table_entry_find_from_table(table, length,
						     PLDM_BIOS_STRING_TABLE,
						     string_table_string_equal,
						     &arg);
}

static bool attr_table_handle_equal(const void *entry, const void *key)
{
	uint16_t handle = *(uint16_t *)key;
	return pldm_bios_table_attr_entry_decode_attribute_handle(entry) ==
	       handle;
}

LIBPLDM_ABI_STABLE
const struct pldm_bios_attr_table_entry *
pldm_bios_table_attr_find_by_handle(const void *table, size_t length,
				    uint16_t handle)
{
	return pldm_bios_table_entry_find_from_table(table, length,
						     PLDM_BIOS_ATTR_TABLE,
						     attr_table_handle_equal,
						     &handle);
}

static bool attr_table_string_handle_equal(const void *entry, const void *key)
{
	uint16_t handle = *(uint16_t *)key;
	return pldm_bios_table_attr_entry_decode_string_handle(entry) == handle;
}

LIBPLDM_ABI_STABLE
const struct pldm_bios_attr_table_entry *
pldm_bios_table_attr_find_by_string_handle(const void *table, size_t length,
					   uint16_t handle)
{
	return pldm_bios_table_entry_find_from_table(
		table, length, PLDM_BIOS_ATTR_TABLE,
		attr_table_string_handle_equal, &handle);
}

static bool attr_value_table_handle_equal(const void *entry, const void *key)
{
	uint16_t handle = *(uint16_t *)key;
	return pldm_bios_table_attr_value_entry_decode_handle(entry) == handle;
}

LIBPLDM_ABI_STABLE
const struct pldm_bios_attr_val_table_entry *
pldm_bios_table_attr_value_find_by_handle(const void *table, size_t length,
					  uint16_t handle)
{
	return pldm_bios_table_entry_find_from_table(
		table, length, PLDM_BIOS_ATTR_VAL_TABLE,
		attr_value_table_handle_equal, &handle);
}

LIBPLDM_ABI_STABLE
int pldm_bios_table_attr_value_copy_and_update(
	const void *src_table, size_t src_length, void *dest_table,
	size_t *dest_length, const void *entry, size_t entry_length)
{
	struct pldm_bios_table_iter *iter = pldm_bios_table_iter_create(
		src_table, src_length, PLDM_BIOS_ATTR_VAL_TABLE);

	int rc = PLDM_SUCCESS;
	const struct pldm_bios_attr_val_table_entry *tmp;
	const struct pldm_bios_attr_val_table_entry *to_update = entry;
	size_t buffer_length = *dest_length;
	size_t copied_length = 0;
	size_t length = 0;
	while (!pldm_bios_table_iter_is_end(iter)) {
		tmp = pldm_bios_table_iter_attr_value_entry_value(iter);
		length = attr_value_table_entry_length(tmp);

		/* we need the tmp's entry_length here, iter_next will calculate
		 * it too, use current_pos directly to avoid calculating it
		 * twice */
		iter->current_pos += length;
		if (tmp->attr_handle == to_update->attr_handle) {
			if (tmp->attr_type != to_update->attr_type) {
				rc = PLDM_ERROR_INVALID_DATA;
				goto out;
			}
			length = entry_length;
			tmp = entry;
		}
		if (copied_length + length > buffer_length) {
			rc = PLDM_ERROR_INVALID_LENGTH;
			goto out;
		}
		memcpy((uint8_t *)dest_table + copied_length, tmp, length);
		copied_length += length;
	}

	size_t pad_checksum_size =
		pldm_bios_table_pad_checksum_size(copied_length);
	if ((pad_checksum_size + copied_length) > buffer_length) {
		rc = PLDM_ERROR_INVALID_LENGTH;
		goto out;
	}

	rc = pldm_bios_table_append_pad_checksum(dest_table, buffer_length,
						 &copied_length);
	if (rc == PLDM_SUCCESS) {
		*dest_length = copied_length;
	}
out:
	pldm_bios_table_iter_free(iter);
	return rc;
}

LIBPLDM_ABI_STABLE
bool pldm_bios_table_checksum(const uint8_t *table, size_t size)
{
	if (table == NULL) {
		return false;
	}

	// 12: BIOSStringHandle(uint16) + BIOSStringLength(uint16) +
	//     Variable(4) + checksum(uint32)
	if (size < 12) {
		return false;
	}

	uint32_t src_crc = le32toh(*(uint32_t *)(table + size - 4));
	uint32_t dst_crc = crc32(table, size - 4);

	return src_crc == dst_crc;
}
