// SPDX-License-Identifier: GPL-2.0-or-later
/*
 * Copyright (c) 2022, Linaro Limited
 */

#include <dm.h>
#include <efi.h>
#include <efi_loader.h>
#include <efi_variable.h>
#include <event.h>
#include <fwu.h>
#include <fwu_mdata.h>
#include <log.h>
#include <malloc.h>

#include <linux/errno.h>
#include <linux/types.h>

#include <u-boot/crc.h>

struct fwu_data g_fwu_data;
static struct udevice *g_dev;
static u8 in_trial;
static u8 boottime_check;

enum {
	IMAGE_ACCEPT_SET = 1,
	IMAGE_ACCEPT_CLEAR,
};

/**
 * fwu_bank_accepted() - Has the bank been accepted
 * @data: Version agnostic FWU metadata information
 * @bank: Update bank to check
 *
 * Check in the given bank if all the images have been accepted.
 *
 * Return: true if all images accepted, false otherwise
 */
bool fwu_bank_accepted(struct fwu_data *data, uint32_t bank)
{
	u32 i;
	struct fwu_image_entry *img_entry;
	struct fwu_image_bank_info *img_bank_info;

	img_entry = &data->fwu_images[0];
	for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) {
		img_bank_info = &img_entry[i].img_bank_info[bank];
		if (!img_bank_info->accepted)
			return false;
	}

	return true;
}

static int trial_counter_update(u16 *trial_state_ctr)
{
	bool delete;
	u32 var_attr;
	efi_status_t status;
	efi_uintn_t var_size;

	delete = !trial_state_ctr ? true : false;
	var_size = !trial_state_ctr ? 0 : (efi_uintn_t)sizeof(*trial_state_ctr);
	var_attr = !trial_state_ctr ? 0 : EFI_VARIABLE_NON_VOLATILE |
		EFI_VARIABLE_BOOTSERVICE_ACCESS;
	status = efi_set_variable_int(u"TrialStateCtr",
				      &efi_global_variable_guid,
				      var_attr,
				      var_size, trial_state_ctr, false);

	if ((delete && (status != EFI_NOT_FOUND &&
			status != EFI_SUCCESS)) ||
	    (!delete && status != EFI_SUCCESS))
		return -1;

	return 0;
}

static int trial_counter_read(u16 *trial_state_ctr)
{
	efi_status_t status;
	efi_uintn_t var_size;

	var_size = (efi_uintn_t)sizeof(trial_state_ctr);
	status = efi_get_variable_int(u"TrialStateCtr",
				      &efi_global_variable_guid,
				      NULL,
				      &var_size, trial_state_ctr,
				      NULL);
	if (status != EFI_SUCCESS) {
		log_err("Unable to read TrialStateCtr variable\n");
		return -1;
	}

	return 0;
}

static int fwu_trial_count_update(void)
{
	int ret;
	u16 trial_state_ctr;

	ret = trial_counter_read(&trial_state_ctr);
	if (ret) {
		log_debug("Unable to read trial_state_ctr\n");
		goto out;
	}

	++trial_state_ctr;
	if (trial_state_ctr > CONFIG_FWU_TRIAL_STATE_CNT) {
		log_info("Trial State count exceeded. Revert back to previous_active_index\n");
		ret = fwu_revert_boot_index();
		if (ret)
			log_err("Unable to revert active_index\n");

		trial_counter_update(NULL);
		ret = 1;
	} else {
		log_info("Trial State count: attempt %d out of %d\n",
			 trial_state_ctr, CONFIG_FWU_TRIAL_STATE_CNT);
		ret = trial_counter_update(&trial_state_ctr);
		if (ret)
			log_err("Unable to increment TrialStateCtr variable\n");
	}

out:
	return ret;
}

static u32 in_trial_state(void)
{
	return g_fwu_data.trial_state;
}

static int fwu_get_image_type_id(u8 image_index, efi_guid_t *image_type_id)
{
	int i;
	struct efi_fw_image *image;

	image = update_info.images;
	for (i = 0; i < update_info.num_images; i++) {
		if (image_index == image[i].image_index) {
			guidcpy(image_type_id, &image[i].image_type_id);
			return 0;
		}
	}

	return -ENOENT;
}

