/*
 * Copyright 2018 The Chromium OS Authors. All rights reserved.
 * Use of this source code is governed by a BSD-style license that can be
 * found in the LICENSE file.
 *
 * The board-specific quirks needed by firmware updater.
 */

#include <assert.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>

#include "futility.h"
#include "host_misc.h"
#include "updater.h"

struct quirks_record {
	const char * const match;
	const char * const quirks;
};

static const struct quirks_record quirks_records[] = {
	{ .match = "Google_Whirlwind.", .quirks = "enlarge_image" },
	{ .match = "Google_Arkham.", .quirks = "enlarge_image" },
	{ .match = "Google_Storm.", .quirks = "enlarge_image" },
	{ .match = "Google_Gale.", .quirks = "enlarge_image" },

	{ .match = "Google_Chell.", .quirks = "unlock_me_for_update" },
	{ .match = "Google_Lars.", .quirks = "unlock_me_for_update" },
	{ .match = "Google_Sentry.", .quirks = "unlock_me_for_update" },
	{ .match = "Google_Asuka.", .quirks = "unlock_me_for_update" },
	{ .match = "Google_Caroline.", .quirks = "unlock_me_for_update" },
	{ .match = "Google_Cave.", .quirks = "unlock_me_for_update" },

	{ .match = "Google_Eve.",
	  .quirks = "unlock_me_for_update,eve_smm_store" },

	{ .match = "Google_Poppy.", .quirks = "min_platform_version=6" },
	{ .match = "Google_Scarlet.", .quirks = "min_platform_version=1" },

	{ .match = "Google_Snow.", .quirks = "daisy_snow_dual_model" },
};

/*
 * Helper function to write a firmware image into file on disk.
 * Returns the result from vb2_write_file.
 */
static int write_image(const char *file_path, struct firmware_image *image)
{
	return vb2_write_file(file_path, image->data, image->size);
}

/* Preserves meta data and reload image contents from given file path. */
static int reload_firmware_image(const char *file_path,
				 struct firmware_image *image)
{
	free_firmware_image(image);
	return load_firmware_image(image, file_path, NULL);
}

/*
 * Quirk to enlarge a firmware image to match flash size. This is needed by
 * devices using multiple SPI flash with different sizes, for example 8M and
 * 16M. The image_to will be padded with 0xFF using the size of image_from.
 * Returns 0 on success, otherwise failure.
 */
static int quirk_enlarge_image(struct updater_config *cfg)
{
	struct firmware_image *image_from = &cfg->image_current,
			      *image_to = &cfg->image;
	const char *tmp_path;
	size_t to_write;
	FILE *fp;

	if (image_from->size <= image_to->size)
		return 0;

	tmp_path = updater_create_temp_file(cfg);
	if (!tmp_path)
		return -1;

	DEBUG("Resize image from %u to %u.", image_to->size, image_from->size);
	to_write = image_from->size - image_to->size;
	write_image(tmp_path, image_to);
	fp = fopen(tmp_path, "ab");
	if (!fp) {
		ERROR("Cannot open temporary file %s.", tmp_path);
		return -1;
	}
	while (to_write-- > 0)
		fputc('\xff', fp);
	fclose(fp);
	return reload_firmware_image(tmp_path, image_to);
}

/*
 * Quirk to unlock a firmware image with SI_ME (management engine) when updating
 * so the system has a chance to make sure SI_ME won't be corrupted on next boot
 * before locking the Flash Master values in SI_DESC.
 * Returns 0 on success, otherwise failure.
 */
static int quirk_unlock_me_for_update(struct updater_config *cfg)
{
	struct firmware_section section;
	struct firmware_image *image_to = &cfg->image;
	const int flash_master_offset = 128;
	const uint8_t flash_master[] = {
		0x00, 0xff, 0xff, 0xff, 0x00, 0xff, 0xff, 0xff, 0x00, 0xff,
		0xff, 0xff
	};

	find_firmware_section(&section, image_to, FMAP_SI_DESC);
	if (section.size < flash_master_offset + ARRAY_SIZE(flash_master))
		return 0;
	if (memcmp(section.data + flash_master_offset, flash_master,
		   ARRAY_SIZE(flash_master)) == 0) {
		DEBUG("Target ME not locked.");
		return 0;
	}
	/*
	 * b/35568719: We should only update with unlocked ME and let
	 * board-postinst lock it.
	 */
	printf("%s: Changed Flash Master Values to unlocked.\n", __FUNCTION__);
	memcpy(section.data + flash_master_offset, flash_master,
	       ARRAY_SIZE(flash_master));
	return 0;
}

