/*
 * Copyright 2017 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.
 */

#include <asm/byteorder.h>
#include <endian.h>
#include <fcntl.h>
#include <getopt.h>
#include <libusb.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>

#include <fmap.h>

#ifndef __packed
#define __packed __attribute__((packed))
#endif

#include "compile_time_macros.h"
#include "misc_util.h"
#include "usb_descriptor.h"
#include "update_fw.h"
#include "vb21_struct.h"

#ifdef DEBUG
#define debug printf
#else
#define debug(fmt, args...)
#endif

/*
 * This file contains the source code of a Linux application used to update
 * EC device firmware (common code only, gsctool takes care of cr50).
 */

#define VID USB_VID_GOOGLE
#define PID 0x5022
#define SUBCLASS USB_SUBCLASS_GOOGLE_UPDATE
#define PROTOCOL USB_PROTOCOL_GOOGLE_UPDATE

enum exit_values {
	noop = 0,	  /* All up to date, no update needed. */
	all_updated = 1,  /* Update completed, reboot required. */
	rw_updated  = 2,  /* RO was not updated, reboot required. */
	update_error = 3  /* Something went wrong. */
};

struct usb_endpoint {
	struct libusb_device_handle *devh;
	uint8_t ep_num;
	int     chunk_len;
};

struct transfer_descriptor {
	/*
	 * offsets of section available for update (not currently active).
	 */
	uint32_t offset;

	struct usb_endpoint uep;
};

/* Information about the target */
static struct first_response_pdu targ;

static uint16_t protocol_version;
static uint16_t header_type;
static char *progname;
static char *short_opts = "bd:efg:hjnp:rsS:tuw";
static const struct option long_opts[] = {
	/* name    hasarg *flag val */
	{"binvers",	1,   NULL, 'b'},
	{"device",	1,   NULL, 'd'},
	{"entropy",	0,   NULL, 'e'},
	{"fwver",	0,   NULL, 'f'},
	{"tp_debug",	1,   NULL, 'g'},
	{"help",	0,   NULL, 'h'},
	{"jump_to_rw",	0,   NULL, 'j'},
	{"no_reset",	0,   NULL, 'n'},
	{"tp_update",	1,   NULL, 'p'},
	{"reboot",	0,   NULL, 'r'},
	{"stay_in_ro",	0,   NULL, 's'},
	{"serial",	1,   NULL, 'S'},
	{"tp_info",	0,   NULL, 't'},
	{"unlock_rollback",	0,   NULL, 'u'},
	{"unlock_rw",	0,   NULL, 'w'},
	{},
};

/* Release USB device and return error to the OS. */
static void shut_down(struct usb_endpoint *uep)
{
	libusb_close(uep->devh);
	libusb_exit(NULL);
	exit(update_error);
}

static void usage(int errs)
{
	printf("\nUsage: %s [options] <binary image>\n"
	       "\n"
	       "This updates EC firmware over USB (common code EC, no cr50).\n"
	       "The required argument is the full RO+RW image.\n"
	       "\n"
	       "Options:\n"
	       "\n"
	       "  -b,--binvers             Report versions of image's "
				"RW and RO, do not update\n"
	       "  -d,--device  VID:PID     USB device (default %04x:%04x)\n"
	       "  -f,--fwver               Report running firmware versions.\n"
	       "  -g,--tp_debug <hex data> Touchpad debug command\n"
	       "  -h,--help                Show this message\n"
	       "  -e,--entropy             Add entropy to device secret\n"
	       "  -j,--jump_to_rw          Tell EC to jump to RW\n"
	       "  -p,--tp_update file      Update touchpad FW\n"
	       "  -r,--reboot              Tell EC to reboot\n"
	       "  -s,--stay_in_ro          Tell EC to stay in RO\n"
	       "  -S,--serial              Device serial number\n"
	       "  -t,--tp_info             Get touchpad information\n"
	       "  -u,--unlock_rollback     Tell EC to unlock the rollback region\n"
	       "  -w,--unlock_rw           Tell EC to unlock the RW region\n"
	       "\n", progname, VID, PID);

	exit(errs ? update_error : noop);
}