static int mdata_crc_check(struct fwu_mdata *mdata)
{
	int ret;
	u32 calc_crc32;
	uint32_t mdata_size;
	void *buf = &mdata->version;

	ret = fwu_get_mdata_size(&mdata_size);
	if (ret)
		return ret;

	calc_crc32 = crc32(0, buf, mdata_size - sizeof(u32));
	return calc_crc32 == mdata->crc32 ? 0 : -EINVAL;
}

static void fwu_data_crc_update(uint32_t crc32)
{
	g_fwu_data.crc32 = crc32;
}

/**
 * fwu_get_data() - Return the version agnostic FWU structure
 *
 * Return the pointer to the version agnostic FWU structure.
 *
 * Return: Pointer to the FWU data structure
 */
struct fwu_data *fwu_get_data(void)
{
	return &g_fwu_data;
}

static void fwu_populate_mdata_bank_index(struct fwu_data *fwu_data)
{
	struct fwu_mdata *mdata = fwu_data->fwu_mdata;

	mdata->active_index = fwu_data->active_index;
	mdata->previous_active_index = fwu_data->previous_active_index;
}

/**
 * fwu_get_dev() - Return the FWU metadata device
 *
 * Return the pointer to the FWU metadata device.
 *
 * Return: Pointer to the FWU metadata dev
 */
struct udevice *fwu_get_dev(void)
{
	return g_dev;
}

/**
 * fwu_sync_mdata() - Update given meta-data partition(s) with the copy provided
 * @data: FWU Data structure
 * @part: Bitmask of FWU metadata partitions to be written to
 *
 * Return: 0 if OK, -ve on error
 */
int fwu_sync_mdata(struct fwu_mdata *mdata, int part)
{
	int err;
	uint mdata_size;
	void *buf = &mdata->version;

	if (part == BOTH_PARTS) {
		err = fwu_sync_mdata(mdata, SECONDARY_PART);
		if (err)
			return err;
		part = PRIMARY_PART;
	}

	err = fwu_get_mdata_size(&mdata_size);
	if (err)
		return err;

	/*
	 * Calculate the crc32 for the updated FWU metadata
	 * and put the updated value in the FWU metadata crc32
	 * field
	 */
	mdata->crc32 = crc32(0, buf, mdata_size - sizeof(u32));
	fwu_data_crc_update(mdata->crc32);

	err = fwu_write_mdata(g_dev, mdata, part == PRIMARY_PART, mdata_size);
	if (err) {
		log_err("Unable to write %s mdata\n",
			part == PRIMARY_PART ?  "primary" : "secondary");
		return err;
	}

	return 0;
}

/**
 * fwu_mdata_copies_allocate() - Allocate memory for metadata
 * @mdata_size: Size of the metadata structure
 *
 * Allocate memory for storing both the copies of the FWU metadata. The
 * copies are then used as a cache for storing FWU metadata contents.
 *
 * Return: 0 if OK, -ve on error
 */
int fwu_mdata_copies_allocate(u32 mdata_size)
{
	if (g_fwu_data.fwu_mdata)
		return 0;

	/*
	 * Allocate the total memory that would be needed for both
	 * the copies.
	 */
	g_fwu_data.fwu_mdata = calloc(2, mdata_size);
	if (!g_fwu_data.fwu_mdata) {
		log_err("Unable to allocate space for FWU metadata\n");
		return -ENOMEM;
	}

	return 0;
}

/**
 * fwu_get_mdata() - Read, verify and return the FWU metadata
 * @mdata: Output FWU metadata read or NULL
 *
 * Read both the metadata copies from the storage media, verify their checksum,
 * and ascertain that both copies match. If one of the copies has gone bad,
 * restore it from the good copy.
 *
 * Return: 0 if OK, -ve on error
 */
