/* Copyright (c) 2014 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.
 *
 * Tests for host library vboot2 key functions
 */

#include <stdio.h>
#include <unistd.h>

#include "2sysincludes.h"
#include "2common.h"
#include "2rsa.h"
#include "vb2_common.h"
#include "host_common.h"
#include "host_key2.h"
#include "host_signature2.h"
#include "test_common.h"

/* Test only the algorithms we use */
struct alg_combo {
	const char *name;
	enum vb2_signature_algorithm sig_alg;
	enum vb2_hash_algorithm hash_alg;
};

static const struct alg_combo test_algs[] = {
	{"RSA2048/SHA-256", VB2_SIG_RSA2048, VB2_HASH_SHA256},
	{"RSA4096/SHA-256", VB2_SIG_RSA4096, VB2_HASH_SHA256},
	{"RSA8192/SHA-512", VB2_SIG_RSA8192, VB2_HASH_SHA512},
};

const struct vb2_id test_id = {.raw = {0xaa}};
const char *test_desc = "The test key";
const char *test_sig_desc = "The test signature";
const uint8_t test_data[] = "Some test data";
const uint32_t test_size = sizeof(test_data);

static void sig_tests(const struct alg_combo *combo,
		      const char *pemfile,
		      const char *keybfile)
{
	struct vb2_private_key *prik, prik2;
	const struct vb2_private_key *prihash, *priks[2];
	struct vb2_public_key *pubk, pubhash;
	struct vb2_signature *sig, *sig2;
	uint32_t size;

	uint8_t workbuf[VB2_VERIFY_DATA_WORKBUF_BYTES]
		 __attribute__ ((aligned (VB2_WORKBUF_ALIGN)));
	struct vb2_workbuf wb;

	uint8_t *buf;
	uint32_t bufsize;
	struct vb2_struct_common *c;
	uint32_t c_sig_offs;

	vb2_workbuf_init(&wb, workbuf, sizeof(workbuf));

	/* Create test keys */
	/* TODO: should read these from .vbprik2, .vbpubk2 files */
	TEST_SUCC(vb2_private_key_read_pem(&prik, pemfile), "Read private key");
	prik->id = test_id;
	prik->hash_alg = combo->hash_alg;
	prik->sig_alg = combo->sig_alg;
	vb2_private_key_set_desc(prik, test_desc);

	TEST_SUCC(vb2_public_key_read_keyb(&pubk, keybfile), "Read pub key");
	pubk->id = &test_id;
	pubk->hash_alg = combo->hash_alg;
	vb2_public_key_set_desc(pubk, test_desc);

	TEST_SUCC(vb2_private_key_hash(&prihash, combo->hash_alg),
		  "Private hash key");
	TEST_SUCC(vb2_public_key_hash(&pubhash, combo->hash_alg),
		  "Public hash key");

	priks[0] = prik;
	priks[1] = prihash;

	/* Sign test data */
	TEST_SUCC(vb2_sign_data(&sig, test_data, test_size, prik, NULL),
		  "Sign good");
	TEST_PTR_NEQ(sig, NULL, "  sig_ptr");
	TEST_EQ(0, strcmp(vb2_common_desc(sig), test_desc), "  desc");
	TEST_EQ(0, memcmp(&sig->id, &test_id, sizeof(test_id)), "  id");
	TEST_EQ(sig->data_size, test_size, "  data_size");
	TEST_SUCC(vb2_sig_size_for_key(&size, prik, NULL), "Sig size");
	TEST_EQ(size, sig->c.total_size, "  size");
	TEST_SUCC(vb2_verify_data(test_data, test_size, sig, pubk, &wb),
		  "Verify good");
	free(sig);

	TEST_SUCC(vb2_sign_data(&sig, test_data, test_size, prik,
				test_sig_desc),
		  "Sign with desc");
	TEST_EQ(0, strcmp(vb2_common_desc(sig),	test_sig_desc), "  desc");
	free(sig);

	TEST_SUCC(vb2_sign_data(&sig, test_data, test_size, prik, ""),
		  "Sign with no desc");
	TEST_EQ(sig->c.desc_size, 0, "  desc");
	TEST_SUCC(vb2_sig_size_for_key(&size, prik, ""), "Sig size");
	TEST_EQ(size, sig->c.total_size, "  size");
	free(sig);

	TEST_SUCC(vb2_sign_data(&sig, test_data, test_size, prihash, NULL),
		  "Sign with hash");
	TEST_SUCC(vb2_verify_data(test_data, test_size, sig, &pubhash, &wb),
		  "Verify with hash");
	free(sig);

	prik2 = *prik;
	prik2.sig_alg = VB2_SIG_INVALID;
	TEST_EQ(vb2_sign_data(&sig, test_data, test_size, &prik2, NULL),
		VB2_SIGN_DATA_SIG_SIZE, "Sign bad sig alg");

	/* Sign an object with a little (24 bytes) data */
	c_sig_offs = sizeof(*c) + 24;
	TEST_SUCC(vb2_sig_size_for_key(&size, prik, NULL), "Sig size");
	bufsize = c_sig_offs + size;
	buf = calloc(1, bufsize);
	memset(buf + sizeof(*c), 0x12, 24);
	c = (struct vb2_struct_common *)buf;
	c->total_size = bufsize;

	TEST_SUCC(vb2_sign_object(buf, c_sig_offs, prik, NULL), "Sign object");
	sig = (struct vb2_signature *)(buf + c_sig_offs);
	TEST_SUCC(vb2_verify_data(buf, c_sig_offs, sig, pubk, &wb),
		  "Verify object");

	TEST_EQ(vb2_sign_object(buf, c_sig_offs + 4, prik, NULL),
		VB2_SIGN_OBJECT_OVERFLOW, "Sign object overflow");
	free(buf);

	/* Multiply sign an object */
	TEST_SUCC(vb2_sig_size_for_keys(&size, priks, 2), "Sigs size");
	bufsize = c_sig_offs + size;
	buf = calloc(1, bufsize);
	memset(buf + sizeof(*c), 0x12, 24);
	c = (struct vb2_struct_common *)buf;
	c->total_size = bufsize;

	TEST_SUCC(vb2_sign_object_multiple(buf, c_sig_offs, priks, 2),
		  "Sign multiple");
	sig = (struct vb2_signature *)(buf + c_sig_offs);
	TEST_SUCC(vb2_verify_data(buf, c_sig_offs, sig, pubk, &wb),
		  "Verify object with sig 1");
	sig2 = (struct vb2_signature *)(buf + c_sig_offs + sig->c.total_size);
	TEST_SUCC(vb2_verify_data(buf, c_sig_offs, sig2, &pubhash, &wb),
		  "Verify object with sig 2");

	c->total_size -= 4;
	TEST_EQ(vb2_sign_object_multiple(buf, c_sig_offs, priks, 2),
		VB2_SIGN_OBJECT_OVERFLOW, "Sign multple overflow");

	TEST_EQ(size, sig->c.total_size + sig2->c.total_size,
		"Sigs size total");

	free(buf);

	vb2_private_key_free(prik);
	vb2_public_key_free(pubk);
}

static int test_algorithm(const struct alg_combo *combo, const char *keys_dir)
{
	int rsa_bits = vb2_rsa_sig_size(combo->sig_alg) * 8;
	char pemfile[1024];
	char keybfile[1024];

	printf("***Testing algorithm: %s\n", combo->name);

	sprintf(pemfile, "%s/key_rsa%d.pem", keys_dir, rsa_bits);
	sprintf(keybfile, "%s/key_rsa%d.keyb", keys_dir, rsa_bits);

	sig_tests(combo, pemfile, keybfile);

	return 0;
}

int main(int argc, char *argv[]) {

	if (argc == 2) {
		int i;

		for (i = 0; i < ARRAY_SIZE(test_algs); i++) {
			if (test_algorithm(test_algs + i, argv[1]))
				return 1;
		}
	} else {
		fprintf(stderr, "Usage: %s <keys_dir>", argv[0]);
		return -1;
	}

	return gTestSuccess ? 0 : 255;
}
