// SPDX-License-Identifier: GPL-2.0+
/*
 * Chromium OS cros_ec driver
 *
 * Copyright (c) 2012 The Chromium OS Authors.
 */

/*
 * This is the interface to the Chrome OS EC. It provides keyboard functions,
 * power control and battery management. Quite a few other functions are
 * provided to enable the EC software to be updated, talk to the EC's I2C bus
 * and store a small amount of data in a memory which persists while the EC
 * is not reset.
 */

#define LOG_CATEGORY UCLASS_CROS_EC

#include <common.h>
#include <command.h>
#include <dm.h>
#include <i2c.h>
#include <cros_ec.h>
#include <fdtdec.h>
#include <log.h>
#include <malloc.h>
#include <spi.h>
#include <linux/delay.h>
#include <linux/errno.h>
#include <asm/io.h>
#include <asm-generic/gpio.h>
#include <dm/device-internal.h>
#include <dm/of_extra.h>
#include <dm/uclass-internal.h>

#ifdef DEBUG_TRACE
#define debug_trace(fmt, b...)	debug(fmt, #b)
#else
#define debug_trace(fmt, b...)
#endif

enum {
	/* Timeout waiting for a flash erase command to complete */
	CROS_EC_CMD_TIMEOUT_MS	= 5000,
	/* Timeout waiting for a synchronous hash to be recomputed */
	CROS_EC_CMD_HASH_TIMEOUT_MS = 2000,

	/* Wait 10 ms between attempts to check if EC's hash is ready */
	CROS_EC_HASH_CHECK_DELAY_MS = 10,

};

#define INVALID_HCMD 0xFF

/*
 * Map UHEPI masks to non UHEPI commands in order to support old EC FW
 * which does not support UHEPI command.
 */
static const struct {
	u8 set_cmd;
	u8 clear_cmd;
	u8 get_cmd;
} event_map[] = {
	[EC_HOST_EVENT_MAIN] = {
		INVALID_HCMD, EC_CMD_HOST_EVENT_CLEAR,
		INVALID_HCMD,
	},
	[EC_HOST_EVENT_B] = {
		INVALID_HCMD, EC_CMD_HOST_EVENT_CLEAR_B,
		EC_CMD_HOST_EVENT_GET_B,
	},
	[EC_HOST_EVENT_SCI_MASK] = {
		EC_CMD_HOST_EVENT_SET_SCI_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_SCI_MASK,
	},
	[EC_HOST_EVENT_SMI_MASK] = {
		EC_CMD_HOST_EVENT_SET_SMI_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_SMI_MASK,
	},
	[EC_HOST_EVENT_ALWAYS_REPORT_MASK] = {
		INVALID_HCMD, INVALID_HCMD, INVALID_HCMD,
	},
	[EC_HOST_EVENT_ACTIVE_WAKE_MASK] = {
		EC_CMD_HOST_EVENT_SET_WAKE_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_WAKE_MASK,
	},
	[EC_HOST_EVENT_LAZY_WAKE_MASK_S0IX] = {
		EC_CMD_HOST_EVENT_SET_WAKE_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_WAKE_MASK,
	},
	[EC_HOST_EVENT_LAZY_WAKE_MASK_S3] = {
		EC_CMD_HOST_EVENT_SET_WAKE_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_WAKE_MASK,
	},
	[EC_HOST_EVENT_LAZY_WAKE_MASK_S5] = {
		EC_CMD_HOST_EVENT_SET_WAKE_MASK, INVALID_HCMD,
		EC_CMD_HOST_EVENT_GET_WAKE_MASK,
	},
};

void cros_ec_dump_data(const char *name, int cmd, const uint8_t *data, int len)
{
#ifdef DEBUG
	int i;

	printf("%s: ", name);
	if (cmd != -1)
		printf("cmd=%#x: ", cmd);
	for (i = 0; i < len; i++)
		printf("%02x ", data[i]);
	printf("\n");
#endif
}

/*
 * Calculate a simple 8-bit checksum of a data block
 *
 * @param data	Data block to checksum
 * @param size	Size of data block in bytes
 * Return: checksum value (0 to 255)
 */
int cros_ec_calc_checksum(const uint8_t *data, int size)
{
	int csum, i;

	for (i = csum = 0; i < size; i++)
		csum += data[i];
	return csum & 0xff;
}

/**
 * Create a request packet for protocol version 3.
 *
 * The packet is stored in the device's internal output buffer.
 *
 * @param dev		CROS-EC device
 * @param cmd		Command to send (EC_CMD_...)
 * @param cmd_version	Version of command to send (EC_VER_...)
 * @param dout          Output data (may be NULL If dout_len=0)
 * @param dout_len      Size of output data in bytes
 * Return: packet size in bytes, or <0 if error.
 */
static int create_proto3_request(struct cros_ec_dev *cdev,
				 int cmd, int cmd_version,
				 const void *dout, int dout_len)
{
	struct ec_host_request *rq = (struct ec_host_request *)cdev->dout;
	int out_bytes = dout_len + sizeof(*rq);

	/* Fail if output size is too big */
	if (out_bytes > (int)sizeof(cdev->dout)) {
		debug("%s: Cannot send %d bytes\n", __func__, dout_len);
		return -EC_RES_REQUEST_TRUNCATED;
	}

	/* Fill in request packet */
	rq->struct_version = EC_HOST_REQUEST_VERSION;
	rq->checksum = 0;
	rq->command = cmd;
	rq->command_version = cmd_version;
	rq->reserved = 0;
	rq->data_len = dout_len;

	/* Copy data after header */
	memcpy(rq + 1, dout, dout_len);

	/* Write checksum field so the entire packet sums to 0 */
	rq->checksum = (uint8_t)(-cros_ec_calc_checksum(cdev->dout, out_bytes));

	cros_ec_dump_data("out", cmd, cdev->dout, out_bytes);

	/* Return size of request packet */
	return out_bytes;
}

/**
 * Prepare the device to receive a protocol version 3 response.
 *
 * @param dev		CROS-EC device
 * @param din_len       Maximum size of response in bytes
 * Return: maximum expected number of bytes in response, or <0 if error.
 */
static int prepare_proto3_response_buffer(struct cros_ec_dev *cdev, int din_len)
{
	int in_bytes = din_len + sizeof(struct ec_host_response);

	/* Fail if input size is too big */
	if (in_bytes > (int)sizeof(cdev->din)) {
		debug("%s: Cannot receive %d bytes\n", __func__, din_len);
		return -EC_RES_RESPONSE_TOO_BIG;
	}

	/* Return expected size of response packet */
	return in_bytes;
}