/*
 * Checks and returns 0 if the platform version of current system is larger
 * or equal to given number, otherwise non-zero.
 */
static int quirk_min_platform_version(struct updater_config *cfg)
{
	int min_version = get_config_quirk(QUIRK_MIN_PLATFORM_VERSION, cfg);
	int platform_version = get_system_property(SYS_PROP_PLATFORM_VER, cfg);

	DEBUG("Minimum required version=%d, current platform version=%d",
	      min_version, platform_version);

	if (platform_version >= min_version)
		return 0;
	ERROR("Need platform version >= %d (current is %d). "
	      "This firmware will only run on newer systems.",
	      min_version, platform_version);
	return -1;
}

/*
 * Adjust firmware image according to running platform version.
 * Returns 0 if success, non-zero if error.
 */
static int quirk_daisy_snow_dual_model(struct updater_config *cfg)
{
	/*
	 * The daisy-snow firmware should be packed as RO, RW_A=x16, RW_B=x8.
	 * RO update for x8 and RO EC update for all are no longer supported.
	 */
	struct firmware_section a, b;
	int i, is_x8 = 0, is_x16 = 0;
	const char * const x8_versions[] = {
		"DVT",
		"PVT",
		"PVT2",
		"MP",
	};
	const char * const x16_versions[] = {
		"MPx16",  /* Rev 4 */
		"MP2",  /* Rev 5 */
	};
	char *platform_version = host_shell("mosys platform version");

	for (i = 0; i < ARRAY_SIZE(x8_versions) && !is_x8; i++) {
		if (strcmp(x8_versions[i], platform_version) == 0)
			is_x8 = 1;
	}
	for (i = 0; i < ARRAY_SIZE(x16_versions) && !is_x8 && !is_x16; i++) {
		if (strcmp(x16_versions[i], platform_version) == 0)
			is_x16 = 1;
	}
	printf("%s: Platform version: %s (original value: %s)\n", __FUNCTION__,
	      is_x8 ? "x8" : is_x16 ? "x16": "unknown", platform_version);
	free(platform_version);

	find_firmware_section(&a, &cfg->image, FMAP_RW_SECTION_A);
	find_firmware_section(&b, &cfg->image, FMAP_RW_SECTION_B);

	if (cfg->ec_image.data) {
		ERROR("EC RO update is not supported with this quirk.");
		return -1;
	}
	if (!a.data || !b.data || a.size != b.size) {
		ERROR("Invalid firmware image: %s", cfg->image.file_name);
		return -1;
	}
	if (memcmp(a.data, b.data, a.size) == 0) {
		ERROR("Input image must have both x8 and x16 firmware.");
		return -1;
	}

	if (is_x16) {
		memmove(b.data, a.data, a.size);
		free(cfg->image.rw_version_b);
		cfg->image.rw_version_b = strdup(cfg->image.rw_version_a);
	} else if (is_x8) {
		memmove(a.data, b.data, b.size);
		free(cfg->image.rw_version_a);
		cfg->image.rw_version_a = strdup(cfg->image.rw_version_b);
		/* Need to use RO from current system. */
		if (!cfg->image_current.data &&
		    load_system_firmware(cfg, &cfg->image_current) != 0) {
			ERROR("Cannot get system RO contents");
			return -1;
		}
		preserve_firmware_section(&cfg->image_current, &cfg->image,
					  FMAP_RO_SECTION);
	} else {
		ERROR("Unknown platform, cannot update.");
		return -1;
	}
	return 0;
}

/*
 * Extracts files from a CBFS on given region (section) of image_file.
 * Returns the path to a temporary file on success, otherwise NULL.
 */
static const char *extract_cbfs_file(struct updater_config *cfg,
				     const char *image_file,
				     const char *cbfs_region,
				     const char *cbfs_name)
{
	const char *output = updater_create_temp_file(cfg);
	char *command, *result;

	ASPRINTF(&command, "cbfstool \"%s\" extract -r %s -n \"%s\" "
		 "-f \"%s\" 2>&1", image_file, cbfs_region,
		 cbfs_name, output);

	result = host_shell(command);
	free(command);

	if (!*result)
		output = NULL;

	free(result);
	return output;
}