static void str2hex(const char *str, uint8_t *data, int *len)
{
	int i;
	int slen = strlen(str);

	if (slen/2 > *len) {
		fprintf(stderr, "Hex string too long.\n");
		exit(update_error);
	}

	if (slen % 2 != 0) {
		fprintf(stderr, "Hex string length not a multiple of 2.\n");
		exit(update_error);
	}

	for (i = 0, *len = 0; i < slen; i += 2, (*len)++) {
		char *end;
		char tmp[3];

		tmp[0] = str[i];
		tmp[1] = str[i+1];
		tmp[2] = 0;

		data[*len] = strtol(tmp, &end, 16);

		if (*end != 0) {
			fprintf(stderr, "Invalid hex string.\n");
			exit(update_error);
		}
	}
}

static void hexdump(const uint8_t *data, int len)
{
	int i;

	for (i = 0; i < len; i++) {
		printf("%02x", data[i]);
		if ((i % 16) == 15)
			printf("\n");
	}

	if ((len % 16) != 0)
		printf("\n");
}

static void dump_touchpad_info(const uint8_t *data, int len)
{
	const struct touchpad_info *info = (const struct touchpad_info *)data;

	if (len != sizeof(struct touchpad_info)) {
		fprintf(stderr, "Hex string length is not %zu",
			sizeof(struct touchpad_info));
		hexdump(data, len);
		return;
	}

	printf("\n");
	printf("status:         0x%02x\n", info->status);
	printf("vendor:         0x%04x\n", info->vendor);
	printf("fw_address:     0x%08x\n", info->fw_address);
	printf("fw_size:        0x%08x\n", info->fw_size);

	printf("allowed_fw_hash:\n");
	hexdump(info->allowed_fw_hash, sizeof(info->allowed_fw_hash));

	switch (info->vendor) {
	case 0x04f3: /* ELAN */
	case 0x0483: /* ST */
		printf("id:             0x%04x\n", info->elan.id);
		printf("fw_version:     0x%04x\n", info->elan.fw_version);
		printf("fw_fw_checksum: 0x%04x\n", info->elan.fw_checksum);
		break;
	default:
		fprintf(stderr, "Unknown vendor, vendor specific data:\n");
		hexdump((const uint8_t *)&info->elan, sizeof(info->elan));
		break;
	}
}

/* Read file into buffer */
static uint8_t *get_file_or_die(const char *filename, size_t *len_ptr)
{
	FILE *fp;
	struct stat st;
	uint8_t *data;
	size_t len;

	fp = fopen(filename, "rb");
	if (!fp) {
		perror(filename);
		exit(update_error);
	}
	if (fstat(fileno(fp), &st)) {
		perror("stat");
		exit(update_error);
	}

	len = st.st_size;

	data = malloc(len);
	if (!data) {
		perror("malloc");
		exit(update_error);
	}

	if (fread(data, st.st_size, 1, fp) != 1) {
		perror("fread");
		exit(update_error);
	}

	fclose(fp);

	*len_ptr = len;
	return data;
}

#define USB_ERROR(m, r) \
	fprintf(stderr, "%s:%d, %s returned %d (%s)\n", __FILE__, __LINE__, \
		m, r, libusb_strerror(r))

/*
 * Actual USB transfer function, the 'allow_less' flag indicates that the
 * valid response could be shortef than allotted memory, the 'rxed_count'
 * pointer, if provided along with 'allow_less' lets the caller know how mavy
 * bytes were received.
 */
static void do_xfer(struct usb_endpoint *uep, void *outbuf, int outlen,
		    void *inbuf, int inlen, int allow_less,
		    size_t *rxed_count)
{

	int r, actual;

	/* Send data out */
	if (outbuf && outlen) {
		actual = 0;
		r = libusb_bulk_transfer(uep->devh, uep->ep_num,
					 outbuf, outlen,
					 &actual, 1000);
		if (r < 0) {
			USB_ERROR("libusb_bulk_transfer", r);
			exit(update_error);
		}
		if (actual != outlen) {
			fprintf(stderr, "%s:%d, only sent %d/%d bytes\n",
				__FILE__, __LINE__, actual, outlen);
			shut_down(uep);
		}
	}

	/* Read reply back */
	if (inbuf && inlen) {

		actual = 0;
		r = libusb_bulk_transfer(uep->devh, uep->ep_num | 0x80,
					 inbuf, inlen,
					 &actual, 1000);
		if (r < 0) {
			USB_ERROR("libusb_bulk_transfer", r);
			exit(update_error);
		}
		if ((actual != inlen) && !allow_less) {
			fprintf(stderr, "%s:%d, only received %d/%d bytes\n",
				__FILE__, __LINE__, actual, inlen);
			hexdump(inbuf, actual);
			shut_down(uep);
		}

		if (rxed_count)
			*rxed_count = actual;
	}
}

