/* Copyright (c) 2013 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.
 *
 * Host functions for verified boot.
 */

#include <string.h>

#include "2common.h"
#include "2rsa.h"
#include "2sysincludes.h"
#include "host_common.h"
#include "host_key21.h"

struct vb2_fw_preamble *vb2_create_fw_preamble(
	uint32_t firmware_version,
	const struct vb2_packed_key *kernel_subkey,
	const struct vb2_signature *body_signature,
	const struct vb2_private_key *signing_key,
	uint32_t flags)
{
	uint32_t signed_size = (sizeof(struct vb2_fw_preamble) +
				kernel_subkey->key_size +
				body_signature->sig_size);
	uint32_t block_size = signed_size +
		vb2_rsa_sig_size(signing_key->sig_alg);

	/* Allocate keyblock */
	struct vb2_fw_preamble *h =
		(struct vb2_fw_preamble *)calloc(block_size, 1);
	if (!h)
		return NULL;

	uint8_t *kernel_subkey_dest = (uint8_t *)(h + 1);
	uint8_t *body_sig_dest = kernel_subkey_dest + kernel_subkey->key_size;
	uint8_t *block_sig_dest = body_sig_dest + body_signature->sig_size;

	h->header_version_major = VB2_FIRMWARE_PREAMBLE_HEADER_VERSION_MAJOR;
	h->header_version_minor = VB2_FIRMWARE_PREAMBLE_HEADER_VERSION_MINOR;
	h->preamble_size = block_size;
	h->firmware_version = firmware_version;
	h->flags = flags;

	/* Copy data key */
	vb2_init_packed_key(&h->kernel_subkey, kernel_subkey_dest,
			    kernel_subkey->key_size);
	if (VB2_SUCCESS !=
	    vb2_copy_packed_key(&h->kernel_subkey, kernel_subkey)) {
		free(h);
		return NULL;
	}

	/* Copy body signature */
	vb2_init_signature(&h->body_signature,
			   body_sig_dest, body_signature->sig_size, 0);
	if (VB2_SUCCESS !=
	    vb2_copy_signature(&h->body_signature, body_signature)) {
		free(h);
		return NULL;
	}

	/* Set up signature struct so we can calculate the signature */
	vb2_init_signature(&h->preamble_signature, block_sig_dest,
			   vb2_rsa_sig_size(signing_key->sig_alg), signed_size);

	/* Calculate signature */
	struct vb2_signature *sig =
		vb2_calculate_signature((uint8_t *)h, signed_size, signing_key);
	vb2_copy_signature(&h->preamble_signature, sig);
	free(sig);

	/* Return the header */
	return h;
}

struct vb2_kernel_preamble *vb2_create_kernel_preamble(
	uint32_t kernel_version,
	uint64_t body_load_address,
	uint64_t bootloader_address,
	uint32_t bootloader_size,
	const struct vb2_signature *body_signature,
	uint64_t vmlinuz_header_address,
	uint32_t vmlinuz_header_size,
	uint32_t flags,
	uint32_t desired_size,
	const struct vb2_private_key *signing_key)
{
	uint64_t signed_size = (sizeof(struct vb2_kernel_preamble) +
				body_signature->sig_size);
	uint32_t sig_size = vb2_rsa_sig_size(signing_key->sig_alg);
	uint32_t block_size = signed_size + sig_size;

	/* If the block size is smaller than the desired size, pad it */
	if (block_size < desired_size)
		block_size = desired_size;

	/* Allocate keyblock */
	struct vb2_kernel_preamble *h =
		(struct vb2_kernel_preamble *)calloc(block_size, 1);
	if (!h)
		return NULL;

	uint8_t *body_sig_dest = (uint8_t *)(h + 1);
	uint8_t *block_sig_dest = body_sig_dest + body_signature->sig_size;

	h->header_version_major = VB2_KERNEL_PREAMBLE_HEADER_VERSION_MAJOR;
	h->header_version_minor = VB2_KERNEL_PREAMBLE_HEADER_VERSION_MINOR;
	h->preamble_size = block_size;
	h->kernel_version = kernel_version;
	h->body_load_address = body_load_address;
	h->bootloader_address = bootloader_address;
	h->bootloader_size = bootloader_size;
	h->vmlinuz_header_address = vmlinuz_header_address;
	h->vmlinuz_header_size = vmlinuz_header_size;
	h->flags = flags;

	/* Copy body signature */
	vb2_init_signature(&h->body_signature, body_sig_dest,
			   body_signature->sig_size, 0);
	vb2_copy_signature(&h->body_signature, body_signature);

	/* Set up signature struct so we can calculate the signature */
	vb2_init_signature(&h->preamble_signature, block_sig_dest,
			   sig_size, signed_size);

	/* Calculate signature */
	struct vb2_signature *sigtmp =
		vb2_calculate_signature((uint8_t *)h, signed_size, signing_key);
	vb2_copy_signature(&h->preamble_signature, sigtmp);
	free(sigtmp);

	/* Return the header */
	return h;
}

void vb2_kernel_get_vmlinuz_header(const struct vb2_kernel_preamble *preamble,
				   uint64_t *vmlinuz_header_address,
				   uint32_t *vmlinuz_header_size)
{
	if (preamble->header_version_minor < 1) {
		*vmlinuz_header_address = 0;
		*vmlinuz_header_size = 0;
	} else {
		/*
		 * Set header and size only if the preamble header version is >
		 * 2.1 as they don't exist in version 2.0 (Note that we don't
		 * need to check header_version_major; if that's not 2 then
		 * vb2_verify_kernel_preamble() would have already failed.
		 */
		*vmlinuz_header_address = preamble->vmlinuz_header_address;
		*vmlinuz_header_size = preamble->vmlinuz_header_size;
	}
}
