// SPDX-License-Identifier: BSD-3-Clause-Clear
/* Copyright (C) 2022 MediaTek Inc. */
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/platform_device.h>
#include <linux/pinctrl/consumer.h>
#include <linux/of.h>
#include <linux/of_reserved_mem.h>
#include <linux/iopoll.h>
#include <linux/reset.h>
#include <linux/of_net.h>
#include <linux/clk.h>
#include "mt7915.h"
#define MT7981_CON_INFRA_VERSION 0x02090000
#define MT7986_CON_INFRA_VERSION 0x02070000
/* INFRACFG */
#define MT_INFRACFG_CONN2AP_SLPPROT 0x0d0
#define MT_INFRACFG_AP2CONN_SLPPROT 0x0d4
#define MT_INFRACFG_RX_EN_MASK BIT(16)
#define MT_INFRACFG_TX_RDY_MASK BIT(4)
#define MT_INFRACFG_TX_EN_MASK BIT(0)
/* TOP POS */
#define MT_TOP_POS_FAST_CTRL 0x114
#define MT_TOP_POS_FAST_EN_MASK BIT(3)
#define MT_TOP_POS_SKU 0x21c
#define MT_TOP_POS_SKU_MASK GENMASK(31, 28)
#define MT_TOP_POS_SKU_ADIE_DBDC_MASK BIT(2)
enum {
ADIE_SB,
ADIE_DBDC
};
static int
mt76_wmac_spi_read(struct mt7915_dev *dev, u8 adie, u32 addr, u32 *val)
{
int ret;
u32 cur;
ret = read_poll_timeout(mt76_rr, cur, !(cur & MT_TOP_SPI_POLLING_BIT),
USEC_PER_MSEC, 50 * USEC_PER_MSEC, false,
dev, MT_TOP_SPI_BUSY_CR(adie));
if (ret)
return ret;
mt76_wr(dev, MT_TOP_SPI_ADDR_CR(adie),
MT_TOP_SPI_READ_ADDR_FORMAT | addr);
mt76_wr(dev, MT_TOP_SPI_WRITE_DATA_CR(adie), 0);
ret = read_poll_timeout(mt76_rr, cur, !(cur & MT_TOP_SPI_POLLING_BIT),
USEC_PER_MSEC, 50 * USEC_PER_MSEC, false,
dev, MT_TOP_SPI_BUSY_CR(adie));
if (ret)
return ret;
*val = mt76_rr(dev, MT_TOP_SPI_READ_DATA_CR(adie));
return 0;
}
static int
mt76_wmac_spi_write(struct mt7915_dev *dev, u8 adie, u32 addr, u32 val)
{
int ret;
u32 cur;
ret = read_poll_timeout(mt76_rr, cur, !(cur & MT_TOP_SPI_POLLING_BIT),
USEC_PER_MSEC, 50 * USEC_PER_MSEC, false,
dev, MT_TOP_SPI_BUSY_CR(adie));
if (ret)
return ret;
mt76_wr(dev, MT_TOP_SPI_ADDR_CR(adie),
MT_TOP_SPI_WRITE_ADDR_FORMAT | addr);
mt76_wr(