static void xfer(struct usb_endpoint *uep, void *outbuf,
		 size_t outlen, void *inbuf, size_t inlen)
{
	do_xfer(uep, outbuf, outlen, inbuf, inlen, 0, NULL);
}

/* Return 0 on error, since it's never gonna be EP 0 */
static int find_endpoint(const struct libusb_interface_descriptor *iface,
			 struct usb_endpoint *uep)
{
	const struct libusb_endpoint_descriptor *ep;

	if (iface->bInterfaceClass == 255 &&
	    iface->bInterfaceSubClass == SUBCLASS &&
	    iface->bInterfaceProtocol == PROTOCOL &&
	    iface->bNumEndpoints) {
		ep = &iface->endpoint[0];
		uep->ep_num = ep->bEndpointAddress & 0x7f;
		uep->chunk_len = ep->wMaxPacketSize;
		return 1;
	}

	return 0;
}

/* Return -1 on error */
static int find_interface(struct usb_endpoint *uep)
{
	int iface_num = -1;
	int r, i, j;
	struct libusb_device *dev;
	struct libusb_config_descriptor *conf = 0;
	const struct libusb_interface *iface0;
	const struct libusb_interface_descriptor *iface;

	dev = libusb_get_device(uep->devh);
	r = libusb_get_active_config_descriptor(dev, &conf);
	if (r < 0) {
		USB_ERROR("libusb_get_active_config_descriptor", r);
		goto out;
	}

	for (i = 0; i < conf->bNumInterfaces; i++) {
		iface0 = &conf->interface[i];
		for (j = 0; j < iface0->num_altsetting; j++) {
			iface = &iface0->altsetting[j];
			if (find_endpoint(iface, uep)) {
				iface_num = i;
				goto out;
			}
		}
	}

out:
	libusb_free_config_descriptor(conf);
	return iface_num;
}

/* Returns true if parsed. */
static int parse_vidpid(const char *input, uint16_t *vid_ptr, uint16_t *pid_ptr)
{
	char *copy, *s, *e = 0;

	copy = strdup(input);

	s = strchr(copy, ':');
	if (!s)
		return 0;
	*s++ = '\0';

	*vid_ptr = (uint16_t) strtoul(copy, &e, 16);
	if (!*optarg || (e && *e))
		return 0;

	*pid_ptr = (uint16_t) strtoul(s, &e, 16);
	if (!*optarg || (e && *e))
		return 0;

	return 1;
}

static libusb_device_handle *check_device(libusb_device *dev,
	uint16_t vid, uint16_t pid, char *serialno)
{
	struct libusb_device_descriptor desc;
	libusb_device_handle *handle = NULL;
	char sn[256];
	int ret;
	int match = 1;
	int snvalid = 0;

	ret = libusb_get_device_descriptor(dev, &desc);
	if (ret < 0)
		return NULL;

	ret = libusb_open(dev, &handle);

	if (ret != LIBUSB_SUCCESS)
		return NULL;

	if (desc.iSerialNumber) {
		ret = libusb_get_string_descriptor_ascii(handle,
			desc.iSerialNumber, (unsigned char *)sn, sizeof(sn));
		if (ret > 0)
			snvalid = 1;
	}

	if (vid != 0 && vid != desc.idVendor)
		match = 0;
	if (pid != 0 && pid != desc.idProduct)
		match = 0;
	if (serialno != NULL && (!snvalid || strstr(sn, serialno) == NULL))
		match = 0;

	if (match)
		return handle;

	libusb_close(handle);
	return NULL;
}