/**
 * Handle a protocol version 3 response packet.
 *
 * The packet must already be stored in the device's internal input buffer.
 *
 * @param dev		CROS-EC device
 * @param dinp          Returns pointer to response data
 * @param din_len       Maximum size of response in bytes
 * Return: number of bytes of response data, or <0 if error. Note that error
 * codes can be from errno.h or -ve EC_RES_INVALID_CHECKSUM values (and they
 * overlap!)
 */
static int handle_proto3_response(struct cros_ec_dev *dev,
				  uint8_t **dinp, int din_len)
{
	struct ec_host_response *rs = (struct ec_host_response *)dev->din;
	int in_bytes;
	int csum;

	cros_ec_dump_data("in-header", -1, dev->din, sizeof(*rs));

	/* Check input data */
	if (rs->struct_version != EC_HOST_RESPONSE_VERSION) {
		debug("%s: EC response version mismatch\n", __func__);
		return -EC_RES_INVALID_RESPONSE;
	}

	if (rs->reserved) {
		debug("%s: EC response reserved != 0\n", __func__);
		return -EC_RES_INVALID_RESPONSE;
	}

	if (rs->data_len > din_len) {
		debug("%s: EC returned too much data\n", __func__);
		return -EC_RES_RESPONSE_TOO_BIG;
	}

	cros_ec_dump_data("in-data", -1, dev->din + sizeof(*rs), rs->data_len);

	/* Update in_bytes to actual data size */
	in_bytes = sizeof(*rs) + rs->data_len;

	/* Verify checksum */
	csum = cros_ec_calc_checksum(dev->din, in_bytes);
	if (csum) {
		debug("%s: EC response checksum invalid: 0x%02x\n", __func__,
		      csum);
		return -EC_RES_INVALID_CHECKSUM;
	}

	/* Return error result, if any */
	if (rs->result)
		return -(int)rs->result;

	/* If we're still here, set response data pointer and return length */
	*dinp = (uint8_t *)(rs + 1);

	return rs->data_len;
}

static int send_command_proto3(struct cros_ec_dev *cdev,
			       int cmd, int cmd_version,
			       const void *dout, int dout_len,
			       uint8_t **dinp, int din_len)
{
	struct dm_cros_ec_ops *ops;
	int out_bytes, in_bytes;
	int rv;

	/* Create request packet */
	out_bytes = create_proto3_request(cdev, cmd, cmd_version,
					  dout, dout_len);
	if (out_bytes < 0)
		return out_bytes;

	/* Prepare response buffer */
	in_bytes = prepare_proto3_response_buffer(cdev, din_len);
	if (in_bytes < 0)
		return in_bytes;

	ops = dm_cros_ec_get_ops(cdev->dev);
	rv = ops->packet ? ops->packet(cdev->dev, out_bytes, in_bytes) :
			-ENOSYS;
	if (rv < 0)
		return rv;

	/* Process the response */
	return handle_proto3_response(cdev, dinp, din_len);
}

static int send_command(struct cros_ec_dev *dev, uint cmd, int cmd_version,
			const void *dout, int dout_len,
			uint8_t **dinp, int din_len)
{
	struct dm_cros_ec_ops *ops;
	int ret = -1;

	/* Handle protocol version 3 support */
	if (dev->protocol_version == 3) {
		return send_command_proto3(dev, cmd, cmd_version,
					   dout, dout_len, dinp, din_len);
	}

	ops = dm_cros_ec_get_ops(dev->dev);
	ret = ops->command(dev->dev, cmd, cmd_version,
			   (const uint8_t *)dout, dout_len, dinp, din_len);

	return ret;
}

/**
 * Send a command to the CROS-EC device and return the reply.
 *
 * The device's internal input/output buffers are used.
 *
 * @param dev		CROS-EC device
 * @param cmd		Command to send (EC_CMD_...)
 * @param cmd_version	Version of command to send (EC_VER_...)
 * @param dout          Output data (may be NULL If dout_len=0)
 * @param dout_len      Size of output data in bytes
 * @param dinp          Response data (may be NULL If din_len=0).
 *			If not NULL, it will be updated to point to the data
 *			and will always be double word aligned (64-bits)
 * @param din_len       Maximum size of response in bytes
 * Return: number of bytes in response, or -ve on error
 */
static int ec_command_inptr(struct udevice *dev, uint cmd,
			    int cmd_version, const void *dout, int dout_len,
			    uint8_t **dinp, int din_len)
{
	struct cros_ec_dev *cdev = dev_get_uclass_priv(dev);
	uint8_t *din = NULL;
	int len;

	len = send_command(cdev, cmd, cmd_version, dout, dout_len, &din,
			   din_len);

	/* If the command doesn't complete, wait a while */
	if (len == -EC_RES_IN_PROGRESS) {
		struct ec_response_get_comms_status *resp = NULL;
		ulong start;

		/* Wait for command to complete */
		start = get_timer(0);
		do {
			int ret;

			mdelay(50);	/* Insert some reasonable delay */
			ret = send_command(cdev, EC_CMD_GET_COMMS_STATUS, 0,
					   NULL, 0,
					   (uint8_t **)&resp, sizeof(*resp));
			if (ret < 0)
				return ret;

			if (get_timer(start) > CROS_EC_CMD_TIMEOUT_MS) {
				debug("%s: Command %#02x timeout\n",
				      __func__, cmd);
				return -EC_RES_TIMEOUT;
			}
		} while (resp->flags & EC_COMMS_STATUS_PROCESSING);

		/* OK it completed, so read the status response */
		/* not sure why it was 0 for the last argument */
		len = send_command(cdev, EC_CMD_RESEND_RESPONSE, 0, NULL, 0,
				   &din, din_len);
	}

	debug("%s: len=%d, din=%p\n", __func__, len, din);
	if (dinp) {
		/* If we have any data to return, it must be 64bit-aligned */
		assert(len <= 0 || !((uintptr_t)din & 7));
		*dinp = din;
	}

	return len;
}

/**
 * Send a command to the CROS-EC device and return the reply.
 *
 * The device's internal input/output buffers are used.
 *
 * @param dev		CROS-EC device
 * @param cmd		Command to send (EC_CMD_...)
 * @param cmd_version	Version of command to send (EC_VER_...)
 * @param dout          Output data (may be NULL If dout_len=0)
 * @param dout_len      Size of output data in bytes
 * @param din           Response data (may be NULL If din_len=0).
 *			It not NULL, it is a place for ec_command() to copy the
 *      data to.
 * @param din_len       Maximum size of response in bytes
 * Return: number of bytes in response, or -ve on error
 */
