// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (c) 2010 ASIX Electronics Corporation
 * Copyright (c) 2020 Samsung Electronics Co., Ltd.
 *
 * ASIX AX88796C SPI Fast Ethernet Linux driver
 */

#define pr_fmt(fmt)	"ax88796c: " fmt

#include <linux/string.h>
#include <linux/spi/spi.h>

#include "ax88796c_spi.h"

const u8 ax88796c_rx_cmd_buf[5] = {AX_SPICMD_READ_RXQ, 0xFF, 0xFF, 0xFF, 0xFF};
const u8 ax88796c_tx_cmd_buf[4] = {AX_SPICMD_WRITE_TXQ, 0xFF, 0xFF, 0xFF};

/* driver bus management functions */
int axspi_wakeup(struct axspi_data *ax_spi)
{
	int ret;

	ax_spi->cmd_buf[0] = AX_SPICMD_EXIT_PWD;	/* OP */
	ret = spi_write(ax_spi->spi, ax_spi->cmd_buf, 1);
	if (ret)
		dev_err(&ax_spi->spi->dev, "%s() failed: ret = %d\n", __func__, ret);
	return ret;
}

int axspi_read_status(struct axspi_data *ax_spi, struct spi_status *status)
{
	int ret;

	/* OP */
	ax_spi->cmd_buf[0] = AX_SPICMD_READ_STATUS;
	ret = spi_write_then_read(ax_spi->spi, ax_spi->cmd_buf, 1, (u8 *)&status, 3);
	if (ret)
		dev_err(&ax_spi->spi->dev, "%s() failed: ret = %d\n", __func__, ret);
	else
		le16_to_cpus(&status->isr);

	return ret;
}

int axspi_read_rxq(struct axspi_data *ax_spi, void *data, int len)
{
	struct spi_transfer *xfer = ax_spi->spi_rx_xfer;
	int ret;

	memcpy(ax_spi->cmd_buf, ax88796c_rx_cmd_buf, 5);

	xfer->tx_buf = ax_spi->cmd_buf;
	xfer->rx_buf = NULL;
	xfer->len = ax_spi->comp ? 2 : 5;
	xfer->bits_per_word = 8;
	spi_message_add_tail(xfer, &ax_spi->rx_msg);

	xfer++;
	xfer->rx_buf = data;
	xfer->tx_buf = NULL;
	xfer->len = len;
	xfer->bits_per_word = 8;
	spi_message_add_tail(xfer, &ax_spi->rx_msg);
	ret = spi_sync(ax_spi->spi, &ax_spi->rx_msg);
	if (ret)
		dev_err(&ax_spi->spi->dev, "%s() failed: ret = %d\n", __func__, ret);

	return ret;
}

int axspi_write_txq(const struct axspi_data *ax_spi, void *data, int len)
{
	return spi_write(ax_spi->spi, data, len);
}

u16 axspi_read_reg(struct axspi_data *ax_spi, u8 reg)
{
	int ret;
	int len = ax_spi->comp ? 3 : 4;

	ax_spi->cmd_buf[0] = 0x03;	/* OP code read register */
	ax_spi->cmd_buf[1] = reg;	/* register address */
	ax_spi->cmd_buf[2] = 0xFF;	/* dumy cycle */
	ax_spi->cmd_buf[3] = 0xFF;	/* dumy cycle */
	ret = spi_write_then_read(ax_spi->spi,
				  ax_spi->cmd_buf, len,
				  ax_spi->rx_buf, 2);
	if (ret) {
		dev_err(&ax_spi->spi->dev,
			"%s() failed: ret = %d\n", __func__, ret);
		return 0xFFFF;
	}

	le16_to_cpus((u16 *)ax_spi->rx_buf);

	return *(u16 *)ax_spi->rx_buf;
}

int axspi_write_reg(struct axspi_data *ax_spi, u8 reg, u16 value)
{
	int ret;

	memset(ax_spi->cmd_buf, 0, sizeof(ax_spi->cmd_buf));
	ax_spi->cmd_buf[0] = AX_SPICMD_WRITE_REG;	/* OP code read register */
	ax_spi->cmd_buf[1] = reg;			/* register address */
	ax_spi->cmd_buf[2] = value;
	ax_spi->cmd_buf[3] = value >> 8;

	ret = spi_write(ax_spi->spi, ax_spi->cmd_buf, 4);
	if (ret)
		dev_err(&ax_spi->spi->dev, "%s() failed: ret = %d\n", __func__, ret);
	return ret;
}