static void usb_findit(uint16_t vid, uint16_t pid,
		char *serialno, struct usb_endpoint *uep)
{
	int iface_num, r, i;
	libusb_device **devs;
	libusb_device_handle *devh = NULL;
	ssize_t count;

	memset(uep, 0, sizeof(*uep));

	r = libusb_init(NULL);
	if (r < 0) {
		USB_ERROR("libusb_init", r);
		exit(update_error);
	}

	count = libusb_get_device_list(NULL, &devs);
	if (count < 0)
		return;

	for (i = 0; devs[i]; i++) {
		devh = check_device(devs[i], vid, pid, serialno);
		if (devh) {
			printf("Found device.\n");
			break;
		}
	}

	libusb_free_device_list(devs, 1);

	if (!devh) {
		fprintf(stderr, "Can't find device\n");
		exit(update_error);
	}

	uep->devh = devh;

	iface_num = find_interface(uep);
	if (iface_num < 0) {
		fprintf(stderr, "USB FW update not supported by that device\n");
		shut_down(uep);
	}
	if (!uep->chunk_len) {
		fprintf(stderr, "wMaxPacketSize isn't valid\n");
		shut_down(uep);
	}

	printf("found interface %d endpoint %d, chunk_len %d\n",
	       iface_num, uep->ep_num, uep->chunk_len);

	libusb_set_auto_detach_kernel_driver(uep->devh, 1);
	r = libusb_claim_interface(uep->devh, iface_num);
	if (r < 0) {
		USB_ERROR("libusb_claim_interface", r);
		shut_down(uep);
	}

	printf("READY\n-------\n");
}

static int transfer_block(struct usb_endpoint *uep,
			  struct update_frame_header *ufh,
			  uint8_t *transfer_data_ptr, size_t payload_size)
{
	size_t transfer_size;
	uint32_t reply;
	int actual;
	int r;

	/* First send the header. */
	xfer(uep, ufh, sizeof(*ufh), NULL, 0);

	/* Now send the block, chunk by chunk. */
	for (transfer_size = 0; transfer_size < payload_size;) {
		int chunk_size;

		chunk_size = MIN(uep->chunk_len, payload_size - transfer_size);
		xfer(uep, transfer_data_ptr, chunk_size, NULL, 0);
		transfer_data_ptr += chunk_size;
		transfer_size += chunk_size;
	}

	/* Now get the reply. */
	r = libusb_bulk_transfer(uep->devh, uep->ep_num | 0x80,
				 (void *) &reply, sizeof(reply),
				 &actual, 1000);
	if (r) {
		if (r == -7) {
			fprintf(stderr, "Timeout!\n");
			return r;
		}
		USB_ERROR("libusb_bulk_transfer", r);
		shut_down(uep);
	}

	reply = *((uint8_t *)&reply);
	if (reply) {
		fprintf(stderr, "Error: status %#x\n", reply);
		exit(update_error);
	}

	return 0;
}

/**
 * Transfer an image section (typically RW or RO).
 *
 * td           - transfer descriptor to use to communicate with the target
 * data_ptr     - pointer at the section base in the image
 * section_addr - address of the section in the target memory space
 * data_len     - section size
 * smart_update - non-zero to enable the smart trailing of 0xff.
 */
static void transfer_section(struct transfer_descriptor *td,
			     uint8_t *data_ptr,
			     uint32_t section_addr,
			     size_t data_len,
			     uint8_t smart_update)
{
	/*
	 * Actually, we can skip trailing chunks of 0xff, as the entire
	 * section space must be erased before the update is attempted.
	 *
	 * FIXME: We can be smarter than this and skip blocks within the image.
	 */
	if (smart_update)
		while (data_len && (data_ptr[data_len - 1] == 0xff))
			data_len--;

	printf("sending 0x%zx bytes to %#x\n", data_len, section_addr);
	while (data_len) {
		size_t payload_size;
		uint32_t block_base;
		int max_retries;

		/* prepare the header to prepend to the block. */
		payload_size = MIN(data_len, targ.common.maximum_pdu_size);

		block_base = htobe32(section_addr);

		struct update_frame_header ufh;

		ufh.block_size = htobe32(payload_size +
					sizeof(struct update_frame_header));
		ufh.cmd.block_base = block_base;
		ufh.cmd.block_digest = 0;
		for (max_retries = 10; max_retries; max_retries--)
			if (!transfer_block(&td->uep, &ufh,
						data_ptr, payload_size))
				break;

		if (!max_retries) {
			fprintf(stderr,
				"Failed to transfer block, %zd to go\n",
				data_len);
			exit(update_error);
		}
		data_len -= payload_size;
		data_ptr += payload_size;
		section_addr += payload_size;
	}
}

/*
 * Each RO or RW section of the new image can be in one of the following
 * states.
 */
enum upgrade_status {
	not_needed = 0,  /* Version below or equal that on the target. */
	not_possible,    /*
			  * RO is newer, but can't be transferred due to
			  * target RW shortcomings.
			  */
	needed            /*
			   * This section needs to be transferred to the
			   * target.
			   */
};