int fwu_get_mdata(struct fwu_mdata *mdata)
{
	int err;
	uint32_t mdata_size;
	bool parts_ok[2] = { false };
	struct fwu_mdata *parts_mdata[2];

	err = fwu_get_mdata_size(&mdata_size);
	if (err)
		return err;

	parts_mdata[0] = g_fwu_data.fwu_mdata;
	if (!parts_mdata[0]) {
		log_err("Memory not allocated for the FWU Metadata copies\n");
		return -ENOMEM;
	}

	parts_mdata[1] = (struct fwu_mdata *)((char *)parts_mdata[0] +
					      mdata_size);

	/* if mdata already read and ready */
	err = mdata_crc_check(parts_mdata[0]);
	if (!err)
		goto ret_mdata;

	/* else read, verify and, if needed, fix mdata */
	for (int i = 0; i < 2; i++) {
		parts_ok[i] = false;
		err = fwu_read_mdata(g_dev, parts_mdata[i], !i, mdata_size);
		if (!err) {
			err = mdata_crc_check(parts_mdata[i]);
			if (!err)
				parts_ok[i] = true;
			else
				log_debug("mdata : %s crc32 failed\n", i ? "secondary" : "primary");
		}
	}

	if (parts_ok[0] && parts_ok[1]) {
		/*
		 * Before returning, check that both the
		 * FWU metadata copies are the same.
		 */
		err = memcmp(parts_mdata[0], parts_mdata[1], mdata_size);
		if (!err)
			goto ret_mdata;

		/*
		 * If not, populate the secondary partition from the
		 * primary partition copy.
		 */
		log_info("Both FWU metadata copies are valid but do not match.");
		log_info(" Restoring the secondary partition from the primary\n");
		parts_ok[1] = false;
	}

	for (int i = 0; i < 2; i++) {
		if (parts_ok[i])
			continue;

		memcpy(parts_mdata[i], parts_mdata[1 - i], mdata_size);
		err = fwu_sync_mdata(parts_mdata[i], i ? SECONDARY_PART : PRIMARY_PART);
		if (err) {
			log_debug("mdata : %s write failed\n", i ? "secondary" : "primary");
			return err;
		}
	}

ret_mdata:
	if (!err && mdata)
		memcpy(mdata, parts_mdata[0], mdata_size);

	return err;
}

/**
 * fwu_get_active_index() - Get active_index from the FWU metadata
 * @active_idx: active_index value to be read
 *
 * Read the active_index field from the FWU metadata and place it in
 * the variable pointed to be the function argument.
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_get_active_index(uint *active_idx)
{
	int ret = 0;
	struct fwu_data *data = &g_fwu_data;

	/*
	 * Found the FWU metadata partition, now read the active_index
	 * value
	 */
	*active_idx = data->active_index;
	if (*active_idx >= CONFIG_FWU_NUM_BANKS) {
		log_debug("Active index value read is incorrect\n");
		ret = -EINVAL;
	}

	return ret;
}

/**
 * fwu_set_active_index() - Set active_index in the FWU metadata
 * @active_idx: active_index value to be set
 *
 * Update the active_index field in the FWU metadata
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_set_active_index(uint active_idx)
{
	int ret;
	struct fwu_data *data =  &g_fwu_data;

	if (active_idx >= CONFIG_FWU_NUM_BANKS) {
		log_debug("Invalid active index value\n");
		return -EINVAL;
	}

	/*
	 * Update the active index and previous_active_index fields
	 * in the FWU metadata
	 */
	data->previous_active_index = data->active_index;
	data->active_index = active_idx;

	fwu_populate_mdata_bank_index(data);

	/*
	 * Now write this updated FWU metadata to both the
	 * FWU metadata partitions
	 */
	ret = fwu_sync_mdata(data->fwu_mdata, BOTH_PARTS);
	if (ret) {
		log_debug("Failed to update FWU metadata partitions\n");
		ret = -EIO;
	}

	return ret;
}

/**
 * fwu_get_dfu_alt_num() - Get the dfu_alt_num to be used for capsule update
 * @image_index:	The Image Index for the image
 * @alt_num:		pointer to store dfu_alt_num
 *
 * Currently, the capsule update driver uses the DFU framework for
 * the updates. This function gets the DFU alt number which is to
 * be used for capsule update.
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_get_dfu_alt_num(u8 image_index, u8 *alt_num)
{
	int ret, i;
	uint update_bank;
	efi_guid_t *image_guid, image_type_id;
	struct fwu_data *data = &g_fwu_data;
	struct fwu_image_entry *img_entry;
	struct fwu_image_bank_info *img_bank_info;

	ret = fwu_plat_get_update_index(&update_bank);
	if (ret) {
		log_debug("Failed to get the FWU update bank\n");
		goto out;
	}

	ret = fwu_get_image_type_id(image_index, &image_type_id);
	if (ret) {
		log_debug("Unable to get image_type_id for image_index %u\n",
			  image_index);
		goto out;
	}

	ret = -EINVAL;
	/*
	 * The FWU metadata has been read. Now get the image_guid for the
	 * image with the update_bank.
	 */
	for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) {
		if (!guidcmp(&image_type_id,
			     &data->fwu_images[i].image_type_guid)) {
			img_entry = &data->fwu_images[i];
			img_bank_info = &img_entry->img_bank_info[update_bank];
			image_guid = &img_bank_info->image_guid;
			ret = fwu_plat_get_alt_num(g_dev, image_guid, alt_num);
			if (ret)
				log_debug("alt_num not found for partition with GUID %pUs\n",
					  image_guid);
			else
				log_debug("alt_num %d for partition %pUs\n",
					  *alt_num, image_guid);

			goto out;
		}
	}

	log_err("Partition with the image type %pUs not found\n",
		&image_type_id);