static int ec_command(struct udevice *dev, uint cmd, int cmd_version,
		      const void *dout, int dout_len,
		      void *din, int din_len)
{
	uint8_t *in_buffer;
	int len;

	assert((din_len == 0) || din);
	len = ec_command_inptr(dev, cmd, cmd_version, dout, dout_len,
			       &in_buffer, din_len);
	if (len > 0) {
		/*
		 * If we were asked to put it somewhere, do so, otherwise just
		 * disregard the result.
		 */
		if (din && in_buffer) {
			assert(len <= din_len);
			if (len > din_len)
				return -ENOSPC;
			memmove(din, in_buffer, len);
		}
	}
	return len;
}

int cros_ec_scan_keyboard(struct udevice *dev, struct mbkp_keyscan *scan)
{
	if (ec_command(dev, EC_CMD_MKBP_STATE, 0, NULL, 0, scan,
		       sizeof(scan->data)) != sizeof(scan->data))
		return -1;

	return 0;
}

int cros_ec_get_next_event(struct udevice *dev,
			   struct ec_response_get_next_event *event)
{
	int ret;

	ret = ec_command(dev, EC_CMD_GET_NEXT_EVENT, 0, NULL, 0,
			 event, sizeof(*event));
	if (ret < 0)
		return ret;
	else if (ret != sizeof(*event))
		return -EC_RES_INVALID_RESPONSE;

	return 0;
}

int cros_ec_read_id(struct udevice *dev, char *id, int maxlen)
{
	struct ec_response_get_version *r;
	int ret;

	ret = ec_command_inptr(dev, EC_CMD_GET_VERSION, 0, NULL, 0,
			       (uint8_t **)&r, sizeof(*r));
	if (ret != sizeof(*r)) {
		log_err("Got rc %d, expected %u\n", ret, (uint)sizeof(*r));
		return -1;
	}

	if (maxlen > (int)sizeof(r->version_string_ro))
		maxlen = sizeof(r->version_string_ro);

	switch (r->current_image) {
	case EC_IMAGE_RO:
		memcpy(id, r->version_string_ro, maxlen);
		break;
	case EC_IMAGE_RW:
		memcpy(id, r->version_string_rw, maxlen);
		break;
	default:
		log_err("Invalid EC image %d\n", r->current_image);
		return -1;
	}

	id[maxlen - 1] = '\0';
	return 0;
}

int cros_ec_read_version(struct udevice *dev,
			 struct ec_response_get_version **versionp)
{
	if (ec_command_inptr(dev, EC_CMD_GET_VERSION, 0, NULL, 0,
			(uint8_t **)versionp, sizeof(**versionp))
			!= sizeof(**versionp))
		return -1;

	return 0;
}

int cros_ec_read_build_info(struct udevice *dev, char **strp)
{
	if (ec_command_inptr(dev, EC_CMD_GET_BUILD_INFO, 0, NULL, 0,
			(uint8_t **)strp, EC_PROTO2_MAX_PARAM_SIZE) < 0)
		return -1;

	return 0;
}

int cros_ec_read_current_image(struct udevice *dev,
			       enum ec_current_image *image)
{
	struct ec_response_get_version *r;

	if (ec_command_inptr(dev, EC_CMD_GET_VERSION, 0, NULL, 0,
			(uint8_t **)&r, sizeof(*r)) != sizeof(*r))
		return -1;

	*image = r->current_image;
	return 0;
}

static int cros_ec_wait_on_hash_done(struct udevice *dev,
				     struct ec_params_vboot_hash *p,
				     struct ec_response_vboot_hash *hash)
{
	ulong start;

	start = get_timer(0);
	while (hash->status == EC_VBOOT_HASH_STATUS_BUSY) {
		mdelay(CROS_EC_HASH_CHECK_DELAY_MS);

		p->cmd = EC_VBOOT_HASH_GET;

		if (ec_command(dev, EC_CMD_VBOOT_HASH, 0, p, sizeof(*p), hash,
			       sizeof(*hash)) < 0)
			return -1;

		if (get_timer(start) > CROS_EC_CMD_HASH_TIMEOUT_MS) {
			debug("%s: EC_VBOOT_HASH_GET timeout\n", __func__);
			return -EC_RES_TIMEOUT;
		}
	}
	return 0;
}

int cros_ec_read_hash(struct udevice *dev, uint hash_offset,
		      struct ec_response_vboot_hash *hash)
{
	struct ec_params_vboot_hash p;
	int rv;

	p.cmd = EC_VBOOT_HASH_GET;
	p.offset = hash_offset;
	if (ec_command(dev, EC_CMD_VBOOT_HASH, 0, &p, sizeof(p),
		       hash, sizeof(*hash)) < 0)
		return -1;

	/* If the EC is busy calculating the hash, fidget until it's done. */
	rv = cros_ec_wait_on_hash_done(dev, &p, hash);
	if (rv)
		return rv;

	/* If the hash is valid, we're done. Otherwise, we have to kick it off
	 * again and wait for it to complete. Note that we explicitly assume
	 * that hashing zero bytes is always wrong, even though that would
	 * produce a valid hash value. */
	if (hash->status == EC_VBOOT_HASH_STATUS_DONE && hash->size)
		return 0;

	debug("%s: No valid hash (status=%d size=%d). Compute one...\n",
	      __func__, hash->status, hash->size);

	p.cmd = EC_VBOOT_HASH_START;
	p.hash_type = EC_VBOOT_HASH_TYPE_SHA256;
	p.nonce_size = 0;
	p.offset = hash_offset;

	if (ec_command(dev, EC_CMD_VBOOT_HASH, 0, &p, sizeof(p),
		       hash, sizeof(*hash)) < 0)
		return -1;

	rv = cros_ec_wait_on_hash_done(dev, &p, hash);
	if (rv)
		return rv;
	if (hash->status != EC_VBOOT_HASH_STATUS_DONE) {
		log_err("Hash did not complete, status=%d\n", hash->status);
		return -EIO;
	}

	debug("%s: hash done\n", __func__);

	return 0;
}

static int cros_ec_invalidate_hash(struct udevice *dev)
{
	struct ec_params_vboot_hash p;
	struct ec_response_vboot_hash *hash;

	/* We don't have an explict command for the EC to discard its current
	 * hash value, so we'll just tell it to calculate one that we know is
	 * wrong (we claim that hashing zero bytes is always invalid).
	 */
	p.cmd = EC_VBOOT_HASH_RECALC;
	p.hash_type = EC_VBOOT_HASH_TYPE_SHA256;
	p.nonce_size = 0;
	p.offset = 0;
	p.size = 0;

	debug("%s:\n", __func__);

	if (ec_command_inptr(dev, EC_CMD_VBOOT_HASH, 0, &p, sizeof(p),
		       (uint8_t **)&hash, sizeof(*hash)) < 0)
		return -1;

	/* No need to wait for it to finish */
	return 0;
}