/* This array describes all sections of the new image. */
static struct {
	const char *name;
	uint32_t    offset;
	uint32_t    size;
	enum upgrade_status  ustatus;
	char version[32];
	int32_t rollback;
	uint32_t key_version;
} sections[] = {
	{"RO"},
	{"RW"}
};

static const struct fmap_area *fmap_find_area_or_die(const struct fmap *fmap,
						     const char *name)
{
	const struct fmap_area *fmaparea;

	fmaparea = fmap_find_area(fmap, name);
	if (!fmaparea) {
		fprintf(stderr, "Cannot find FMAP area %s\n", name);
		exit(update_error);
	}

	return fmaparea;
}

/*
 * Scan the new image and retrieve versions of all sections.
 */
static void fetch_header_versions(const uint8_t *image, size_t len)
{
	const struct fmap *fmap;
	const struct fmap_area *fmaparea;
	long int offset;
	size_t i;

	offset = fmap_find(image, len);
	if (offset < 0) {
		fprintf(stderr, "Cannot find FMAP in image\n");
		exit(update_error);
	}
	fmap = (const struct fmap *)(image+offset);

	/* FIXME: validate fmap struct more than this? */
	if (fmap->size != len) {
		fprintf(stderr, "Mismatch between FMAP size and image size\n");
		exit(update_error);
	}

	for (i = 0; i < ARRAY_SIZE(sections); i++) {
		const char *fmap_name;
		const char *fmap_fwid_name;
		const char *fmap_rollback_name = NULL;
		const char *fmap_key_name = NULL;

		if (!strcmp(sections[i].name, "RO")) {
			fmap_name = "EC_RO";
			fmap_fwid_name = "RO_FRID";
		} else if (!strcmp(sections[i].name, "RW")) {
			fmap_name = "EC_RW";
			fmap_fwid_name = "RW_FWID";
			fmap_rollback_name = "RW_RBVER";
			/*
			 * Key version comes from key RO (RW signature does not
			 * contain the key version.
			 */
			fmap_key_name = "KEY_RO";
		} else {
			fprintf(stderr, "Invalid section name\n");
			exit(update_error);
		}

		fmaparea = fmap_find_area_or_die(fmap, fmap_name);

		/* FIXME: endianness? */
		sections[i].offset = fmaparea->offset;
		sections[i].size = fmaparea->size;

		fmaparea = fmap_find_area_or_die(fmap, fmap_fwid_name);

		if (fmaparea->size != sizeof(sections[i].version)) {
			fprintf(stderr, "Invalid fwid size\n");
			exit(update_error);
		}
		memcpy(sections[i].version, image+fmaparea->offset,
			fmaparea->size);

		sections[i].rollback = -1;
		if (fmap_rollback_name) {
			fmaparea = fmap_find_area(fmap, fmap_rollback_name);
			if (fmaparea)
				memcpy(&sections[i].rollback,
				       image+fmaparea->offset,
				       sizeof(sections[i].rollback));
		}

		sections[i].key_version = -1;
		if (fmap_key_name) {
			fmaparea = fmap_find_area(fmap, fmap_key_name);
			if (fmaparea) {
				const struct vb21_packed_key *key =
					(const void *)(image+fmaparea->offset);
				sections[i].key_version = key->key_version;
			}
		}
	}
}

static int show_headers_versions(const void *image)
{
	size_t i;

	for (i = 0; i < ARRAY_SIZE(sections); i++) {
		printf("%s off=%08x/%08x v=%.32s rb=%d kv=%d\n",
			sections[i].name, sections[i].offset, sections[i].size,
			sections[i].version, sections[i].rollback,
			sections[i].key_version);
	}
	return 0;
}

/*
 * Pick sections to transfer based on information retrieved from the target,
 * the new image, and the protocol version the target is running.
 */
static void pick_sections(struct transfer_descriptor *td)
{
	size_t i;

	for (i = 0; i < ARRAY_SIZE(sections); i++) {
		uint32_t offset = sections[i].offset;

		/* Skip currently active section. */
		if (offset != td->offset)
			continue;

		sections[i].ustatus = needed;
	}
}