out:
	return ret;
}

/**
 * fwu_revert_boot_index() - Revert the active index in the FWU metadata
 *
 * Revert the active_index value in the FWU metadata, by swapping the values
 * of active_index and previous_active_index in both copies of the
 * FWU metadata.
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_revert_boot_index(void)
{
	int ret;
	u32 cur_active_index;
	struct fwu_data *data =  &g_fwu_data;

	/*
	 * Swap the active index and previous_active_index fields
	 * in the FWU metadata
	 */
	cur_active_index = data->active_index;
	data->active_index = data->previous_active_index;
	data->previous_active_index = cur_active_index;

	fwu_populate_mdata_bank_index(data);

	/*
	 * Now write this updated FWU metadata to both the
	 * FWU metadata partitions
	 */
	ret = fwu_sync_mdata(data->fwu_mdata, BOTH_PARTS);
	if (ret) {
		log_debug("Failed to update FWU metadata partitions\n");
		ret = -EIO;
	}

	return ret;
}

/**
 * fwu_clrset_image_accept() - Set or Clear the Acceptance bit for the image
 * @img_type_id: GUID of the image type for which the accepted bit is to be
 *               set or cleared
 * @bank: Bank of which the image's Accept bit is to be set or cleared
 * @action: Action which specifies whether image's Accept bit is to be set or
 *          cleared
 *
 * Set/Clear the accepted bit for the image specified by the img_guid parameter.
 * This indicates acceptance or rejection of image for subsequent boots by some
 * governing component like OS(or firmware).
 *
 * Return: 0 if OK, -ve on error
 *
 */
static int fwu_clrset_image_accept(efi_guid_t *img_type_id, u32 bank, u8 action)
{
	int ret, i;
	struct fwu_data *data = &g_fwu_data;
	struct fwu_image_entry *img_entry;
	struct fwu_image_bank_info *img_bank_info;

	img_entry = &data->fwu_images[0];
	for (i = 0; i < CONFIG_FWU_NUM_IMAGES_PER_BANK; i++) {
		if (!guidcmp(&img_entry[i].image_type_guid, img_type_id)) {
			img_bank_info = &img_entry[i].img_bank_info[bank];
			if (action == IMAGE_ACCEPT_SET)
				img_bank_info->accepted |= FWU_IMAGE_ACCEPTED;
			else
				img_bank_info->accepted = 0;

			fwu_populate_mdata_image_info(data);
			ret = fwu_sync_mdata(data->fwu_mdata, BOTH_PARTS);
			goto out;
		}
	}

	/* Image not found */
	ret = -ENOENT;

out:
	return ret;
}

/**
 * fwu_accept_image() - Set the Acceptance bit for the image
 * @img_type_id: GUID of the image type for which the accepted bit is to be
 *               cleared
 * @bank: Bank of which the image's Accept bit is to be set
 *
 * Set the accepted bit for the image specified by the img_guid parameter. This
 * indicates acceptance of image for subsequent boots by some governing component
 * like OS(or firmware).
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_accept_image(efi_guid_t *img_type_id, u32 bank)
{
	return fwu_clrset_image_accept(img_type_id, bank,
				       IMAGE_ACCEPT_SET);
}

/**
 * fwu_clear_accept_image() - Clear the Acceptance bit for the image
 * @img_type_id: GUID of the image type for which the accepted bit is to be
 *               cleared
 * @bank: Bank of which the image's Accept bit is to be cleared
 *
 * Clear the accepted bit for the image type specified by the img_type_id parameter.
 * This function is called after the image has been updated. The accepted bit is
 * cleared to be set subsequently after passing the image acceptance criteria, by
 * either the OS(or firmware)
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_clear_accept_image(efi_guid_t *img_type_id, u32 bank)
{
	return fwu_clrset_image_accept(img_type_id, bank,
				       IMAGE_ACCEPT_CLEAR);
}

/**
 * fwu_plat_get_update_index() - Get the value of the update bank
 * @update_idx: Bank number to which images are to be updated
 *
 * Get the value of the bank(partition) to which the update needs to be
 * made.
 *
 * Note: This is a weak function and platforms can override this with
 * their own implementation for selection of the update bank.
 *
 * Return: 0 if OK, -ve on error
 *
 */