int cros_ec_hello(struct udevice *dev, uint *handshakep)
{
	struct ec_params_hello req;
	struct ec_response_hello *resp;

	req.in_data = 0x12345678;
	if (ec_command_inptr(dev, EC_CMD_HELLO, 0, &req, sizeof(req),
			     (uint8_t **)&resp, sizeof(*resp)) < 0)
		return -EIO;
	if (resp->out_data != req.in_data + 0x01020304) {
		printf("Received invalid handshake %x\n", resp->out_data);
		if (handshakep)
			*handshakep = req.in_data;
		return -ENOTSYNC;
	}

	return 0;
}

int cros_ec_reboot(struct udevice *dev, enum ec_reboot_cmd cmd, uint8_t flags)
{
	struct ec_params_reboot_ec p;

	p.cmd = cmd;
	p.flags = flags;

	if (ec_command_inptr(dev, EC_CMD_REBOOT_EC, 0, &p, sizeof(p), NULL, 0)
			< 0)
		return -1;

	if (!(flags & EC_REBOOT_FLAG_ON_AP_SHUTDOWN)) {
		ulong start;

		/*
		 * EC reboot will take place immediately so delay to allow it
		 * to complete.  Note that some reboot types (EC_REBOOT_COLD)
		 * will reboot the AP as well, in which case we won't actually
		 * get to this point.
		 */
		mdelay(50);
		start = get_timer(0);
		while (cros_ec_hello(dev, NULL)) {
			if (get_timer(start) > 3000) {
				log_err("EC did not return from reboot\n");
				return -ETIMEDOUT;
			}
			mdelay(5);
		}
	}

	return 0;
}

int cros_ec_interrupt_pending(struct udevice *dev)
{
	struct cros_ec_dev *cdev = dev_get_uclass_priv(dev);

	/* no interrupt support : always poll */
	if (!dm_gpio_is_valid(&cdev->ec_int))
		return -ENOENT;

	return dm_gpio_get_value(&cdev->ec_int);
}

int cros_ec_info(struct udevice *dev, struct ec_response_mkbp_info *info)
{
	if (ec_command(dev, EC_CMD_MKBP_INFO, 0, NULL, 0, info,
		       sizeof(*info)) != sizeof(*info))
		return -1;

	return 0;
}

int cros_ec_get_event_mask(struct udevice *dev, uint type, uint32_t *mask)
{
	struct ec_response_host_event_mask rsp;
	int ret;

	ret = ec_command(dev, type, 0, NULL, 0, &rsp, sizeof(rsp));
	if (ret < 0)
		return ret;
	else if (ret != sizeof(rsp))
		return -EINVAL;

	*mask = rsp.mask;

	return 0;
}

int cros_ec_set_event_mask(struct udevice *dev, uint type, uint32_t mask)
{
	struct ec_params_host_event_mask req;
	int ret;

	req.mask = mask;

	ret = ec_command(dev, type, 0, &req, sizeof(req), NULL, 0);
	if (ret < 0)
		return ret;

	return 0;
}

int cros_ec_get_host_events(struct udevice *dev, uint32_t *events_ptr)
{
	struct ec_response_host_event_mask *resp;

	/*
	 * Use the B copy of the event flags, because the main copy is already
	 * used by ACPI/SMI.
	 */
	if (ec_command_inptr(dev, EC_CMD_HOST_EVENT_GET_B, 0, NULL, 0,
		       (uint8_t **)&resp, sizeof(*resp)) < (int)sizeof(*resp))
		return -1;

	if (resp->mask & EC_HOST_EVENT_MASK(EC_HOST_EVENT_INVALID))
		return -1;

	*events_ptr = resp->mask;
	return 0;
}

int cros_ec_clear_host_events(struct udevice *dev, uint32_t events)
{
	struct ec_params_host_event_mask params;

	params.mask = events;

	/*
	 * Use the B copy of the event flags, so it affects the data returned
	 * by cros_ec_get_host_events().
	 */
	if (ec_command_inptr(dev, EC_CMD_HOST_EVENT_CLEAR_B, 0,
		       &params, sizeof(params), NULL, 0) < 0)
		return -1;

	return 0;
}

int cros_ec_flash_protect(struct udevice *dev, uint32_t set_mask,
			  uint32_t set_flags,
			  struct ec_response_flash_protect *resp)
{
	struct ec_params_flash_protect params;

	params.mask = set_mask;
	params.flags = set_flags;

	if (ec_command(dev, EC_CMD_FLASH_PROTECT, EC_VER_FLASH_PROTECT,
		       &params, sizeof(params),
		       resp, sizeof(*resp)) != sizeof(*resp))
		return -1;

	return 0;
}

static int cros_ec_check_version(struct udevice *dev)
{
	struct cros_ec_dev *cdev = dev_get_uclass_priv(dev);
	struct ec_params_hello req;

	struct dm_cros_ec_ops *ops;
	int ret;

	ops = dm_cros_ec_get_ops(dev);
	if (ops->check_version) {
		ret = ops->check_version(dev);
		if (ret)
			return ret;
	}

	/*
	 * TODO(sjg@chromium.org).
	 * There is a strange oddity here with the EC. We could just ignore
	 * the response, i.e. pass the last two parameters as NULL and 0.
	 * In this case we won't read back very many bytes from the EC.
	 * On the I2C bus the EC gets upset about this and will try to send
	 * the bytes anyway. This means that we will have to wait for that
	 * to complete before continuing with a new EC command.
	 *
	 * This problem is probably unique to the I2C bus.
	 *
	 * So for now, just read all the data anyway.
	 */

	/* Try sending a version 3 packet */
	cdev->protocol_version = 3;
	req.in_data = 0;
	ret = cros_ec_hello(dev, NULL);
	if (!ret || ret == -ENOTSYNC)
		return 0;

	/* Try sending a version 2 packet */
	cdev->protocol_version = 2;
	ret = cros_ec_hello(dev, NULL);
	if (!ret || ret == -ENOTSYNC)
		return 0;

	/*
	 * Fail if we're still here, since the EC doesn't understand any
	 * protcol version we speak.  Version 1 interface without command
	 * version is no longer supported, and we don't know about any new
	 * protocol versions.
	 */
	cdev->protocol_version = 0;
	printf("%s: ERROR: old EC interface not supported\n", __func__);
	return -1;
}

int cros_ec_test(struct udevice *dev)
{
	uint out_data;
	int ret;

	ret = cros_ec_hello(dev, &out_data);
	if (ret == -ENOTSYNC) {
		printf("Received invalid handshake %x\n", out_data);
		return ret;
	} else if (ret) {
		printf("ec_command_inptr() returned error\n");
		return ret;
	}

	return 0;
}