static void setup_connection(struct transfer_descriptor *td)
{
	size_t rxed_size;
	size_t i;
	uint32_t error_code;

	/*
	 * Need to be backwards compatible, communicate with targets running
	 * different protocol versions.
	 */
	union {
		struct first_response_pdu rpdu;
		uint32_t legacy_resp;
	} start_resp;

	/* Send start request. */
	printf("start\n");

	struct update_frame_header ufh;
	uint8_t inbuf[td->uep.chunk_len];
	int actual = 0;

	/* Flush all data from endpoint to recover in case of error. */
	while (!libusb_bulk_transfer(td->uep.devh,
					td->uep.ep_num | 0x80,
					(void *)&inbuf, td->uep.chunk_len,
					&actual, 10)) {
		printf("flush\n");
	}

	memset(&ufh, 0, sizeof(ufh));
	ufh.block_size = htobe32(sizeof(ufh));
	do_xfer(&td->uep, &ufh, sizeof(ufh), &start_resp,
		sizeof(start_resp), 1, &rxed_size);

	/* We got something. Check for errors in response */
	if (rxed_size < 8) {
		fprintf(stderr, "Unexpected response size %zd: ", rxed_size);
		for (i = 0; i < rxed_size; i++)
			fprintf(stderr, " %02x", ((uint8_t *)&start_resp)[i]);
		fprintf(stderr, "\n");
		exit(update_error);
	}

	protocol_version = be16toh(start_resp.rpdu.protocol_version);
	if (protocol_version < 5 || protocol_version > 6) {
		fprintf(stderr, "Unsupported protocol version %d\n",
			protocol_version);
		exit(update_error);
	}

	header_type = be16toh(start_resp.rpdu.header_type);

	printf("target running protocol version %d (type %d)\n",
		protocol_version, header_type);
	if (header_type != UPDATE_HEADER_TYPE_COMMON) {
		fprintf(stderr, "Unsupported header type %d\n",
			header_type);
		exit(update_error);
	}

	error_code = be32toh(start_resp.rpdu.return_value);

	if (error_code) {
		fprintf(stderr, "Target reporting error %d\n", error_code);
		shut_down(&td->uep);
		exit(update_error);
	}

	td->offset = be32toh(start_resp.rpdu.common.offset);
	memcpy(targ.common.version, start_resp.rpdu.common.version,
		sizeof(start_resp.rpdu.common.version));
	targ.common.maximum_pdu_size =
		be32toh(start_resp.rpdu.common.maximum_pdu_size);
	targ.common.flash_protection =
		be32toh(start_resp.rpdu.common.flash_protection);
	targ.common.min_rollback = be32toh(start_resp.rpdu.common.min_rollback);
	targ.common.key_version = be32toh(start_resp.rpdu.common.key_version);

	printf("maximum PDU size: %d\n", targ.common.maximum_pdu_size);
	printf("Flash protection status: %04x\n", targ.common.flash_protection);
	printf("version: %32s\n", targ.common.version);
	printf("key_version: %d\n", targ.common.key_version);
	printf("min_rollback: %d\n", targ.common.min_rollback);
	printf("offset: writable at %#x\n", td->offset);

	pick_sections(td);
}

/*
 * Channel TPM extension/vendor command over USB. The payload of the USB frame
 * in this case consists of the 2 byte subcommand code concatenated with the
 * command body. The caller needs to indicate if a response is expected, and
 * if it is - of what maximum size.
 */
static int ext_cmd_over_usb(struct usb_endpoint *uep, uint16_t subcommand,
			    void *cmd_body, size_t body_size,
			    void *resp, size_t *resp_size)
{
	struct update_frame_header *ufh;
	uint16_t *frame_ptr;
	size_t usb_msg_size;

	usb_msg_size = sizeof(struct update_frame_header) +
		sizeof(subcommand) + body_size;

	ufh = malloc(usb_msg_size);
	if (!ufh) {
		printf("%s: failed to allocate %zd bytes\n",
		       __func__, usb_msg_size);
		return -1;
	}

	ufh->block_size = htobe32(usb_msg_size);
	ufh->cmd.block_digest = 0;
	ufh->cmd.block_base = htobe32(UPDATE_EXTRA_CMD);
	frame_ptr = (uint16_t *)(ufh + 1);
	*frame_ptr = htobe16(subcommand);

	if (body_size)
		memcpy(frame_ptr + 1, cmd_body, body_size);

	xfer(uep, ufh, usb_msg_size, resp, resp_size ? *resp_size : 0);

	free(ufh);
	return 0;
}

/*
 * Indicate to the target that update image transfer has been completed. Upon
 * receiveing of this message the target state machine transitions into the
 * 'rx_idle' state. The host may send an extension command to reset the target
 * after this.
 */