__weak int fwu_plat_get_update_index(uint *update_idx)
{
	int ret;
	u32 active_idx;

	ret = fwu_get_active_index(&active_idx);
	if (ret < 0)
		return -1;

	*update_idx = (active_idx + 1) % CONFIG_FWU_NUM_BANKS;

	return ret;
}

/**
 * fwu_plat_get_bootidx() - Get the value of the boot index
 * @boot_idx: Boot index value
 *
 * Get the value of the bank(partition) from which the platform
 * has booted. This value is passed to U-Boot from the earlier
 * stage bootloader which loads and boots all the relevant
 * firmware images
 */
__weak void fwu_plat_get_bootidx(uint *boot_idx)
{
	int ret;

	ret = fwu_get_active_index(boot_idx);
	if (ret < 0)
		*boot_idx = 0; /* Dummy value */
}

/**
 * fwu_update_checks_pass() - Check if FWU update can be done
 *
 * Check if the FWU update can be executed. The updates are
 * allowed only when the platform is not in Trial State and
 * the boot time checks have passed
 *
 * Return: 1 if OK, 0 if checks do not pass
 *
 */
u8 fwu_update_checks_pass(void)
{
	return !in_trial && boottime_check;
}

/**
 * fwu_empty_capsule_checks_pass() - Check if empty capsule can be processed
 *
 * Check if the empty capsule can be processed to either accept or revert
 * an earlier executed update. The empty capsules need to be processed
 * only when the platform is in Trial State and the boot time checks have
 * passed
 *
 * Return: 1 if OK, 0 if not to be allowed
 *
 */
u8 fwu_empty_capsule_checks_pass(void)
{
	return in_trial && boottime_check;
}

/**
 * fwu_trial_state_ctr_start() - Start the Trial State counter
 *
 * Start the counter to identify the platform booting in the
 * Trial State. The counter is implemented as an EFI variable.
 *
 * Return: 0 if OK, -ve on error
 *
 */
int fwu_trial_state_ctr_start(void)
{
	int ret;
	u16 trial_state_ctr;

	trial_state_ctr = 0;
	ret = trial_counter_update(&trial_state_ctr);
	if (ret)
		log_err("Unable to initialise TrialStateCtr\n");

	return ret;
}

static int fwu_boottime_checks(void)
{
	int ret;
	u32 boot_idx, active_idx;

	ret = uclass_first_device_err(UCLASS_FWU_MDATA, &g_dev);
	if (ret) {
		log_debug("Cannot find fwu device\n");
		return ret;
	}

	/* Don't have boot time checks on sandbox */
	if (IS_ENABLED(CONFIG_SANDBOX)) {
		boottime_check = 1;
		return 0;
	}

	ret = fwu_init();
	if (ret) {
		log_debug("fwu_init() failed\n");
		return ret;
	}

	/*
	 * Get the Boot Index, i.e. the bank from
	 * which the platform has booted. This value
	 * gets passed from the ealier stage bootloader
	 * which booted u-boot, e.g. tf-a. If the
	 * boot index is not the same as the
	 * active_index read from the FWU metadata,
	 * update the active_index.
	 */
	fwu_plat_get_bootidx(&boot_idx);
	if (boot_idx >= CONFIG_FWU_NUM_BANKS) {
		log_err("Received incorrect value of boot_index\n");
		return 0;
	}

	ret = fwu_get_active_index(&active_idx);
	if (ret) {
		log_err("Unable to read active_index\n");
		return 0;
	}

	if (boot_idx != active_idx) {
		log_info("Boot idx %u is not matching active idx %u, changing active_idx\n",
			 boot_idx, active_idx);
		ret = fwu_set_active_index(boot_idx);
		if (!ret)
			boottime_check = 1;
	}

	if (efi_init_obj_list() != EFI_SUCCESS)
		return 0;

	in_trial = in_trial_state();

	ret = in_trial ? fwu_trial_count_update() : trial_counter_update(NULL);

	if (!ret)
		boottime_check = 1;

	return 0;
}
EVENT_SPY_SIMPLE(EVT_MAIN_LOOP, fwu_boottime_checks);