int cros_ec_flash_offset(struct udevice *dev, enum ec_flash_region region,
		      uint32_t *offset, uint32_t *size)
{
	struct ec_params_flash_region_info p;
	struct ec_response_flash_region_info *r;
	int ret;

	p.region = region;
	ret = ec_command_inptr(dev, EC_CMD_FLASH_REGION_INFO,
			 EC_VER_FLASH_REGION_INFO,
			 &p, sizeof(p), (uint8_t **)&r, sizeof(*r));
	if (ret != sizeof(*r))
		return -1;

	if (offset)
		*offset = r->offset;
	if (size)
		*size = r->size;

	return 0;
}

int cros_ec_flash_erase(struct udevice *dev, uint32_t offset, uint32_t size)
{
	struct ec_params_flash_erase p;

	p.offset = offset;
	p.size = size;
	return ec_command_inptr(dev, EC_CMD_FLASH_ERASE, 0, &p, sizeof(p),
			NULL, 0);
}

/**
 * Write a single block to the flash
 *
 * Write a block of data to the EC flash. The size must not exceed the flash
 * write block size which you can obtain from cros_ec_flash_write_burst_size().
 *
 * The offset starts at 0. You can obtain the region information from
 * cros_ec_flash_offset() to find out where to write for a particular region.
 *
 * Attempting to write to the region where the EC is currently running from
 * will result in an error.
 *
 * @param dev		CROS-EC device
 * @param data		Pointer to data buffer to write
 * @param offset	Offset within flash to write to.
 * @param size		Number of bytes to write
 * Return: 0 if ok, -1 on error
 */
static int cros_ec_flash_write_block(struct udevice *dev, const uint8_t *data,
				     uint32_t offset, uint32_t size)
{
	struct ec_params_flash_write *p;
	int ret;

	p = malloc(sizeof(*p) + size);
	if (!p)
		return -ENOMEM;

	p->offset = offset;
	p->size = size;
	assert(data && p->size <= EC_FLASH_WRITE_VER0_SIZE);
	memcpy(p + 1, data, p->size);

	ret = ec_command_inptr(dev, EC_CMD_FLASH_WRITE, 0,
			  p, sizeof(*p) + size, NULL, 0) >= 0 ? 0 : -1;

	free(p);

	return ret;
}

/**
 * Return optimal flash write burst size
 */
static int cros_ec_flash_write_burst_size(struct udevice *dev)
{
	return EC_FLASH_WRITE_VER0_SIZE;
}

/**
 * Check if a block of data is erased (all 0xff)
 *
 * This function is useful when dealing with flash, for checking whether a
 * data block is erased and thus does not need to be programmed.
 *
 * @param data		Pointer to data to check (must be word-aligned)
 * @param size		Number of bytes to check (must be word-aligned)
 * Return: 0 if erased, non-zero if any word is not erased
 */
static int cros_ec_data_is_erased(const uint32_t *data, int size)
{
	assert(!(size & 3));
	size /= sizeof(uint32_t);
	for (; size > 0; size -= 4, data++)
		if (*data != -1U)
			return 0;

	return 1;
}

/**
 * Read back flash parameters
 *
 * This function reads back parameters of the flash as reported by the EC
 *
 * @param dev  Pointer to device
 * @param info Pointer to output flash info struct
 */
int cros_ec_read_flashinfo(struct udevice *dev,
			   struct ec_response_flash_info *info)
{
	int ret;

	ret = ec_command(dev, EC_CMD_FLASH_INFO, 0,
			 NULL, 0, info, sizeof(*info));
	if (ret < 0)
		return ret;

	return ret < sizeof(*info) ? -1 : 0;
}

int cros_ec_flash_write(struct udevice *dev, const uint8_t *data,
			uint32_t offset, uint32_t size)
{
	struct cros_ec_dev *cdev = dev_get_uclass_priv(dev);
	uint32_t burst = cros_ec_flash_write_burst_size(dev);
	uint32_t end, off;
	int ret;

	if (!burst)
		return -EINVAL;

	/*
	 * TODO: round up to the nearest multiple of write size.  Can get away
	 * without that on link right now because its write size is 4 bytes.
	 */
	end = offset + size;
	for (off = offset; off < end; off += burst, data += burst) {
		uint32_t todo;

		/* If the data is empty, there is no point in programming it */
		todo = min(end - off, burst);
		if (cdev->optimise_flash_write &&
		    cros_ec_data_is_erased((uint32_t *)data, todo))
			continue;

		ret = cros_ec_flash_write_block(dev, data, off, todo);
		if (ret)
			return ret;
	}

	return 0;
}

/**
 * Run verification on a slot
 *
 * @param me     CrosEc instance
 * @param region Region to run verification on
 * Return: 0 if success or not applicable. Non-zero if verification failed.
 */
int cros_ec_efs_verify(struct udevice *dev, enum ec_flash_region region)
{
	struct ec_params_efs_verify p;
	int rv;

	log_info("EFS: EC is verifying updated image...\n");
	p.region = region;

	rv = ec_command(dev, EC_CMD_EFS_VERIFY, 0, &p, sizeof(p), NULL, 0);
	if (rv >= 0) {
		log_info("EFS: Verification success\n");
		return 0;
	}
	if (rv == -EC_RES_INVALID_COMMAND) {
		log_info("EFS: EC doesn't support EFS_VERIFY command\n");
		return 0;
	}
	log_info("EFS: Verification failed\n");

	return rv;
}

/**
 * Read a single block from the flash
 *
 * Read a block of data from the EC flash. The size must not exceed the flash
 * write block size which you can obtain from cros_ec_flash_write_burst_size().
 *
 * The offset starts at 0. You can obtain the region information from
 * cros_ec_flash_offset() to find out where to read for a particular region.
 *
 * @param dev		CROS-EC device
 * @param data		Pointer to data buffer to read into
 * @param offset	Offset within flash to read from
 * @param size		Number of bytes to read
 * Return: 0 if ok, -1 on error
 */
static int cros_ec_flash_read_block(struct udevice *dev, uint8_t *data,
				    uint32_t offset, uint32_t size)
{
	struct ec_params_flash_read p;

	p.offset = offset;
	p.size = size;

	return ec_command(dev, EC_CMD_FLASH_READ, 0,
			  &p, sizeof(p), data, size) >= 0 ? 0 : -1;
}

int cros_ec_flash_read(struct udevice *dev, uint8_t *data, uint32_t offset,
		       uint32_t size)
{
	uint32_t burst = cros_ec_flash_write_burst_size(dev);
	uint32_t end, off;
	int ret;

	end = offset + size;
	for (off = offset; off < end; off += burst, data += burst) {
		ret = cros_ec_flash_read_block(dev, data, off,
					    min(end - off, burst));
		if (ret)
			return ret;
	}

	return 0;
}