/*
 * Quirk to help preserving SMM store on devices without a dedicated "SMMSTORE"
 * FMAP section. These devices will store "smm store" file in same CBFS where
 * the legacy boot loader lives (i.e, FMAP RW_LEGACY).
 * Note this currently has dependency on external program "cbstool".
 * Returns 0 if the SMM store is properly preserved, or if the system is not
 * available to do that (problem in cbfstool, or no "smm store" in current
 * system firmware). Otherwise non-zero as failure.
 */
static int quirk_eve_smm_store(struct updater_config *cfg)
{
	const char *smm_store_name = "smm store";
	const char *temp_image = updater_create_temp_file(cfg);
	const char *old_store;
	char *command;

	if (write_image(temp_image, &cfg->image_current) != VBERROR_SUCCESS)
		return -1;

	old_store = extract_cbfs_file(cfg, temp_image, FMAP_RW_LEGACY,
				      smm_store_name);
	if (!old_store) {
		DEBUG("cbfstool failure or SMM store not available. "
		      "Don't preserve.");
		return 0;
	}

	/* Reuse temp_image. */
	if (write_image(temp_image, &cfg->image) != VBERROR_SUCCESS)
		return -1;

	/* crosreview.com/1165109: The offset is fixed at 0x1bf000. */
	ASPRINTF(&command,
		 "cbfstool \"%s\" remove -r %s -n \"%s\" 2>/dev/null; "
		 "cbfstool \"%s\" add -r %s -n \"%s\" -f \"%s\" "
		 " -t raw -b 0x1bf000", temp_image, FMAP_RW_LEGACY,
		 smm_store_name, temp_image, FMAP_RW_LEGACY,
		 smm_store_name, old_store);
	host_shell(command);
	free(command);

	return reload_firmware_image(temp_image, &cfg->image);
}

/*
 * Registers known quirks to a updater_config object.
 */
void updater_register_quirks(struct updater_config *cfg)
{
	struct quirk_entry *quirks;

	assert(ARRAY_SIZE(cfg->quirks) == QUIRK_MAX);
	quirks = &cfg->quirks[QUIRK_ENLARGE_IMAGE];
	quirks->name = "enlarge_image";
	quirks->help = "Enlarge firmware image by flash size.";
	quirks->apply = quirk_enlarge_image;

	quirks = &cfg->quirks[QUIRK_MIN_PLATFORM_VERSION];
	quirks->name = "min_platform_version";
	quirks->help = "Minimum compatible platform version "
			"(also known as Board ID version).";
	quirks->apply = quirk_min_platform_version;

	quirks = &cfg->quirks[QUIRK_UNLOCK_ME_FOR_UPDATE];
	quirks->name = "unlock_me_for_update";
	quirks->help = "b/35568719; only lock management engine in "
			"board-postinst.";
	quirks->apply = quirk_unlock_me_for_update;

	quirks = &cfg->quirks[QUIRK_DAISY_SNOW_DUAL_MODEL];
	quirks->name = "daisy_snow_dual_model";
	quirks->help = "b/35525858; needs an image RW A=[model x16], B=x8.";
	quirks->apply = quirk_daisy_snow_dual_model;

	quirks = &cfg->quirks[QUIRK_EVE_SMM_STORE];
	quirks->name = "eve_smm_store";
	quirks->help = "b/70682365; preserve UEFI SMM store without "
		       "dedicated FMAP section.";
	quirks->apply = quirk_eve_smm_store;
}

/*
 * Gets the default quirk config string for target image.
 * Returns a string (in same format as --quirks) to load or NULL if no quirks.
 */
const char * const updater_get_default_quirks(struct updater_config *cfg)
{
	const char *pattern = cfg->image.ro_version;
	int i;

	if (!pattern) {
		DEBUG("Cannot identify system for default quirks.");
		return NULL;
	}

	for (i = 0; i < ARRAY_SIZE(quirks_records); i++) {
		const struct quirks_record *r = &quirks_records[i];
		if (strncmp(r->match, pattern, strlen(r->match)) != 0)
		    continue;
		DEBUG("Found system default quirks: %s", r->quirks);
		return r->quirks;
	}
	return NULL;
}
