// SPDX-License-Identifier: GPL-2.0-only
/*
 * drivers/mfd/si476x-cmd.c -- Subroutines implementing command
 * protocol of si476x series of chips
 *
 * Copyright (C) 2012 Innovative Converged Devices(ICD)
 * Copyright (C) 2013 Andrey Smirnov
 *
 * Author: Andrey Smirnov <andrew.smirnov@gmail.com>
 */

#include <linux/module.h>
#include <linux/completion.h>
#include <linux/delay.h>
#include <linux/atomic.h>
#include <linux/i2c.h>
#include <linux/device.h>
#include <linux/gpio.h>
#include <linux/videodev2.h>

#include <linux/mfd/si476x-core.h>

#include <asm/unaligned.h>

#define msb(x)                  ((u8)((u16) x >> 8))
#define lsb(x)                  ((u8)((u16) x &  0x00FF))



#define CMD_POWER_UP				0x01
#define CMD_POWER_UP_A10_NRESP			1
#define CMD_POWER_UP_A10_NARGS			5

#define CMD_POWER_UP_A20_NRESP			1
#define CMD_POWER_UP_A20_NARGS			5

#define POWER_UP_DELAY_MS			110

#define CMD_POWER_DOWN				0x11
#define CMD_POWER_DOWN_A10_NRESP		1

#define CMD_POWER_DOWN_A20_NRESP		1
#define CMD_POWER_DOWN_A20_NARGS		1

#define CMD_FUNC_INFO				0x12
#define CMD_FUNC_INFO_NRESP			7

#define CMD_SET_PROPERTY			0x13
#define CMD_SET_PROPERTY_NARGS			5
#define CMD_SET_PROPERTY_NRESP			1

#define CMD_GET_PROPERTY			0x14
#define CMD_GET_PROPERTY_NARGS			3
#define CMD_GET_PROPERTY_NRESP			4

#define CMD_AGC_STATUS				0x17
#define CMD_AGC_STATUS_NRESP_A10		2
#define CMD_AGC_STATUS_NRESP_A20                6

#define PIN_CFG_BYTE(x) (0x7F & (x))
#define CMD_DIG_AUDIO_PIN_CFG			0x18
#define CMD_DIG_AUDIO_PIN_CFG_NARGS		4
#define CMD_DIG_AUDIO_PIN_CFG_NRESP		5

#define CMD_ZIF_PIN_CFG				0x19
#define CMD_ZIF_PIN_CFG_NARGS			4
#define CMD_ZIF_PIN_CFG_NRESP			5

#define CMD_IC_LINK_GPO_CTL_PIN_CFG		0x1A
#define CMD_IC_LINK_GPO_CTL_PIN_CFG_NARGS	4
#define CMD_IC_LINK_GPO_CTL_PIN_CFG_NRESP	5

#define CMD_ANA_AUDIO_PIN_CFG			0x1B
#define CMD_ANA_AUDIO_PIN_CFG_NARGS		1
#define CMD_ANA_AUDIO_PIN_CFG_NRESP		2

#define CMD_INTB_PIN_CFG			0x1C
#define CMD_INTB_PIN_CFG_NARGS			2
#define CMD_INTB_PIN_CFG_A10_NRESP		6
#define CMD_INTB_PIN_CFG_A20_NRESP		3

#define CMD_FM_TUNE_FREQ			0x30
#define CMD_FM_TUNE_FREQ_A10_NARGS		5
#define CMD_FM_TUNE_FREQ_A20_NARGS		3
#define CMD_FM_TUNE_FREQ_NRESP			1

#define CMD_FM_RSQ_STATUS			0x32

#define CMD_FM_RSQ_STATUS_A10_NARGS		1
#define CMD_FM_RSQ_STATUS_A10_NRESP		17
#define CMD_FM_RSQ_STATUS_A30_NARGS		1
#define CMD_FM_RSQ_STATUS_A30_NRESP		23


#define CMD_FM_SEEK_START			0x31
#define CMD_FM_SEEK_START_NARGS			1
#define CMD_FM_SEEK_START_NRESP			1

#define CMD_FM_RDS_STATUS			0x36
#define CMD_FM_RDS_STATUS_NARGS			1
#define CMD_FM_RDS_STATUS_NRESP			16

#define CMD_FM_RDS_BLOCKCOUNT			0x37
#define CMD_FM_RDS_BLOCKCOUNT_NARGS		1
#define CMD_FM_RDS_BLOCKCOUNT_NRESP		8

#define CMD_FM_PHASE_DIVERSITY			0x38
#define CMD_FM_PHASE_DIVERSITY_NARGS		1
#define CMD_FM_PHASE_DIVERSITY_NRESP		1

#define CMD_FM_PHASE_DIV_STATUS			0x39
#define CMD_FM_PHASE_DIV_STATUS_NRESP		2

#define CMD_AM_TUNE_FREQ			0x40
#define CMD_AM_TUNE_FREQ_NARGS			3
#define CMD_AM_TUNE_FREQ_NRESP			1

#define CMD_AM_RSQ_STATUS			0x42
#define CMD_AM_RSQ_STATUS_NARGS			1
#define CMD_AM_RSQ_STATUS_NRESP			13

#define CMD_AM_SEEK_START			0x41
#define CMD_AM_SEEK_START_NARGS			1
#define CMD_AM_SEEK_START_NRESP			1


#define CMD_AM_ACF_STATUS			0x45
#define CMD_AM_ACF_STATUS_NRESP			6
#define CMD_AM_ACF_STATUS_NARGS			1

#define CMD_FM_ACF_STATUS			0x35
#define CMD_FM_ACF_STATUS_NRESP			8
#define CMD_FM_ACF_STATUS_NARGS			1

#define CMD_MAX_ARGS_COUNT			(10)


enum si476x_acf_status_report_bits {
	SI476X_ACF_BLEND_INT	= (1 << 4),
	SI476X_ACF_HIBLEND_INT	= (1 << 3),
	SI476X_ACF_HICUT_INT	= (1 << 2),
	SI476X_ACF_CHBW_INT	= (1 << 1),
	SI476X_ACF_SOFTMUTE_INT	= (1 << 0),

	SI476X_ACF_SMUTE	= (1 << 0),
	SI476X_ACF_SMATTN	= 0x1f,
	SI476X_ACF_PILOT	= (1 << 7),
	SI476X_ACF_STBLEND	= ~SI476X_ACF_PILOT,
};

enum si476x_agc_status_report_bits {
	SI476X_AGC_MXHI		= (1 << 5),
	SI476X_AGC_MXLO		= (1 << 4),
	SI476X_AGC_LNAHI	= (1 << 3),
	SI476X_AGC_LNALO	= (1 << 2),
};

