brintos

brintos / linux-shallow public Read only

0
0
Text · 9.0 KiB · 3770b8e Raw
389 lines · c
1// SPDX-License-Identifier: GPL-2.02//3// spi-mt7621.c -- MediaTek MT7621 SPI controller driver4//5// Copyright (C) 2011 Sergiy <piratfm@gmail.com>6// Copyright (C) 2011-2013 Gabor Juhos <juhosg@openwrt.org>7// Copyright (C) 2014-2015 Felix Fietkau <nbd@nbd.name>8//9// Some parts are based on spi-orion.c:10//   Author: Shadi Ammouri <shadi@marvell.com>11//   Copyright (C) 2007-2008 Marvell Ltd.12 13#include <linux/clk.h>14#include <linux/delay.h>15#include <linux/io.h>16#include <linux/module.h>17#include <linux/of.h>18#include <linux/of_device.h>19#include <linux/platform_device.h>20#include <linux/reset.h>21#include <linux/spi/spi.h>22 23#define DRIVER_NAME		"spi-mt7621"24 25/* in usec */26#define RALINK_SPI_WAIT_MAX_LOOP 200027 28/* SPISTAT register bit field */29#define SPISTAT_BUSY		BIT(0)30 31#define MT7621_SPI_TRANS	0x0032#define SPITRANS_BUSY		BIT(16)33 34#define MT7621_SPI_OPCODE	0x0435#define MT7621_SPI_DATA0	0x0836#define MT7621_SPI_DATA4	0x1837#define SPI_CTL_TX_RX_CNT_MASK	0xff38#define SPI_CTL_START		BIT(8)39 40#define MT7621_SPI_MASTER	0x2841#define MASTER_MORE_BUFMODE	BIT(2)42#define MASTER_FULL_DUPLEX	BIT(10)43#define MASTER_RS_CLK_SEL	GENMASK(27, 16)44#define MASTER_RS_CLK_SEL_SHIFT	1645#define MASTER_RS_SLAVE_SEL	GENMASK(31, 29)46 47#define MT7621_SPI_MOREBUF	0x2c48#define MT7621_SPI_POLAR	0x3849#define MT7621_SPI_SPACE	0x3c50 51#define MT7621_CPHA		BIT(5)52#define MT7621_CPOL		BIT(4)53#define MT7621_LSB_FIRST	BIT(3)54 55#define MT7621_NATIVE_CS_COUNT	256 57struct mt7621_spi {58	struct spi_controller	*host;59	void __iomem		*base;60	unsigned int		sys_freq;61	unsigned int		speed;62	int			pending_write;63};64 65static inline struct mt7621_spi *spidev_to_mt7621_spi(struct spi_device *spi)66{67	return spi_controller_get_devdata(spi->controller);68}69 70static inline u32 mt7621_spi_read(struct mt7621_spi *rs, u32 reg)71{72	return ioread32(rs->base + reg);73}74 75static inline void mt7621_spi_write(struct mt7621_spi *rs, u32 reg, u32 val)76{77	iowrite32(val, rs->base + reg);78}79 80static void mt7621_spi_set_native_cs(struct spi_device *spi, bool enable)81{82	struct mt7621_spi *rs = spidev_to_mt7621_spi(spi);83	int cs = spi_get_chipselect(spi, 0);84	bool active = spi->mode & SPI_CS_HIGH ? enable : !enable;85	u32 polar = 0;86	u32 host;87 88	/*89	 * Select SPI device 7, enable "more buffer mode" and disable90	 * full-duplex (only half-duplex really works on this chip91	 * reliably)92	 */93	host = mt7621_spi_read(rs, MT7621_SPI_MASTER);94	host |= MASTER_RS_SLAVE_SEL | MASTER_MORE_BUFMODE;95	host &= ~MASTER_FULL_DUPLEX;96	mt7621_spi_write(rs, MT7621_SPI_MASTER, host);97 98	rs->pending_write = 0;99 100	if (active)101		polar = BIT(cs);102	mt7621_spi_write(rs, MT7621_SPI_POLAR, polar);103}104 105static int mt7621_spi_prepare(struct spi_device *spi, unsigned int speed)106{107	struct mt7621_spi *rs = spidev_to_mt7621_spi(spi);108	u32 rate;109	u32 reg;110 111	dev_dbg(&spi->dev, "speed:%u\n", speed);112 113	rate = DIV_ROUND_UP(rs->sys_freq, speed);114	dev_dbg(&spi->dev, "rate-1:%u\n", rate);115 116	if (rate > 4097)117		return -EINVAL;118 119	if (rate < 2)120		rate = 2;121 122	reg = mt7621_spi_read(rs, MT7621_SPI_MASTER);123	reg &= ~MASTER_RS_CLK_SEL;124	reg |= (rate - 2) << MASTER_RS_CLK_SEL_SHIFT;125	rs->speed = speed;126 127	reg &= ~MT7621_LSB_FIRST;128	if (spi->mode & SPI_LSB_FIRST)129		reg |= MT7621_LSB_FIRST;130 131	/*132	 * This SPI controller seems to be tested on SPI flash only and some133	 * bits are swizzled under other SPI modes probably due to incorrect134	 * wiring inside the silicon. Only mode 0 works correctly.135	 */136	reg &= ~(MT7621_CPHA | MT7621_CPOL);137 138	mt7621_spi_write(rs, MT7621_SPI_MASTER, reg);139 140	return 0;141}142 143static inline int mt7621_spi_wait_till_ready(struct mt7621_spi *rs)144{145	int i;146 147	for (i = 0; i < RALINK_SPI_WAIT_MAX_LOOP; i++) {148		u32 status;149 150		status = mt7621_spi_read(rs, MT7621_SPI_TRANS);151		if ((status & SPITRANS_BUSY) == 0)152			return 0;153		cpu_relax();154		udelay(1);155	}156 157	return -ETIMEDOUT;158}159 160static int mt7621_spi_prepare_message(struct spi_controller *host,161				      struct spi_message *m)162{163	struct mt7621_spi *rs = spi_controller_get_devdata(host);164	struct spi_device *spi = m->spi;165	unsigned int speed = spi->max_speed_hz;166	struct spi_transfer *t = NULL;167 168	mt7621_spi_wait_till_ready(rs);169 170	list_for_each_entry(t, &m->transfers, transfer_list)171		if (t->speed_hz < speed)172			speed = t->speed_hz;173 174	return mt7621_spi_prepare(spi, speed);175}176 177static void mt7621_spi_read_half_duplex(struct mt7621_spi *rs,178					int rx_len, u8 *buf)179{180	int tx_len;181 182	/*183	 * Combine with any pending write, and perform one or more half-duplex184	 * transactions reading 'len' bytes. Data to be written is already in185	 * MT7621_SPI_DATA.186	 */187	tx_len = rs->pending_write;188	rs->pending_write = 0;189 190	while (rx_len || tx_len) {191		int i;192		u32 val = (min(tx_len, 4) * 8) << 24;193		int rx = min(rx_len, 32);194 195		if (tx_len > 4)196			val |= (tx_len - 4) * 8;197		val |= (rx * 8) << 12;198		mt7621_spi_write(rs, MT7621_SPI_MOREBUF, val);199 200		tx_len = 0;201 202		val = mt7621_spi_read(rs, MT7621_SPI_TRANS);203		val |= SPI_CTL_START;204		mt7621_spi_write(rs, MT7621_SPI_TRANS, val);205 206		mt7621_spi_wait_till_ready(rs);207 208		for (i = 0; i < rx; i++) {209			if ((i % 4) == 0)210				val = mt7621_spi_read(rs, MT7621_SPI_DATA0 + i);211			*buf++ = val & 0xff;212			val >>= 8;213		}214 215		rx_len -= i;216	}217}218 219static inline void mt7621_spi_flush(struct mt7621_spi *rs)220{221	mt7621_spi_read_half_duplex(rs, 0, NULL);222}223 224static void mt7621_spi_write_half_duplex(struct mt7621_spi *rs,225					 int tx_len, const u8 *buf)226{227	int len = rs->pending_write;228	int val = 0;229 230	if (len & 3) {231		val = mt7621_spi_read(rs, MT7621_SPI_OPCODE + (len & ~3));232		if (len < 4) {233			val <<= (4 - len) * 8;234			val = swab32(val);235		}236	}237 238	while (tx_len > 0) {239		if (len >= 36) {240			rs->pending_write = len;241			mt7621_spi_flush(rs);242			len = 0;243		}244 245		val |= *buf++ << (8 * (len & 3));246		len++;247		if ((len & 3) == 0) {248			if (len == 4)249				/* The byte-order of the opcode is weird! */250				val = swab32(val);251			mt7621_spi_write(rs, MT7621_SPI_OPCODE + len - 4, val);252			val = 0;253		}254		tx_len -= 1;255	}256 257	if (len & 3) {258		if (len < 4) {259			val = swab32(val);260			val >>= (4 - len) * 8;261		}262		mt7621_spi_write(rs, MT7621_SPI_OPCODE + (len & ~3), val);263	}264 265	rs->pending_write = len;266	mt7621_spi_flush(rs);267}268 269static int mt7621_spi_transfer_one(struct spi_controller *host,270				   struct spi_device *spi,271				   struct spi_transfer *t)272{273	struct mt7621_spi *rs = spi_controller_get_devdata(host);274 275	if ((t->rx_buf) && (t->tx_buf)) {276		/*277		 * This controller will shift some extra data out278		 * of spi_opcode if (mosi_bit_cnt > 0) &&279		 * (cmd_bit_cnt == 0). So the claimed full-duplex280		 * support is broken since we have no way to read281		 * the MISO value during that bit.282		 */283		return -EIO;284	} else if (t->rx_buf) {285		mt7621_spi_read_half_duplex(rs, t->len, t->rx_buf);286	} else if (t->tx_buf) {287		mt7621_spi_write_half_duplex(rs, t->len, t->tx_buf);288	}289 290	return 0;291}292 293static int mt7621_spi_setup(struct spi_device *spi)294{295	struct mt7621_spi *rs = spidev_to_mt7621_spi(spi);296 297	if ((spi->max_speed_hz == 0) ||298	    (spi->max_speed_hz > (rs->sys_freq / 2)))299		spi->max_speed_hz = rs->sys_freq / 2;300 301	if (spi->max_speed_hz < (rs->sys_freq / 4097)) {302		dev_err(&spi->dev, "setup: requested speed is too low %d Hz\n",303			spi->max_speed_hz);304		return -EINVAL;305	}306 307	return 0;308}309 310static const struct of_device_id mt7621_spi_match[] = {311	{ .compatible = "ralink,mt7621-spi" },312	{},313};314MODULE_DEVICE_TABLE(of, mt7621_spi_match);315 316static int mt7621_spi_probe(struct platform_device *pdev)317{318	const struct of_device_id *match;319	struct spi_controller *host;320	struct mt7621_spi *rs;321	void __iomem *base;322	struct clk *clk;323	int ret;324 325	match = of_match_device(mt7621_spi_match, &pdev->dev);326	if (!match)327		return -EINVAL;328 329	base = devm_platform_ioremap_resource(pdev, 0);330	if (IS_ERR(base))331		return PTR_ERR(base);332 333	clk = devm_clk_get_enabled(&pdev->dev, NULL);334	if (IS_ERR(clk))335		return dev_err_probe(&pdev->dev, PTR_ERR(clk),336				     "unable to get SYS clock\n");337 338	host = devm_spi_alloc_host(&pdev->dev, sizeof(*rs));339	if (!host) {340		dev_info(&pdev->dev, "host allocation failed\n");341		return -ENOMEM;342	}343 344	host->mode_bits = SPI_LSB_FIRST;345	host->flags = SPI_CONTROLLER_HALF_DUPLEX;346	host->setup = mt7621_spi_setup;347	host->prepare_message = mt7621_spi_prepare_message;348	host->set_cs = mt7621_spi_set_native_cs;349	host->transfer_one = mt7621_spi_transfer_one;350	host->bits_per_word_mask = SPI_BPW_MASK(8);351	host->dev.of_node = pdev->dev.of_node;352	host->max_native_cs = MT7621_NATIVE_CS_COUNT;353	host->num_chipselect = MT7621_NATIVE_CS_COUNT;354	host->use_gpio_descriptors = true;355 356	dev_set_drvdata(&pdev->dev, host);357 358	rs = spi_controller_get_devdata(host);359	rs->base = base;360	rs->host = host;361	rs->sys_freq = clk_get_rate(clk);362	rs->pending_write = 0;363	dev_info(&pdev->dev, "sys_freq: %u\n", rs->sys_freq);364 365	ret = device_reset(&pdev->dev);366	if (ret) {367		dev_err(&pdev->dev, "SPI reset failed!\n");368		return ret;369	}370 371	return devm_spi_register_controller(&pdev->dev, host);372}373 374MODULE_ALIAS("platform:" DRIVER_NAME);375 376static struct platform_driver mt7621_spi_driver = {377	.driver = {378		.name = DRIVER_NAME,379		.of_match_table = mt7621_spi_match,380	},381	.probe = mt7621_spi_probe,382};383 384module_platform_driver(mt7621_spi_driver);385 386MODULE_DESCRIPTION("MT7621 SPI driver");387MODULE_AUTHOR("Felix Fietkau <nbd@nbd.name>");388MODULE_LICENSE("GPL");389