int cros_ec_flash_update_rw(struct udevice *dev, const uint8_t *image,
			    int image_size)
{
	uint32_t rw_offset, rw_size;
	int ret;

	if (cros_ec_flash_offset(dev, EC_FLASH_REGION_ACTIVE, &rw_offset,
		&rw_size))
		return -1;
	if (image_size > (int)rw_size)
		return -1;

	/* Invalidate the existing hash, just in case the AP reboots
	 * unexpectedly during the update. If that happened, the EC RW firmware
	 * would be invalid, but the EC would still have the original hash.
	 */
	ret = cros_ec_invalidate_hash(dev);
	if (ret)
		return ret;

	/*
	 * Erase the entire RW section, so that the EC doesn't see any garbage
	 * past the new image if it's smaller than the current image.
	 *
	 * TODO: could optimize this to erase just the current image, since
	 * presumably everything past that is 0xff's.  But would still need to
	 * round up to the nearest multiple of erase size.
	 */
	ret = cros_ec_flash_erase(dev, rw_offset, rw_size);
	if (ret)
		return ret;

	/* Write the image */
	ret = cros_ec_flash_write(dev, image, rw_offset, image_size);
	if (ret)
		return ret;

	return 0;
}

int cros_ec_get_sku_id(struct udevice *dev)
{
	struct ec_sku_id_info *r;
	int ret;

	ret = ec_command_inptr(dev, EC_CMD_GET_SKU_ID, 0, NULL, 0,
			       (uint8_t **)&r, sizeof(*r));
	if (ret != sizeof(*r)) {
		if (ret >= 0)
			ret = -EIO;
		return ret;
	}

	return r->sku_id;
}

int cros_ec_read_nvdata(struct udevice *dev, uint8_t *block, int size)
{
	struct ec_params_vbnvcontext p;
	int len;

	if (size != EC_VBNV_BLOCK_SIZE && size != EC_VBNV_BLOCK_SIZE_V2)
		return -EINVAL;

	p.op = EC_VBNV_CONTEXT_OP_READ;

	len = ec_command(dev, EC_CMD_VBNV_CONTEXT, EC_VER_VBNV_CONTEXT,
			 &p, sizeof(uint32_t) + size, block, size);
	if (len != size) {
		log_err("Expected %d bytes, got %d\n", size, len);
		return -EIO;
	}

	return 0;
}

int cros_ec_write_nvdata(struct udevice *dev, const uint8_t *block, int size)
{
	struct ec_params_vbnvcontext p;
	int len;

	if (size != EC_VBNV_BLOCK_SIZE && size != EC_VBNV_BLOCK_SIZE_V2)
		return -EINVAL;
	p.op = EC_VBNV_CONTEXT_OP_WRITE;
	memcpy(p.block, block, size);

	len = ec_command_inptr(dev, EC_CMD_VBNV_CONTEXT, EC_VER_VBNV_CONTEXT,
			&p, sizeof(uint32_t) + size, NULL, 0);
	if (len < 0)
		return -1;

	return 0;
}

int cros_ec_battery_cutoff(struct udevice *dev, uint8_t flags)
{
	struct ec_params_battery_cutoff p;
	int len;

	p.flags = flags;
	len = ec_command(dev, EC_CMD_BATTERY_CUT_OFF, 1, &p, sizeof(p),
			 NULL, 0);

	if (len < 0)
		return -1;
	return 0;
}

int cros_ec_set_pwm_duty(struct udevice *dev, uint8_t index, uint16_t duty)
{
	struct ec_params_pwm_set_duty p;
	int ret;

	p.duty = duty;
	p.pwm_type = EC_PWM_TYPE_GENERIC;
	p.index = index;

	ret = ec_command(dev, EC_CMD_PWM_SET_DUTY, 0, &p, sizeof(p),
			 NULL, 0);
	if (ret < 0)
		return ret;

	return 0;
}

int cros_ec_set_ldo(struct udevice *dev, uint8_t index, uint8_t state)
{
	struct ec_params_ldo_set params;

	params.index = index;
	params.state = state;

	if (ec_command_inptr(dev, EC_CMD_LDO_SET, 0, &params, sizeof(params),
			     NULL, 0))
		return -1;

	return 0;
}

int cros_ec_get_ldo(struct udevice *dev, uint8_t index, uint8_t *state)
{
	struct ec_params_ldo_get params;
	struct ec_response_ldo_get *resp;

	params.index = index;

	if (ec_command_inptr(dev, EC_CMD_LDO_GET, 0, &params, sizeof(params),
			     (uint8_t **)&resp, sizeof(*resp)) !=
			     sizeof(*resp))
		return -1;

	*state = resp->state;

	return 0;
}

int cros_ec_register(struct udevice *dev)
{
	struct cros_ec_dev *cdev = dev_get_uclass_priv(dev);
	char id[MSG_BYTES];

	cdev->dev = dev;
	gpio_request_by_name(dev, "ec-interrupt", 0, &cdev->ec_int,
			     GPIOD_IS_IN);
	cdev->optimise_flash_write = dev_read_bool(dev, "optimise-flash-write");

	if (cros_ec_check_version(dev)) {
		debug("%s: Could not detect CROS-EC version\n", __func__);
		return -CROS_EC_ERR_CHECK_VERSION;
	}

	if (cros_ec_read_id(dev, id, sizeof(id))) {
		debug("%s: Could not read KBC ID\n", __func__);
		return -CROS_EC_ERR_READ_ID;
	}

	/* Remember this device for use by the cros_ec command */
	debug("Google Chrome EC v%d CROS-EC driver ready, id '%s'\n",
	      cdev->protocol_version, id);

	return 0;
}

int cros_ec_decode_ec_flash(struct udevice *dev, struct fdt_cros_ec *config)
{
	ofnode flash_node, node;

	flash_node = dev_read_subnode(dev, "flash");
	if (!ofnode_valid(flash_node)) {
		debug("Failed to find flash node\n");
		return -1;
	}

	if (ofnode_read_fmap_entry(flash_node,  &config->flash)) {
		debug("Failed to decode flash node in chrome-ec\n");
		return -1;
	}

	config->flash_erase_value = ofnode_read_s32_default(flash_node,
							    "erase-value", -1);
	ofnode_for_each_subnode(node, flash_node) {
		const char *name = ofnode_get_name(node);
		enum ec_flash_region region;

		if (0 == strcmp(name, "ro")) {
			region = EC_FLASH_REGION_RO;
		} else if (0 == strcmp(name, "rw")) {
			region = EC_FLASH_REGION_ACTIVE;
		} else if (0 == strcmp(name, "wp-ro")) {
			region = EC_FLASH_REGION_WP_RO;
		} else {
			debug("Unknown EC flash region name '%s'\n", name);
			return -1;
		}

		if (ofnode_read_fmap_entry(node, &config->region[region])) {
			debug("Failed to decode flash region in chrome-ec'\n");
			return -1;
		}
	}

	return 0;
}