enum si476x_errors {
	SI476X_ERR_BAD_COMMAND		= 0x10,
	SI476X_ERR_BAD_ARG1		= 0x11,
	SI476X_ERR_BAD_ARG2		= 0x12,
	SI476X_ERR_BAD_ARG3		= 0x13,
	SI476X_ERR_BAD_ARG4		= 0x14,
	SI476X_ERR_BUSY			= 0x18,
	SI476X_ERR_BAD_INTERNAL_MEMORY  = 0x20,
	SI476X_ERR_BAD_PATCH		= 0x30,
	SI476X_ERR_BAD_BOOT_MODE	= 0x31,
	SI476X_ERR_BAD_PROPERTY		= 0x40,
};

static int si476x_core_parse_and_nag_about_error(struct si476x_core *core)
{
	int err;
	char *cause;
	u8 buffer[2];

	if (core->revision != SI476X_REVISION_A10) {
		err = si476x_core_i2c_xfer(core, SI476X_I2C_RECV,
					   buffer, sizeof(buffer));
		if (err == sizeof(buffer)) {
			switch (buffer[1]) {
			case SI476X_ERR_BAD_COMMAND:
				cause = "Bad command";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_ARG1:
				cause = "Bad argument #1";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_ARG2:
				cause = "Bad argument #2";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_ARG3:
				cause = "Bad argument #3";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_ARG4:
				cause = "Bad argument #4";
				err = -EINVAL;
				break;
			case SI476X_ERR_BUSY:
				cause = "Chip is busy";
				err = -EBUSY;
				break;
			case SI476X_ERR_BAD_INTERNAL_MEMORY:
				cause = "Bad internal memory";
				err = -EIO;
				break;
			case SI476X_ERR_BAD_PATCH:
				cause = "Bad patch";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_BOOT_MODE:
				cause = "Bad boot mode";
				err = -EINVAL;
				break;
			case SI476X_ERR_BAD_PROPERTY:
				cause = "Bad property";
				err = -EINVAL;
				break;
			default:
				cause = "Unknown";
				err = -EIO;
			}

			dev_err(&core->client->dev,
				"[Chip error status]: %s\n", cause);
		} else {
			dev_err(&core->client->dev,
				"Failed to fetch error code\n");
			err = (err >= 0) ? -EIO : err;
		}
	} else {
		err = -EIO;
	}

	return err;
}

/**
 * si476x_core_send_command() - sends a command to si476x and waits its
 * response
 * @core:     si476x_device structure for the device we are
 *            communicating with
 * @command:  command id
 * @args:     command arguments we are sending
 * @argn:     actual size of @args
 * @resp:     buffer to place the expected response from the device
 * @respn:    actual size of @resp
 * @usecs:    amount of time to wait before reading the response (in
 *            usecs)
 *
 * Function returns 0 on succsess and negative error code on
 * failure
 */
static int si476x_core_send_command(struct si476x_core *core,
				    const u8 command,
				    const u8 args[],
				    const int argn,
				    u8 resp[],
				    const int respn,
				    const int usecs)
{
	struct i2c_client *client = core->client;
	int err;
	u8  data[CMD_MAX_ARGS_COUNT + 1];

	if (argn > CMD_MAX_ARGS_COUNT) {
		err = -ENOMEM;
		goto exit;
	}

	if (!client->adapter) {
		err = -ENODEV;
		goto exit;
	}

	/* First send the command and its arguments */
	data[0] = command;
	memcpy(&data[1], args, argn);
	dev_dbg(&client->dev, "Command:\n %*ph\n", argn + 1, data);

	err = si476x_core_i2c_xfer(core, SI476X_I2C_SEND,
				   (char *) data, argn + 1);
	if (err != argn + 1) {
		dev_err(&core->client->dev,
			"Error while sending command 0x%02x\n",
			command);
		err = (err >= 0) ? -EIO : err;
		goto exit;
	}
	/* Set CTS to zero only after the command is send to avoid
	 * possible racing conditions when working in polling mode */
	atomic_set(&core->cts, 0);

	/* if (unlikely(command == CMD_POWER_DOWN) */
	if (!wait_event_timeout(core->command,
				atomic_read(&core->cts),
				usecs_to_jiffies(usecs) + 1))
		dev_warn(&core->client->dev,
			 "(%s) [CMD 0x%02x] Answer timeout.\n",
			 __func__, command);

	/*
	  When working in polling mode, for some reason the tuner will
	  report CTS bit as being set in the first status byte read,
	  but all the consequtive ones will return zeros until the
	  tuner is actually completed the POWER_UP command. To
	  workaround that we wait for second CTS to be reported
	 */
	if (unlikely(!core->client->irq && command == CMD_POWER_UP)) {
		if (!wait_event_timeout(core->command,
					atomic_read(&core->cts),
					usecs_to_jiffies(usecs) + 1))
			dev_warn(&core->client->dev,
				 "(%s) Power up took too much time.\n",
				 __func__);
	}

	/* Then get the response */
	err = si476x_core_i2c_xfer(core, SI476X_I2C_RECV, resp, respn);
	if (err != respn) {
		dev_err(&core->client->dev,
			"Error while reading response for command 0x%02x\n",
			command);
		err = (err >= 0) ? -EIO : err;
		goto exit;
	}
	dev_dbg(&client->dev, "Response:\n %*ph\n", respn, resp);

	err = 0;

	if (resp[0] & SI476X_ERR) {
		dev_err(&core->client->dev,
			"[CMD 0x%02x] Chip set error flag\n", command);
		err = si476x_core_parse_and_nag_about_error(core);
		goto exit;
	}

	if (!(resp[0] & SI476X_CTS))
		err = -EBUSY;
exit:
	return err;
}

static int si476x_cmd_clear_stc(struct si476x_core *core)
{
	int err;
	struct si476x_rsq_status_args args = {
		.primary	= false,
		.rsqack		= false,
		.attune		= false,
		.cancel		= false,
		.stcack		= true,
	};

	switch (core->power_up_parameters.func) {
	case SI476X_FUNC_FM_RECEIVER:
		err = si476x_core_cmd_fm_rsq_status(core, &args, NULL);
		break;
	case SI476X_FUNC_AM_RECEIVER:
		err = si476x_core_cmd_am_rsq_status(core, &args, NULL);
		break;
	default:
		err = -EINVAL;
	}

	return err;
}

static int si476x_cmd_tune_seek_freq(struct si476x_core *core,
				     uint8_t cmd,
				     const uint8_t args[], size_t argn,
				     uint8_t *resp, size_t respn)
{
	int err;


	atomic_set(&core->stc, 0);
	err = si476x_core_send_command(core, cmd, args, argn, resp, respn,
				       SI476X_TIMEOUT_TUNE);
	if (!err) {
		wait_event_killable(core->tuning,
				    atomic_read(&core->stc));
		si476x_cmd_clear_stc(core);
	}

	return err;
}

/**
 * si476x_cmd_func_info() - send 'FUNC_INFO' command to the device
 * @core: device to send the command to
 * @info:  struct si476x_func_info to fill all the information
 *         returned by the command
 *
 * The command requests the firmware and patch version for currently
 * loaded firmware (dependent on the function of the device FM/AM/WB)
 *
 * Function returns 0 on succsess and negative error code on
 * failure
 */