static void send_done(struct usb_endpoint *uep)
{
	uint32_t out;

	/* Send stop request, ignoring reply. */
	out = htobe32(UPDATE_DONE);
	xfer(uep, &out, sizeof(out), &out, 1);
}

static void send_subcommand(struct transfer_descriptor *td, uint16_t subcommand,
			    void *cmd_body, size_t body_size,
			    uint8_t *response, size_t response_size)
{
	send_done(&td->uep);

	ext_cmd_over_usb(&td->uep, subcommand,
			cmd_body, body_size,
			response, &response_size);
	printf("sent command %x, resp %x\n", subcommand, response[0]);
}

/* Returns number of successfully transmitted image sections. */
static int transfer_image(struct transfer_descriptor *td,
			       uint8_t *data, size_t data_len)
{
	size_t i;
	int num_txed_sections = 0;

	for (i = 0; i < ARRAY_SIZE(sections); i++)
		if (sections[i].ustatus == needed) {
			transfer_section(td,
					 data + sections[i].offset,
					 sections[i].offset,
					 sections[i].size, 1);
			num_txed_sections++;
		}

	/*
	 * Move USB receiver sate machine to idle state so that vendor
	 * commands can be processed later, if any.
	 */
	send_done(&td->uep);

	if (!num_txed_sections)
		printf("nothing to do\n");
	else
		printf("-------\nupdate complete\n");
	return num_txed_sections;
}

static void generate_reset_request(struct transfer_descriptor *td)
{
	size_t response_size;
	uint8_t response;
	uint16_t subcommand;
	uint8_t command_body[2]; /* Max command body size. */
	size_t command_body_size;

	if (protocol_version < 6) {
		/*
		 * Send a second stop request, which should reboot
		 * without replying.
		 */
		send_done(&td->uep);
		/* Nothing we can do over /dev/tpm0 running versions below 6. */
		return;
	}

	/*
	 * If the user explicitly wants it, request post reset instead of
	 * immediate reset. In this case next time the target reboots, the h1
	 * will reboot as well, and will consider running the uploaded code.
	 *
	 * In case target RW version is 19 or above, to reset the target the
	 * host is supposed to send the command to enable the uploaded image
	 * disabled by default.
	 *
	 * Otherwise the immediate reset command would suffice.
	 */
	/* Most common case. */
	command_body_size = 0;
	response_size = 1;
	subcommand = UPDATE_EXTRA_CMD_IMMEDIATE_RESET;
	ext_cmd_over_usb(&td->uep, subcommand,
			command_body, command_body_size,
			&response, &response_size);

	printf("reboot not triggered\n");
}

static void get_random(uint8_t *data, int len)
{
	FILE *fp;
	int i = 0;

	fp = fopen("/dev/random", "rb");
	if (!fp) {
		perror("Can't open /dev/random");
		exit(update_error);
	}

	while (i < len) {
		int ret = fread(data+i, len-i, 1, fp);

		if (ret < 0) {
			perror("fread");
			exit(update_error);
		}

		i += ret;
	}

	fclose(fp);
}