int cros_ec_i2c_tunnel(struct udevice *dev, int port, struct i2c_msg *in,
		       int nmsgs)
{
	union {
		struct ec_params_i2c_passthru p;
		uint8_t outbuf[EC_PROTO2_MAX_PARAM_SIZE];
	} params;
	union {
		struct ec_response_i2c_passthru r;
		uint8_t inbuf[EC_PROTO2_MAX_PARAM_SIZE];
	} response;
	struct ec_params_i2c_passthru *p = &params.p;
	struct ec_response_i2c_passthru *r = &response.r;
	struct ec_params_i2c_passthru_msg *msg;
	uint8_t *pdata, *read_ptr = NULL;
	int read_len;
	int size;
	int rv;
	int i;

	p->port = port;

	p->num_msgs = nmsgs;
	size = sizeof(*p) + p->num_msgs * sizeof(*msg);

	/* Create a message to write the register address and optional data */
	pdata = (uint8_t *)p + size;

	read_len = 0;
	for (i = 0, msg = p->msg; i < nmsgs; i++, msg++, in++) {
		bool is_read = in->flags & I2C_M_RD;

		msg->addr_flags = in->addr;
		msg->len = in->len;
		if (is_read) {
			msg->addr_flags |= EC_I2C_FLAG_READ;
			read_len += in->len;
			read_ptr = in->buf;
			if (sizeof(*r) + read_len > sizeof(response)) {
				puts("Read length too big for buffer\n");
				return -1;
			}
		} else {
			if (pdata - (uint8_t *)p + in->len > sizeof(params)) {
				puts("Params too large for buffer\n");
				return -1;
			}
			memcpy(pdata, in->buf, in->len);
			pdata += in->len;
		}
	}

	rv = ec_command(dev, EC_CMD_I2C_PASSTHRU, 0, p, pdata - (uint8_t *)p,
			r, sizeof(*r) + read_len);
	if (rv < 0)
		return rv;

	/* Parse response */
	if (r->i2c_status & EC_I2C_STATUS_ERROR) {
		printf("Transfer failed with status=0x%x\n", r->i2c_status);
		return -1;
	}

	if (rv < sizeof(*r) + read_len) {
		puts("Truncated read response\n");
		return -1;
	}

	/* We only support a single read message for each transfer */
	if (read_len)
		memcpy(read_ptr, r->data, read_len);

	return 0;
}

int cros_ec_get_features(struct udevice *dev, u64 *featuresp)
{
	struct ec_response_get_features r;
	int rv;

	rv = ec_command(dev, EC_CMD_GET_FEATURES, 0, NULL, 0, &r, sizeof(r));
	if (rv != sizeof(r))
		return -EIO;
	*featuresp = r.flags[0] | (u64)r.flags[1] << 32;

	return 0;
}

int cros_ec_check_feature(struct udevice *dev, uint feature)
{
	struct ec_response_get_features r;
	int rv;

	rv = ec_command(dev, EC_CMD_GET_FEATURES, 0, NULL, 0, &r, sizeof(r));
	if (rv != sizeof(r))
		return -EIO;

	if (feature >= 8 * sizeof(r.flags))
		return -EINVAL;

	return r.flags[feature / 32] & EC_FEATURE_MASK_0(feature) ? true :
		 false;
}

/*
 * Query the EC for specified mask indicating enabled events.
 * The EC maintains separate event masks for SMI, SCI and WAKE.
 */
static int cros_ec_uhepi_cmd(struct udevice *dev, uint mask, uint action,
			     uint64_t *value)
{
	int ret;
	struct ec_params_host_event req;
	struct ec_response_host_event rsp;

	req.action = action;
	req.mask_type = mask;
	if (action != EC_HOST_EVENT_GET)
		req.value = *value;
	else
		*value = 0;
	ret = ec_command(dev, EC_CMD_HOST_EVENT, 0, &req, sizeof(req), &rsp,
			 sizeof(rsp));

	if (action != EC_HOST_EVENT_GET)
		return ret;
	if (ret == 0)
		*value = rsp.value;

	return ret;
}

static int cros_ec_handle_non_uhepi_cmd(struct udevice *dev, uint hcmd,
					uint action, uint64_t *value)
{
	int ret = -1;
	struct ec_params_host_event_mask req;
	struct ec_response_host_event_mask rsp;

	if (hcmd == INVALID_HCMD)
		return ret;

	if (action != EC_HOST_EVENT_GET)
		req.mask = (uint32_t)*value;
	else
		*value = 0;

	ret = ec_command(dev, hcmd, 0, &req, sizeof(req), &rsp, sizeof(rsp));
	if (action != EC_HOST_EVENT_GET)
		return ret;
	if (ret == 0)
		*value = rsp.mask;

	return ret;
}

bool cros_ec_is_uhepi_supported(struct udevice *dev)
{
#define UHEPI_SUPPORTED 1
#define UHEPI_NOT_SUPPORTED 2
	static int uhepi_support;

	if (!uhepi_support) {
		uhepi_support = cros_ec_check_feature(dev,
			EC_FEATURE_UNIFIED_WAKE_MASKS) > 0 ? UHEPI_SUPPORTED :
			UHEPI_NOT_SUPPORTED;
		log_debug("Chrome EC: UHEPI %s\n",
			  uhepi_support == UHEPI_SUPPORTED ? "supported" :
			  "not supported");
	}
	return uhepi_support == UHEPI_SUPPORTED;
}

static int cros_ec_get_mask(struct udevice *dev, uint type)
{
	u64 value = 0;

	if (cros_ec_is_uhepi_supported(dev)) {
		cros_ec_uhepi_cmd(dev, type, EC_HOST_EVENT_GET, &value);
	} else {
		assert(type < ARRAY_SIZE(event_map));
		cros_ec_handle_non_uhepi_cmd(dev, event_map[type].get_cmd,
					     EC_HOST_EVENT_GET, &value);
	}
	return value;
}

static int cros_ec_clear_mask(struct udevice *dev, uint type, u64 mask)
{
	if (cros_ec_is_uhepi_supported(dev))
		return cros_ec_uhepi_cmd(dev, type, EC_HOST_EVENT_CLEAR, &mask);

	assert(type < ARRAY_SIZE(event_map));

	return cros_ec_handle_non_uhepi_cmd(dev, event_map[type].clear_cmd,
					    EC_HOST_EVENT_CLEAR, &mask);
}