int si476x_core_cmd_func_info(struct si476x_core *core,
			      struct si476x_func_info *info)
{
	int err;
	u8  resp[CMD_FUNC_INFO_NRESP];

	err = si476x_core_send_command(core, CMD_FUNC_INFO,
				       NULL, 0,
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);

	info->firmware.major    = resp[1];
	info->firmware.minor[0] = resp[2];
	info->firmware.minor[1] = resp[3];

	info->patch_id = ((u16) resp[4] << 8) | resp[5];
	info->func     = resp[6];

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_func_info);

/**
 * si476x_cmd_set_property() - send 'SET_PROPERTY' command to the device
 * @core:    device to send the command to
 * @property: property address
 * @value:    property value
 *
 * Function returns 0 on succsess and negative error code on
 * failure
 */
int si476x_core_cmd_set_property(struct si476x_core *core,
				 u16 property, u16 value)
{
	u8       resp[CMD_SET_PROPERTY_NRESP];
	const u8 args[CMD_SET_PROPERTY_NARGS] = {
		0x00,
		msb(property),
		lsb(property),
		msb(value),
		lsb(value),
	};

	return si476x_core_send_command(core, CMD_SET_PROPERTY,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_set_property);

/**
 * si476x_cmd_get_property() - send 'GET_PROPERTY' command to the device
 * @core:    device to send the command to
 * @property: property address
 *
 * Function return the value of property as u16 on success or a
 * negative error on failure
 */
int si476x_core_cmd_get_property(struct si476x_core *core, u16 property)
{
	int err;
	u8       resp[CMD_GET_PROPERTY_NRESP];
	const u8 args[CMD_GET_PROPERTY_NARGS] = {
		0x00,
		msb(property),
		lsb(property),
	};

	err = si476x_core_send_command(core, CMD_GET_PROPERTY,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	if (err < 0)
		return err;
	else
		return get_unaligned_be16(resp + 2);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_get_property);

/**
 * si476x_cmd_dig_audio_pin_cfg() - send 'DIG_AUDIO_PIN_CFG' command to
 * the device
 * @core: device to send the command to
 * @dclk:  DCLK pin function configuration:
 *	   #SI476X_DCLK_NOOP     - do not modify the behaviour
 *         #SI476X_DCLK_TRISTATE - put the pin in tristate condition,
 *                                 enable 1MOhm pulldown
 *         #SI476X_DCLK_DAUDIO   - set the pin to be a part of digital
 *                                 audio interface
 * @dfs:   DFS pin function configuration:
 *         #SI476X_DFS_NOOP      - do not modify the behaviour
 *         #SI476X_DFS_TRISTATE  - put the pin in tristate condition,
 *                             enable 1MOhm pulldown
 *      SI476X_DFS_DAUDIO    - set the pin to be a part of digital
 *                             audio interface
 * @dout: - DOUT pin function configuration:
 *      SI476X_DOUT_NOOP       - do not modify the behaviour
 *      SI476X_DOUT_TRISTATE   - put the pin in tristate condition,
 *                               enable 1MOhm pulldown
 *      SI476X_DOUT_I2S_OUTPUT - set this pin to be digital out on I2S
 *                               port 1
 *      SI476X_DOUT_I2S_INPUT  - set this pin to be digital in on I2S
 *                               port 1
 * @xout: - XOUT pin function configuration:
 *	SI476X_XOUT_NOOP        - do not modify the behaviour
 *      SI476X_XOUT_TRISTATE    - put the pin in tristate condition,
 *                                enable 1MOhm pulldown
 *      SI476X_XOUT_I2S_INPUT   - set this pin to be digital in on I2S
 *                                port 1
 *      SI476X_XOUT_MODE_SELECT - set this pin to be the input that
 *                                selects the mode of the I2S audio
 *                                combiner (analog or HD)
 *                                [SI4761/63/65/67 Only]
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_dig_audio_pin_cfg(struct  si476x_core *core,
				      enum si476x_dclk_config dclk,
				      enum si476x_dfs_config  dfs,
				      enum si476x_dout_config dout,
				      enum si476x_xout_config xout)
{
	u8       resp[CMD_DIG_AUDIO_PIN_CFG_NRESP];
	const u8 args[CMD_DIG_AUDIO_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(dclk),
		PIN_CFG_BYTE(dfs),
		PIN_CFG_BYTE(dout),
		PIN_CFG_BYTE(xout),
	};

	return si476x_core_send_command(core, CMD_DIG_AUDIO_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_dig_audio_pin_cfg);

/**
 * si476x_cmd_zif_pin_cfg - send 'ZIF_PIN_CFG_COMMAND'
 * @core: - device to send the command to
 * @iqclk: - IQCL pin function configuration:
 *       SI476X_IQCLK_NOOP     - do not modify the behaviour
 *       SI476X_IQCLK_TRISTATE - put the pin in tristate condition,
 *                               enable 1MOhm pulldown
 *       SI476X_IQCLK_IQ       - set pin to be a part of I/Q interace
 *                               in master mode
 * @iqfs: - IQFS pin function configuration:
 *       SI476X_IQFS_NOOP     - do not modify the behaviour
 *       SI476X_IQFS_TRISTATE - put the pin in tristate condition,
 *                              enable 1MOhm pulldown
 *       SI476X_IQFS_IQ       - set pin to be a part of I/Q interace
 *                              in master mode
 * @iout: - IOUT pin function configuration:
 *       SI476X_IOUT_NOOP     - do not modify the behaviour
 *       SI476X_IOUT_TRISTATE - put the pin in tristate condition,
 *                              enable 1MOhm pulldown
 *       SI476X_IOUT_OUTPUT   - set pin to be I out
 * @qout: - QOUT pin function configuration:
 *       SI476X_QOUT_NOOP     - do not modify the behaviour
 *       SI476X_QOUT_TRISTATE - put the pin in tristate condition,
 *                              enable 1MOhm pulldown
 *       SI476X_QOUT_OUTPUT   - set pin to be Q out
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_zif_pin_cfg(struct si476x_core *core,
				enum si476x_iqclk_config iqclk,
				enum si476x_iqfs_config iqfs,
				enum si476x_iout_config iout,
				enum si476x_qout_config qout)
{
	u8       resp[CMD_ZIF_PIN_CFG_NRESP];
	const u8 args[CMD_ZIF_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(iqclk),
		PIN_CFG_BYTE(iqfs),
		PIN_CFG_BYTE(iout),
		PIN_CFG_BYTE(qout),
	};

	return si476x_core_send_command(core, CMD_ZIF_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_zif_pin_cfg);

/**
 * si476x_cmd_ic_link_gpo_ctl_pin_cfg - send
 * 'IC_LINK_GPIO_CTL_PIN_CFG' comand to the device
 * @core: - device to send the command to
 * @icin: - ICIN pin function configuration:
 *      SI476X_ICIN_NOOP      - do not modify the behaviour
 *      SI476X_ICIN_TRISTATE  - put the pin in tristate condition,
 *                              enable 1MOhm pulldown
 *      SI476X_ICIN_GPO1_HIGH - set pin to be an output, drive it high
 *      SI476X_ICIN_GPO1_LOW  - set pin to be an output, drive it low
 *      SI476X_ICIN_IC_LINK   - set the pin to be a part of Inter-Chip link
 * @icip: - ICIP pin function configuration:
 *      SI476X_ICIP_NOOP      - do not modify the behaviour
 *      SI476X_ICIP_TRISTATE  - put the pin in tristate condition,
 *                              enable 1MOhm pulldown
 *      SI476X_ICIP_GPO1_HIGH - set pin to be an output, drive it high
 *      SI476X_ICIP_GPO1_LOW  - set pin to be an output, drive it low
 *      SI476X_ICIP_IC_LINK   - set the pin to be a part of Inter-Chip link
 * @icon: - ICON pin function configuration:
 *      SI476X_ICON_NOOP     - do not modify the behaviour
 *      SI476X_ICON_TRISTATE - put the pin in tristate condition,
 *                             enable 1MOhm pulldown
 *      SI476X_ICON_I2S      - set the pin to be a part of audio
 *                             interface in slave mode (DCLK)
 *      SI476X_ICON_IC_LINK  - set the pin to be a part of Inter-Chip link
 * @icop: - ICOP pin function configuration:
 *      SI476X_ICOP_NOOP     - do not modify the behaviour
 *      SI476X_ICOP_TRISTATE - put the pin in tristate condition,
 *                             enable 1MOhm pulldown
 *      SI476X_ICOP_I2S      - set the pin to be a part of audio
 *                             interface in slave mode (DOUT)
 *                             [Si4761/63/65/67 Only]
 *      SI476X_ICOP_IC_LINK  - set the pin to be a part of Inter-Chip link
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_ic_link_gpo_ctl_pin_cfg(struct si476x_core *core,
					    enum si476x_icin_config icin,
					    enum si476x_icip_config icip,
					    enum si476x_icon_config icon,
					    enum si476x_icop_config icop)
{
	u8       resp[CMD_IC_LINK_GPO_CTL_PIN_CFG_NRESP];
	const u8 args[CMD_IC_LINK_GPO_CTL_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(icin),
		PIN_CFG_BYTE(icip),
		PIN_CFG_BYTE(icon),
		PIN_CFG_BYTE(icop),
	};

	return si476x_core_send_command(core, CMD_IC_LINK_GPO_CTL_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_ic_link_gpo_ctl_pin_cfg);

/**
 * si476x_cmd_ana_audio_pin_cfg - send 'ANA_AUDIO_PIN_CFG' to the
 * device
 * @core: - device to send the command to
 * @lrout: - LROUT pin function configuration:
 *       SI476X_LROUT_NOOP     - do not modify the behaviour
 *       SI476X_LROUT_TRISTATE - put the pin in tristate condition,
 *                               enable 1MOhm pulldown
 *       SI476X_LROUT_AUDIO    - set pin to be audio output
 *       SI476X_LROUT_MPX      - set pin to be MPX output
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_ana_audio_pin_cfg(struct si476x_core *core,
				      enum si476x_lrout_config lrout)
{
	u8       resp[CMD_ANA_AUDIO_PIN_CFG_NRESP];
	const u8 args[CMD_ANA_AUDIO_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(lrout),
	};

	return si476x_core_send_command(core, CMD_ANA_AUDIO_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_ana_audio_pin_cfg);


/**
 * si476x_cmd_intb_pin_cfg - send 'INTB_PIN_CFG' command to the device
 * @core: - device to send the command to
 * @intb: - INTB pin function configuration:
 *      SI476X_INTB_NOOP     - do not modify the behaviour
 *      SI476X_INTB_TRISTATE - put the pin in tristate condition,
 *                             enable 1MOhm pulldown
 *      SI476X_INTB_DAUDIO   - set pin to be a part of digital
 *                             audio interface in slave mode
 *      SI476X_INTB_IRQ      - set pin to be an interrupt request line
 * @a1: - A1 pin function configuration:
 *      SI476X_A1_NOOP     - do not modify the behaviour
 *      SI476X_A1_TRISTATE - put the pin in tristate condition,
 *                           enable 1MOhm pulldown
 *      SI476X_A1_IRQ      - set pin to be an interrupt request line
 *
 * Function returns 0 on success and negative error code on failure
 */
static int si476x_core_cmd_intb_pin_cfg_a10(struct si476x_core *core,
					    enum si476x_intb_config intb,
					    enum si476x_a1_config a1)
{
	u8       resp[CMD_INTB_PIN_CFG_A10_NRESP];
	const u8 args[CMD_INTB_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(intb),
		PIN_CFG_BYTE(a1),
	};

	return si476x_core_send_command(core, CMD_INTB_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}

static int si476x_core_cmd_intb_pin_cfg_a20(struct si476x_core *core,
					    enum si476x_intb_config intb,
					    enum si476x_a1_config a1)
{
	u8       resp[CMD_INTB_PIN_CFG_A20_NRESP];
	const u8 args[CMD_INTB_PIN_CFG_NARGS] = {
		PIN_CFG_BYTE(intb),
		PIN_CFG_BYTE(a1),
	};

	return si476x_core_send_command(core, CMD_INTB_PIN_CFG,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}



/**
 * si476x_cmd_am_rsq_status - send 'AM_RSQ_STATUS' command to the
 * device
 * @core:  - device to send the command to
 * @rsqargs: - pointer to a structure containing a group of sub-args
 *             relevant to sending the RSQ status command
 * @report: - all signal quality information retured by the command
 *           (if NULL then the output of the command is ignored)
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_am_rsq_status(struct si476x_core *core,
				  struct si476x_rsq_status_args *rsqargs,
				  struct si476x_rsq_status_report *report)
{
	int err;
	u8       resp[CMD_AM_RSQ_STATUS_NRESP];
	const u8 args[CMD_AM_RSQ_STATUS_NARGS] = {
		rsqargs->rsqack << 3 | rsqargs->attune << 2 |
		rsqargs->cancel << 1 | rsqargs->stcack,
	};

	err = si476x_core_send_command(core, CMD_AM_RSQ_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	/*
	 * Besides getting received signal quality information this
	 * command can be used to just acknowledge different interrupt
	 * flags in those cases it is useless to copy and parse
	 * received data so user can pass NULL, and thus avoid
	 * unnecessary copying.
	 */
	if (!report)
		return err;

	report->snrhint		= 0x08 & resp[1];
	report->snrlint		= 0x04 & resp[1];
	report->rssihint	= 0x02 & resp[1];
	report->rssilint	= 0x01 & resp[1];

	report->bltf		= 0x80 & resp[2];
	report->snr_ready	= 0x20 & resp[2];
	report->rssiready	= 0x08 & resp[2];
	report->afcrl		= 0x02 & resp[2];
	report->valid		= 0x01 & resp[2];

	report->readfreq	= get_unaligned_be16(resp + 3);
	report->freqoff		= resp[5];
	report->rssi		= resp[6];
	report->snr		= resp[7];
	report->lassi		= resp[9];
	report->hassi		= resp[10];
	report->mult		= resp[11];
	report->dev		= resp[12];

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_am_rsq_status);

int si476x_core_cmd_fm_acf_status(struct si476x_core *core,
			     struct si476x_acf_status_report *report)
{
	int err;
	u8       resp[CMD_FM_ACF_STATUS_NRESP];
	const u8 args[CMD_FM_ACF_STATUS_NARGS] = {
		0x0,
	};

	if (!report)
		return -EINVAL;

	err = si476x_core_send_command(core, CMD_FM_ACF_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	if (err < 0)
		return err;

	report->blend_int	= resp[1] & SI476X_ACF_BLEND_INT;
	report->hblend_int	= resp[1] & SI476X_ACF_HIBLEND_INT;
	report->hicut_int	= resp[1] & SI476X_ACF_HICUT_INT;
	report->chbw_int	= resp[1] & SI476X_ACF_CHBW_INT;
	report->softmute_int	= resp[1] & SI476X_ACF_SOFTMUTE_INT;
	report->smute		= resp[2] & SI476X_ACF_SMUTE;
	report->smattn		= resp[3] & SI476X_ACF_SMATTN;
	report->chbw		= resp[4];
	report->hicut		= resp[5];
	report->hiblend		= resp[6];
	report->pilot		= resp[7] & SI476X_ACF_PILOT;
	report->stblend		= resp[7] & SI476X_ACF_STBLEND;

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_acf_status);

int si476x_core_cmd_am_acf_status(struct si476x_core *core,
				  struct si476x_acf_status_report *report)
{
	int err;
	u8       resp[CMD_AM_ACF_STATUS_NRESP];
	const u8 args[CMD_AM_ACF_STATUS_NARGS] = {
		0x0,
	};

	if (!report)
		return -EINVAL;

	err = si476x_core_send_command(core, CMD_AM_ACF_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	if (err < 0)
		return err;

	report->blend_int	= resp[1] & SI476X_ACF_BLEND_INT;
	report->hblend_int	= resp[1] & SI476X_ACF_HIBLEND_INT;
	report->hicut_int	= resp[1] & SI476X_ACF_HICUT_INT;
	report->chbw_int	= resp[1] & SI476X_ACF_CHBW_INT;
	report->softmute_int	= resp[1] & SI476X_ACF_SOFTMUTE_INT;
	report->smute		= resp[2] & SI476X_ACF_SMUTE;
	report->smattn		= resp[3] & SI476X_ACF_SMATTN;
	report->chbw		= resp[4];
	report->hicut		= resp[5];

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_am_acf_status);


/**
 * si476x_cmd_fm_seek_start - send 'FM_SEEK_START' command to the
 * device
 * @core:  - device to send the command to
 * @seekup: - if set the direction of the search is 'up'
 * @wrap:   - if set seek wraps when hitting band limit
 *
 * This function begins search for a valid station. The station is
 * considered valid when 'FM_VALID_SNR_THRESHOLD' and
 * 'FM_VALID_RSSI_THRESHOLD' and 'FM_VALID_MAX_TUNE_ERROR' criteria
 * are met.
} *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_fm_seek_start(struct si476x_core *core,
				  bool seekup, bool wrap)
{
	u8       resp[CMD_FM_SEEK_START_NRESP];
	const u8 args[CMD_FM_SEEK_START_NARGS] = {
		seekup << 3 | wrap << 2,
	};

	return si476x_cmd_tune_seek_freq(core, CMD_FM_SEEK_START,
					 args, sizeof(args),
					 resp, sizeof(resp));
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_seek_start);

/**
 * si476x_cmd_fm_rds_status - send 'FM_RDS_STATUS' command to the
 * device
 * @core: - device to send the command to
 * @status_only: - if set the data is not removed from RDSFIFO,
 *                RDSFIFOUSED is not decremented and data in all the
 *                rest RDS data contains the last valid info received
 * @mtfifo: if set the command clears RDS receive FIFO
 * @intack: if set the command clards the RDSINT bit.
 * @report: - all signal quality information retured by the command
 *           (if NULL then the output of the command is ignored)
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_fm_rds_status(struct si476x_core *core,
				  bool status_only,
				  bool mtfifo,
				  bool intack,
				  struct si476x_rds_status_report *report)
{
	int err;
	u8       resp[CMD_FM_RDS_STATUS_NRESP];
	const u8 args[CMD_FM_RDS_STATUS_NARGS] = {
		status_only << 2 | mtfifo << 1 | intack,
	};

	err = si476x_core_send_command(core, CMD_FM_RDS_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	/*
	 * Besides getting RDS status information this command can be
	 * used to just acknowledge different interrupt flags in those
	 * cases it is useless to copy and parse received data so user
	 * can pass NULL, and thus avoid unnecessary copying.
	 */
	if (err < 0 || report == NULL)
		return err;

	report->rdstpptyint	= 0x10 & resp[1];
	report->rdspiint	= 0x08 & resp[1];
	report->rdssyncint	= 0x02 & resp[1];
	report->rdsfifoint	= 0x01 & resp[1];

	report->tpptyvalid	= 0x10 & resp[2];
	report->pivalid		= 0x08 & resp[2];
	report->rdssync		= 0x02 & resp[2];
	report->rdsfifolost	= 0x01 & resp[2];

	report->tp		= 0x20 & resp[3];
	report->pty		= 0x1f & resp[3];

	report->pi		= get_unaligned_be16(resp + 4);
	report->rdsfifoused	= resp[6];

	report->ble[V4L2_RDS_BLOCK_A]	= 0xc0 & resp[7];
	report->ble[V4L2_RDS_BLOCK_B]	= 0x30 & resp[7];
	report->ble[V4L2_RDS_BLOCK_C]	= 0x0c & resp[7];
	report->ble[V4L2_RDS_BLOCK_D]	= 0x03 & resp[7];

	report->rds[V4L2_RDS_BLOCK_A].block = V4L2_RDS_BLOCK_A;
	report->rds[V4L2_RDS_BLOCK_A].msb = resp[8];
	report->rds[V4L2_RDS_BLOCK_A].lsb = resp[9];

	report->rds[V4L2_RDS_BLOCK_B].block = V4L2_RDS_BLOCK_B;
	report->rds[V4L2_RDS_BLOCK_B].msb = resp[10];
	report->rds[V4L2_RDS_BLOCK_B].lsb = resp[11];

	report->rds[V4L2_RDS_BLOCK_C].block = V4L2_RDS_BLOCK_C;
	report->rds[V4L2_RDS_BLOCK_C].msb = resp[12];
	report->rds[V4L2_RDS_BLOCK_C].lsb = resp[13];

	report->rds[V4L2_RDS_BLOCK_D].block = V4L2_RDS_BLOCK_D;
	report->rds[V4L2_RDS_BLOCK_D].msb = resp[14];
	report->rds[V4L2_RDS_BLOCK_D].lsb = resp[15];

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_rds_status);

int si476x_core_cmd_fm_rds_blockcount(struct si476x_core *core,
				bool clear,
				struct si476x_rds_blockcount_report *report)
{
	int err;
	u8       resp[CMD_FM_RDS_BLOCKCOUNT_NRESP];
	const u8 args[CMD_FM_RDS_BLOCKCOUNT_NARGS] = {
		clear,
	};

	if (!report)
		return -EINVAL;

	err = si476x_core_send_command(core, CMD_FM_RDS_BLOCKCOUNT,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);

	if (!err) {
		report->expected	= get_unaligned_be16(resp + 2);
		report->received	= get_unaligned_be16(resp + 4);
		report->uncorrectable	= get_unaligned_be16(resp + 6);
	}

	return err;
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_rds_blockcount);

int si476x_core_cmd_fm_phase_diversity(struct si476x_core *core,
				       enum si476x_phase_diversity_mode mode)
{
	u8       resp[CMD_FM_PHASE_DIVERSITY_NRESP];
	const u8 args[CMD_FM_PHASE_DIVERSITY_NARGS] = {
		mode & 0x07,
	};

	return si476x_core_send_command(core, CMD_FM_PHASE_DIVERSITY,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_phase_diversity);
/**
 * si476x_core_cmd_fm_phase_div_status() - get the phase diversity
 * status
 *
 * @core: si476x device
 *
 * NOTE caller must hold core lock
 *
 * Function returns the value of the status bit in case of success and
 * negative error code in case of failre.
 */
int si476x_core_cmd_fm_phase_div_status(struct si476x_core *core)
{
	int err;
	u8 resp[CMD_FM_PHASE_DIV_STATUS_NRESP];

	err = si476x_core_send_command(core, CMD_FM_PHASE_DIV_STATUS,
				       NULL, 0,
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);

	return (err < 0) ? err : resp[1];
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_phase_div_status);


/**
 * si476x_cmd_am_seek_start - send 'FM_SEEK_START' command to the
 * device
 * @core:  - device to send the command to
 * @seekup: - if set the direction of the search is 'up'
 * @wrap:   - if set seek wraps when hitting band limit
 *
 * This function begins search for a valid station. The station is
 * considered valid when 'FM_VALID_SNR_THRESHOLD' and
 * 'FM_VALID_RSSI_THRESHOLD' and 'FM_VALID_MAX_TUNE_ERROR' criteria
 * are met.
 *
 * Function returns 0 on success and negative error code on failure
 */
int si476x_core_cmd_am_seek_start(struct si476x_core *core,
				  bool seekup, bool wrap)
{
	u8       resp[CMD_AM_SEEK_START_NRESP];
	const u8 args[CMD_AM_SEEK_START_NARGS] = {
		seekup << 3 | wrap << 2,
	};

	return si476x_cmd_tune_seek_freq(core,  CMD_AM_SEEK_START,
					 args, sizeof(args),
					 resp, sizeof(resp));
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_am_seek_start);



static int si476x_core_cmd_power_up_a10(struct si476x_core *core,
					struct si476x_power_up_args *puargs)
{
	u8       resp[CMD_POWER_UP_A10_NRESP];
	const bool intsel = (core->pinmux.a1 == SI476X_A1_IRQ);
	const bool ctsen  = (core->client->irq != 0);
	const u8 args[CMD_POWER_UP_A10_NARGS] = {
		0xF7,		/* Reserved, always 0xF7 */
		0x3F & puargs->xcload,	/* First two bits are reserved to be
				 * zeros */
		ctsen << 7 | intsel << 6 | 0x07, /* Last five bits
						   * are reserved to
						   * be written as 0x7 */
		puargs->func << 4 | puargs->freq,
		0x11,		/* Reserved, always 0x11 */
	};

	return si476x_core_send_command(core, CMD_POWER_UP,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_TIMEOUT_POWER_UP);
}

static int si476x_core_cmd_power_up_a20(struct si476x_core *core,
				 struct si476x_power_up_args *puargs)
{
	u8       resp[CMD_POWER_UP_A20_NRESP];
	const bool intsel = (core->pinmux.a1 == SI476X_A1_IRQ);
	const bool ctsen  = (core->client->irq != 0);
	const u8 args[CMD_POWER_UP_A20_NARGS] = {
		puargs->ibias6x << 7 | puargs->xstart,
		0x3F & puargs->xcload,	/* First two bits are reserved to be
					 * zeros */
		ctsen << 7 | intsel << 6 | puargs->fastboot << 5 |
		puargs->xbiashc << 3 | puargs->xbias,
		puargs->func << 4 | puargs->freq,
		0x10 | puargs->xmode,
	};

	return si476x_core_send_command(core, CMD_POWER_UP,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_TIMEOUT_POWER_UP);
}

static int si476x_core_cmd_power_down_a10(struct si476x_core *core,
					  struct si476x_power_down_args *pdargs)
{
	u8 resp[CMD_POWER_DOWN_A10_NRESP];

	return si476x_core_send_command(core, CMD_POWER_DOWN,
					NULL, 0,
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}

static int si476x_core_cmd_power_down_a20(struct si476x_core *core,
					  struct si476x_power_down_args *pdargs)
{
	u8 resp[CMD_POWER_DOWN_A20_NRESP];
	const u8 args[CMD_POWER_DOWN_A20_NARGS] = {
		pdargs->xosc,
	};
	return si476x_core_send_command(core, CMD_POWER_DOWN,
					args, ARRAY_SIZE(args),
					resp, ARRAY_SIZE(resp),
					SI476X_DEFAULT_TIMEOUT);
}

static int si476x_core_cmd_am_tune_freq_a10(struct si476x_core *core,
					struct si476x_tune_freq_args *tuneargs)
{

	const int am_freq = tuneargs->freq;
	u8       resp[CMD_AM_TUNE_FREQ_NRESP];
	const u8 args[CMD_AM_TUNE_FREQ_NARGS] = {
		(tuneargs->hd << 6),
		msb(am_freq),
		lsb(am_freq),
	};

	return si476x_cmd_tune_seek_freq(core, CMD_AM_TUNE_FREQ, args,
					 sizeof(args),
					 resp, sizeof(resp));
}

static int si476x_core_cmd_am_tune_freq_a20(struct si476x_core *core,
					struct si476x_tune_freq_args *tuneargs)
{
	const int am_freq = tuneargs->freq;
	u8       resp[CMD_AM_TUNE_FREQ_NRESP];
	const u8 args[CMD_AM_TUNE_FREQ_NARGS] = {
		(tuneargs->zifsr << 6) | (tuneargs->injside & 0x03),
		msb(am_freq),
		lsb(am_freq),
	};

	return si476x_cmd_tune_seek_freq(core, CMD_AM_TUNE_FREQ,
					 args, sizeof(args),
					 resp, sizeof(resp));
}

static int si476x_core_cmd_fm_rsq_status_a10(struct si476x_core *core,
					struct si476x_rsq_status_args *rsqargs,
					struct si476x_rsq_status_report *report)
{
	int err;
	u8       resp[CMD_FM_RSQ_STATUS_A10_NRESP];
	const u8 args[CMD_FM_RSQ_STATUS_A10_NARGS] = {
		rsqargs->rsqack << 3 | rsqargs->attune << 2 |
		rsqargs->cancel << 1 | rsqargs->stcack,
	};

	err = si476x_core_send_command(core, CMD_FM_RSQ_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	/*
	 * Besides getting received signal quality information this
	 * command can be used to just acknowledge different interrupt
	 * flags in those cases it is useless to copy and parse
	 * received data so user can pass NULL, and thus avoid
	 * unnecessary copying.
	 */
	if (err < 0 || report == NULL)
		return err;

	report->multhint	= 0x80 & resp[1];
	report->multlint	= 0x40 & resp[1];
	report->snrhint		= 0x08 & resp[1];
	report->snrlint		= 0x04 & resp[1];
	report->rssihint	= 0x02 & resp[1];
	report->rssilint	= 0x01 & resp[1];

	report->bltf		= 0x80 & resp[2];
	report->snr_ready	= 0x20 & resp[2];
	report->rssiready	= 0x08 & resp[2];
	report->afcrl		= 0x02 & resp[2];
	report->valid		= 0x01 & resp[2];

	report->readfreq	= get_unaligned_be16(resp + 3);
	report->freqoff		= resp[5];
	report->rssi		= resp[6];
	report->snr		= resp[7];
	report->lassi		= resp[9];
	report->hassi		= resp[10];
	report->mult		= resp[11];
	report->dev		= resp[12];
	report->readantcap	= get_unaligned_be16(resp + 13);
	report->assi		= resp[15];
	report->usn		= resp[16];

	return err;
}

static int si476x_core_cmd_fm_rsq_status_a20(struct si476x_core *core,
				     struct si476x_rsq_status_args *rsqargs,
				     struct si476x_rsq_status_report *report)
{
	int err;
	u8       resp[CMD_FM_RSQ_STATUS_A10_NRESP];
	const u8 args[CMD_FM_RSQ_STATUS_A30_NARGS] = {
		rsqargs->primary << 4 | rsqargs->rsqack << 3 |
		rsqargs->attune  << 2 | rsqargs->cancel << 1 |
		rsqargs->stcack,
	};

	err = si476x_core_send_command(core, CMD_FM_RSQ_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	/*
	 * Besides getting received signal quality information this
	 * command can be used to just acknowledge different interrupt
	 * flags in those cases it is useless to copy and parse
	 * received data so user can pass NULL, and thus avoid
	 * unnecessary copying.
	 */
	if (err < 0 || report == NULL)
		return err;

	report->multhint	= 0x80 & resp[1];
	report->multlint	= 0x40 & resp[1];
	report->snrhint		= 0x08 & resp[1];
	report->snrlint		= 0x04 & resp[1];
	report->rssihint	= 0x02 & resp[1];
	report->rssilint	= 0x01 & resp[1];

	report->bltf		= 0x80 & resp[2];
	report->snr_ready	= 0x20 & resp[2];
	report->rssiready	= 0x08 & resp[2];
	report->afcrl		= 0x02 & resp[2];
	report->valid		= 0x01 & resp[2];

	report->readfreq	= get_unaligned_be16(resp + 3);
	report->freqoff		= resp[5];
	report->rssi		= resp[6];
	report->snr		= resp[7];
	report->lassi		= resp[9];
	report->hassi		= resp[10];
	report->mult		= resp[11];
	report->dev		= resp[12];
	report->readantcap	= get_unaligned_be16(resp + 13);
	report->assi		= resp[15];
	report->usn		= resp[16];

	return err;
}


static int si476x_core_cmd_fm_rsq_status_a30(struct si476x_core *core,
					struct si476x_rsq_status_args *rsqargs,
					struct si476x_rsq_status_report *report)
{
	int err;
	u8       resp[CMD_FM_RSQ_STATUS_A30_NRESP];
	const u8 args[CMD_FM_RSQ_STATUS_A30_NARGS] = {
		rsqargs->primary << 4 | rsqargs->rsqack << 3 |
		rsqargs->attune << 2 | rsqargs->cancel << 1 |
		rsqargs->stcack,
	};

	err = si476x_core_send_command(core, CMD_FM_RSQ_STATUS,
				       args, ARRAY_SIZE(args),
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	/*
	 * Besides getting received signal quality information this
	 * command can be used to just acknowledge different interrupt
	 * flags in those cases it is useless to copy and parse
	 * received data so user can pass NULL, and thus avoid
	 * unnecessary copying.
	 */
	if (err < 0 || report == NULL)
		return err;

	report->multhint	= 0x80 & resp[1];
	report->multlint	= 0x40 & resp[1];
	report->snrhint		= 0x08 & resp[1];
	report->snrlint		= 0x04 & resp[1];
	report->rssihint	= 0x02 & resp[1];
	report->rssilint	= 0x01 & resp[1];

	report->bltf		= 0x80 & resp[2];
	report->snr_ready	= 0x20 & resp[2];
	report->rssiready	= 0x08 & resp[2];
	report->injside         = 0x04 & resp[2];
	report->afcrl		= 0x02 & resp[2];
	report->valid		= 0x01 & resp[2];

	report->readfreq	= get_unaligned_be16(resp + 3);
	report->freqoff		= resp[5];
	report->rssi		= resp[6];
	report->snr		= resp[7];
	report->issi		= resp[8];
	report->lassi		= resp[9];
	report->hassi		= resp[10];
	report->mult		= resp[11];
	report->dev		= resp[12];
	report->readantcap	= get_unaligned_be16(resp + 13);
	report->assi		= resp[15];
	report->usn		= resp[16];

	report->pilotdev	= resp[17];
	report->rdsdev		= resp[18];
	report->assidev		= resp[19];
	report->strongdev	= resp[20];
	report->rdspi		= get_unaligned_be16(resp + 21);

	return err;
}

static int si476x_core_cmd_fm_tune_freq_a10(struct si476x_core *core,
					struct si476x_tune_freq_args *tuneargs)
{
	u8       resp[CMD_FM_TUNE_FREQ_NRESP];
	const u8 args[CMD_FM_TUNE_FREQ_A10_NARGS] = {
		(tuneargs->hd << 6) | (tuneargs->tunemode << 4)
		| (tuneargs->smoothmetrics << 2),
		msb(tuneargs->freq),
		lsb(tuneargs->freq),
		msb(tuneargs->antcap),
		lsb(tuneargs->antcap)
	};

	return si476x_cmd_tune_seek_freq(core, CMD_FM_TUNE_FREQ,
					 args, sizeof(args),
					 resp, sizeof(resp));
}

static int si476x_core_cmd_fm_tune_freq_a20(struct si476x_core *core,
					struct si476x_tune_freq_args *tuneargs)
{
	u8       resp[CMD_FM_TUNE_FREQ_NRESP];
	const u8 args[CMD_FM_TUNE_FREQ_A20_NARGS] = {
		(tuneargs->hd << 6) | (tuneargs->tunemode << 4)
		|  (tuneargs->smoothmetrics << 2) | (tuneargs->injside),
		msb(tuneargs->freq),
		lsb(tuneargs->freq),
	};

	return si476x_cmd_tune_seek_freq(core, CMD_FM_TUNE_FREQ,
					 args, sizeof(args),
					 resp, sizeof(resp));
}

static int si476x_core_cmd_agc_status_a20(struct si476x_core *core,
					struct si476x_agc_status_report *report)
{
	int err;
	u8 resp[CMD_AGC_STATUS_NRESP_A20];

	if (!report)
		return -EINVAL;

	err = si476x_core_send_command(core, CMD_AGC_STATUS,
				       NULL, 0,
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	if (err < 0)
		return err;

	report->mxhi		= resp[1] & SI476X_AGC_MXHI;
	report->mxlo		= resp[1] & SI476X_AGC_MXLO;
	report->lnahi		= resp[1] & SI476X_AGC_LNAHI;
	report->lnalo		= resp[1] & SI476X_AGC_LNALO;
	report->fmagc1		= resp[2];
	report->fmagc2		= resp[3];
	report->pgagain		= resp[4];
	report->fmwblang	= resp[5];

	return err;
}

static int si476x_core_cmd_agc_status_a10(struct si476x_core *core,
					struct si476x_agc_status_report *report)
{
	int err;
	u8 resp[CMD_AGC_STATUS_NRESP_A10];

	if (!report)
		return -EINVAL;

	err = si476x_core_send_command(core, CMD_AGC_STATUS,
				       NULL, 0,
				       resp, ARRAY_SIZE(resp),
				       SI476X_DEFAULT_TIMEOUT);
	if (err < 0)
		return err;

	report->mxhi	= resp[1] & SI476X_AGC_MXHI;
	report->mxlo	= resp[1] & SI476X_AGC_MXLO;
	report->lnahi	= resp[1] & SI476X_AGC_LNAHI;
	report->lnalo	= resp[1] & SI476X_AGC_LNALO;

	return err;
}

typedef int (*tune_freq_func_t) (struct si476x_core *core,
				 struct si476x_tune_freq_args *tuneargs);

static struct {
	int (*power_up)(struct si476x_core *,
			struct si476x_power_up_args *);
	int (*power_down)(struct si476x_core *,
			  struct si476x_power_down_args *);

	tune_freq_func_t fm_tune_freq;
	tune_freq_func_t am_tune_freq;

	int (*fm_rsq_status)(struct si476x_core *,
			     struct si476x_rsq_status_args *,
			     struct si476x_rsq_status_report *);

	int (*agc_status)(struct si476x_core *,
			  struct si476x_agc_status_report *);
	int (*intb_pin_cfg)(struct si476x_core *core,
			    enum si476x_intb_config intb,
			    enum si476x_a1_config a1);
} si476x_cmds_vtable[] = {
	[SI476X_REVISION_A10] = {
		.power_up	= si476x_core_cmd_power_up_a10,
		.power_down	= si476x_core_cmd_power_down_a10,
		.fm_tune_freq	= si476x_core_cmd_fm_tune_freq_a10,
		.am_tune_freq	= si476x_core_cmd_am_tune_freq_a10,
		.fm_rsq_status	= si476x_core_cmd_fm_rsq_status_a10,
		.agc_status	= si476x_core_cmd_agc_status_a10,
		.intb_pin_cfg   = si476x_core_cmd_intb_pin_cfg_a10,
	},
	[SI476X_REVISION_A20] = {
		.power_up	= si476x_core_cmd_power_up_a20,
		.power_down	= si476x_core_cmd_power_down_a20,
		.fm_tune_freq	= si476x_core_cmd_fm_tune_freq_a20,
		.am_tune_freq	= si476x_core_cmd_am_tune_freq_a20,
		.fm_rsq_status	= si476x_core_cmd_fm_rsq_status_a20,
		.agc_status	= si476x_core_cmd_agc_status_a20,
		.intb_pin_cfg   = si476x_core_cmd_intb_pin_cfg_a20,
	},
	[SI476X_REVISION_A30] = {
		.power_up	= si476x_core_cmd_power_up_a20,
		.power_down	= si476x_core_cmd_power_down_a20,
		.fm_tune_freq	= si476x_core_cmd_fm_tune_freq_a20,
		.am_tune_freq	= si476x_core_cmd_am_tune_freq_a20,
		.fm_rsq_status	= si476x_core_cmd_fm_rsq_status_a30,
		.agc_status	= si476x_core_cmd_agc_status_a20,
		.intb_pin_cfg   = si476x_core_cmd_intb_pin_cfg_a20,
	},
};

int si476x_core_cmd_power_up(struct si476x_core *core,
			     struct si476x_power_up_args *args)
{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].power_up(core, args);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_power_up);

int si476x_core_cmd_power_down(struct si476x_core *core,
			       struct si476x_power_down_args *args)
{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].power_down(core, args);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_power_down);

int si476x_core_cmd_fm_tune_freq(struct si476x_core *core,
				 struct si476x_tune_freq_args *args)
{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].fm_tune_freq(core, args);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_tune_freq);

int si476x_core_cmd_am_tune_freq(struct si476x_core *core,
				 struct si476x_tune_freq_args *args)
{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].am_tune_freq(core, args);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_am_tune_freq);

int si476x_core_cmd_fm_rsq_status(struct si476x_core *core,
				  struct si476x_rsq_status_args *args,
				  struct si476x_rsq_status_report *report)

{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].fm_rsq_status(core, args,
								report);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_fm_rsq_status);

int si476x_core_cmd_agc_status(struct si476x_core *core,
				  struct si476x_agc_status_report *report)

{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);
	return si476x_cmds_vtable[core->revision].agc_status(core, report);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_agc_status);

int si476x_core_cmd_intb_pin_cfg(struct si476x_core *core,
			    enum si476x_intb_config intb,
			    enum si476x_a1_config a1)
{
	BUG_ON(core->revision > SI476X_REVISION_A30 ||
	       core->revision == -1);

	return si476x_cmds_vtable[core->revision].intb_pin_cfg(core, intb, a1);
}
EXPORT_SYMBOL_GPL(si476x_core_cmd_intb_pin_cfg);

MODULE_LICENSE("GPL");
MODULE_AUTHOR("Andrey Smirnov <andrew.smirnov@gmail.com>");
MODULE_DESCRIPTION("API for command exchange for si476x");