int main(int argc, char *argv[])
{
	struct transfer_descriptor td;
	int errorcnt;
	uint8_t *data = 0;
	size_t data_len = 0;
	uint16_t vid = VID, pid = PID;
	char *serialno = NULL;
	int i;
	size_t j;
	int transferred_sections = 0;
	int binary_vers = 0;
	int show_fw_ver = 0;
	int no_reset_request = 0;
	int touchpad_update = 0;
	int extra_command = -1;
	uint8_t extra_command_data[50];
	int extra_command_data_len = 0;
	uint8_t extra_command_answer[64];
	int extra_command_answer_len = 1;

	progname = strrchr(argv[0], '/');
	if (progname)
		progname++;
	else
		progname = argv[0];

	/* Usb transfer - default mode. */
	memset(&td, 0, sizeof(td));

	errorcnt = 0;
	opterr = 0;				/* quiet, you */
	while ((i = getopt_long(argc, argv, short_opts, long_opts, 0)) != -1) {
		switch (i) {
		case 'b':
			binary_vers = 1;
			break;
		case 'd':
			if (!parse_vidpid(optarg, &vid, &pid)) {
				printf("Invalid argument: \"%s\"\n", optarg);
				errorcnt++;
			}
			break;
		case 'f':
			show_fw_ver = 1;
			break;
		case 'g':
			extra_command = UPDATE_EXTRA_CMD_TOUCHPAD_DEBUG;
			/* Maximum length. */
			extra_command_data_len = 50;
			str2hex(optarg,
				extra_command_data, &extra_command_data_len);
			hexdump(extra_command_data, extra_command_data_len);
			extra_command_answer_len = 64;
			break;
		case 'h':
			usage(errorcnt);
			break;
		case 'e':
			get_random(extra_command_data, 32);
			extra_command_data_len = 32;
			extra_command = UPDATE_EXTRA_CMD_INJECT_ENTROPY;
			break;
		case 'j':
			extra_command = UPDATE_EXTRA_CMD_JUMP_TO_RW;
			break;
		case 'n':
			no_reset_request = 1;
			break;
		case 'p':
			touchpad_update = 1;

			data = get_file_or_die(optarg, &data_len);
			printf("read %zd(%#zx) bytes from %s\n",
				data_len, data_len, argv[optind]);

			break;
		case 'r':
			extra_command = UPDATE_EXTRA_CMD_IMMEDIATE_RESET;
			break;
		case 's':
			extra_command = UPDATE_EXTRA_CMD_STAY_IN_RO;
			break;
		case 'S':
			serialno = optarg;
			break;
		case 't':
			extra_command = UPDATE_EXTRA_CMD_TOUCHPAD_INFO;
			extra_command_answer_len =
				sizeof(struct touchpad_info);
			break;
		case 'u':
			extra_command = UPDATE_EXTRA_CMD_UNLOCK_ROLLBACK;
			break;
		case 'w':
			extra_command = UPDATE_EXTRA_CMD_UNLOCK_RW;
			break;
		case 0:				/* auto-handled option */
			break;
		case '?':
			if (optopt)
				printf("Unrecognized option: -%c\n", optopt);
			else
				printf("Unrecognized option: %s\n",
				       argv[optind - 1]);
			errorcnt++;
			break;
		case ':':
			printf("Missing argument to %s\n", argv[optind - 1]);
			errorcnt++;
			break;
		default:
			printf("Internal error at %s:%d\n", __FILE__, __LINE__);
			exit(update_error);
		}
	}

	if (errorcnt)
		usage(errorcnt);

	if (!show_fw_ver && extra_command == -1 && !touchpad_update) {
		if (optind >= argc) {
			fprintf(stderr,
				"\nERROR: Missing required <binary image>\n\n");
			usage(1);
		}

		data = get_file_or_die(argv[optind], &data_len);
		printf("read %zd(%#zx) bytes from %s\n",
		       data_len, data_len, argv[optind]);

		fetch_header_versions(data, data_len);

		if (binary_vers)
			exit(show_headers_versions(data));
	} else {
		if (optind < argc)
			printf("Ignoring binary image %s\n", argv[optind]);
	}

	usb_findit(vid, pid, serialno, &td.uep);

	setup_connection(&td);

	if (show_fw_ver) {
		printf("Current versions:\n");
		printf("Writable %32s\n", targ.common.version);
	}

	if (data) {
		if (touchpad_update) {
			transfer_section(&td,
					data,
					0x80000000,
					data_len, 0);
			free(data);

			send_done(&td.uep);
		} else {
			transferred_sections = transfer_image(&td,
							data, data_len);
			free(data);

			if (transferred_sections && !no_reset_request)
				generate_reset_request(&td);
		}
	} else if (extra_command > -1) {
		send_subcommand(&td, extra_command,
				extra_command_data, extra_command_data_len,
				extra_command_answer, extra_command_answer_len);

		switch (extra_command) {
		case UPDATE_EXTRA_CMD_TOUCHPAD_INFO:
			dump_touchpad_info(extra_command_answer,
					   extra_command_answer_len);
			break;
		case  UPDATE_EXTRA_CMD_TOUCHPAD_DEBUG:
			hexdump(extra_command_answer, extra_command_answer_len);
			break;
		}
	}

	libusb_close(td.uep.devh);
	libusb_exit(NULL);

	if (!transferred_sections)
		return noop;
	/*
	 * We should indicate if RO update was not done because of the
	 * insufficient RW version.
	 */
	for (j = 0; j < ARRAY_SIZE(sections); j++)
		if (sections[j].ustatus == not_possible) {
			/* This will allow scripting repeat attempts. */
			printf("Failed to update RO, run the command again\n");
			return rw_updated;
		}

	printf("image updated\n");
	return all_updated;
}