uint64_t cros_ec_get_events_b(struct udevice *dev)
{
	return cros_ec_get_mask(dev, EC_HOST_EVENT_B);
}

int cros_ec_clear_events_b(struct udevice *dev, uint64_t mask)
{
	log_debug("Chrome EC: clear events_b mask to 0x%016llx\n", mask);

	return cros_ec_clear_mask(dev, EC_HOST_EVENT_B, mask);
}

int cros_ec_read_limit_power(struct udevice *dev, int *limit_powerp)
{
	struct ec_params_charge_state p;
	struct ec_response_charge_state r;
	int ret;

	p.cmd = CHARGE_STATE_CMD_GET_PARAM;
	p.get_param.param = CS_PARAM_LIMIT_POWER;
	ret = ec_command(dev, EC_CMD_CHARGE_STATE, 0, &p, sizeof(p),
			 &r, sizeof(r));

	/*
	 * If our EC doesn't support the LIMIT_POWER parameter, assume that
	 * LIMIT_POWER is not requested.
	 */
	if (ret == -EC_RES_INVALID_PARAM || ret == -EC_RES_INVALID_COMMAND) {
		log_warning("PARAM_LIMIT_POWER not supported by EC\n");
		return -ENOSYS;
	}

	if (ret != sizeof(r.get_param))
		return -EINVAL;

	*limit_powerp = r.get_param.value;
	return 0;
}

int cros_ec_config_powerbtn(struct udevice *dev, uint32_t flags)
{
	struct ec_params_config_power_button params;
	int ret;

	params.flags = flags;
	ret = ec_command(dev, EC_CMD_CONFIG_POWER_BUTTON, 0,
			 &params, sizeof(params), NULL, 0);
	if (ret < 0)
		return ret;

	return 0;
}

int cros_ec_get_lid_shutdown_mask(struct udevice *dev)
{
	u32 mask;
	int ret;

	ret = cros_ec_get_event_mask(dev, EC_CMD_HOST_EVENT_GET_SMI_MASK,
				     &mask);
	if (ret < 0)
		return ret;

	return !!(mask & EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_CLOSED));
}

int cros_ec_set_lid_shutdown_mask(struct udevice *dev, int enable)
{
	u32 mask;
	int ret;

	ret = cros_ec_get_event_mask(dev, EC_CMD_HOST_EVENT_GET_SMI_MASK,
				     &mask);
	if (ret < 0)
		return ret;

	/* Set lid close event state in the EC SMI event mask */
	if (enable)
		mask |= EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_CLOSED);
	else
		mask &= ~EC_HOST_EVENT_MASK(EC_HOST_EVENT_LID_CLOSED);

	ret = cros_ec_set_event_mask(dev, EC_CMD_HOST_EVENT_SET_SMI_MASK, mask);
	if (ret < 0)
		return ret;

	printf("EC: %sabled lid close event\n", enable ? "en" : "dis");
	return 0;
}

int cros_ec_vstore_supported(struct udevice *dev)
{
	return cros_ec_check_feature(dev, EC_FEATURE_VSTORE);
}

int cros_ec_vstore_info(struct udevice *dev, u32 *lockedp)
{
	struct ec_response_vstore_info *resp;

	if (ec_command_inptr(dev, EC_CMD_VSTORE_INFO, 0, NULL, 0,
			     (uint8_t **)&resp, sizeof(*resp)) != sizeof(*resp))
		return -EIO;

	if (lockedp)
		*lockedp = resp->slot_locked;

	return resp->slot_count;
}

/*
 * cros_ec_vstore_read - Read data from EC vstore slot
 *
 * @slot: vstore slot to read from
 * @data: buffer to store read data, must be EC_VSTORE_SLOT_SIZE bytes
 */
int cros_ec_vstore_read(struct udevice *dev, int slot, uint8_t *data)
{
	struct ec_params_vstore_read req;
	struct ec_response_vstore_read *resp;

	req.slot = slot;
	if (ec_command_inptr(dev, EC_CMD_VSTORE_READ, 0, &req, sizeof(req),
			     (uint8_t **)&resp, sizeof(*resp)) != sizeof(*resp))
		return -EIO;

	if (!data || req.slot >= EC_VSTORE_SLOT_MAX)
		return -EINVAL;

	memcpy(data, resp->data, sizeof(resp->data));

	return 0;
}

/*
 * cros_ec_vstore_write - Save data into EC vstore slot
 *
 * @slot: vstore slot to write into
 * @data: data to write
 * @size: size of data in bytes
 *
 * Maximum size of data is EC_VSTORE_SLOT_SIZE.  It is the callers
 * responsibility to check the number of implemented slots by
 * querying the vstore info.
 */
int cros_ec_vstore_write(struct udevice *dev, int slot, const uint8_t *data,
			 size_t size)
{
	struct ec_params_vstore_write req;

	if (slot >= EC_VSTORE_SLOT_MAX || size > EC_VSTORE_SLOT_SIZE)
		return -EINVAL;

	req.slot = slot;
	memcpy(req.data, data, size);

	if (ec_command(dev, EC_CMD_VSTORE_WRITE, 0, &req, sizeof(req), NULL, 0))
		return -EIO;

	return 0;
}

int cros_ec_get_switches(struct udevice *dev)
{
	struct dm_cros_ec_ops *ops;
	int ret;

	ops = dm_cros_ec_get_ops(dev);
	if (!ops->get_switches)
		return -ENOSYS;

	ret = ops->get_switches(dev);
	if (ret < 0)
		return log_msg_ret("get", ret);

	return ret;
}

int cros_ec_read_batt_charge(struct udevice *dev, uint *chargep)
{
	struct ec_params_charge_state req;
	struct ec_response_charge_state resp;
	int ret;

	req.cmd = CHARGE_STATE_CMD_GET_STATE;
	ret = ec_command(dev, EC_CMD_CHARGE_STATE, 0, &req, sizeof(req),
			 &resp, sizeof(resp));
	if (ret)
		return log_msg_ret("read", ret);

	*chargep = resp.get_state.batt_state_of_charge;

	return 0;
}

UCLASS_DRIVER(cros_ec) = {
	.id		= UCLASS_CROS_EC,
	.name		= "cros-ec",
	.per_device_auto	= sizeof(struct cros_ec_dev),
#if CONFIG_IS_ENABLED(OF_REAL)
	.post_bind	= dm_scan_fdt_dev,
#endif
	.flags		= DM_UC_FLAG_ALLOC_PRIV_DMA,
};
