blob: 97ac97b1a5db4d4608810f07022df9130c3bf1d6 [file] [log] [blame]
Tom Rini10e47792018-05-06 17:58:06 -04001// SPDX-License-Identifier: GPL-2.0+
Sekhar Nori4708b172010-01-27 11:10:40 -05002/*
3 * Copyright (C) 2009 Texas Instruments Incorporated - http://www.ti.com/
4 *
5 * Driver for SPI controller on DaVinci. Based on atmel_spi.c
6 * by Atmel Corporation
7 *
8 * Copyright (C) 2007 Atmel Corporation
Sekhar Nori4708b172010-01-27 11:10:40 -05009 */
Jagan Tekiccaa8fc2015-06-27 00:51:29 +053010
Sekhar Nori4708b172010-01-27 11:10:40 -050011#include <common.h>
Simon Glass0f2af882020-05-10 11:40:05 -060012#include <log.h>
Sekhar Nori4708b172010-01-27 11:10:40 -050013#include <spi.h>
14#include <malloc.h>
15#include <asm/io.h>
16#include <asm/arch/hardware.h>
Vignesh Rc1091e12016-07-06 09:58:56 +053017#include <dm.h>
Jagan Tekia147f662018-09-03 23:00:23 +053018#include <dm/platform_data/spi_davinci.h>
Simon Glass4dcacfc2020-05-10 11:40:13 -060019#include <linux/bitops.h>
Simon Glassdbd79542020-05-10 11:40:11 -060020#include <linux/delay.h>
Jagan Teki742d53d2015-06-27 00:51:28 +053021
Jagan Teki742d53d2015-06-27 00:51:28 +053022/* SPIGCR0 */
23#define SPIGCR0_SPIENA_MASK 0x1
24#define SPIGCR0_SPIRST_MASK 0x0
25
26/* SPIGCR0 */
27#define SPIGCR1_CLKMOD_MASK BIT(1)
28#define SPIGCR1_MASTER_MASK BIT(0)
29#define SPIGCR1_SPIENA_MASK BIT(24)
30
31/* SPIPC0 */
32#define SPIPC0_DIFUN_MASK BIT(11) /* SIMO */
33#define SPIPC0_DOFUN_MASK BIT(10) /* SOMI */
34#define SPIPC0_CLKFUN_MASK BIT(9) /* CLK */
35#define SPIPC0_EN0FUN_MASK BIT(0)
36
37/* SPIFMT0 */
38#define SPIFMT_SHIFTDIR_SHIFT 20
39#define SPIFMT_POLARITY_SHIFT 17
40#define SPIFMT_PHASE_SHIFT 16
41#define SPIFMT_PRESCALE_SHIFT 8
42
43/* SPIDAT1 */
44#define SPIDAT1_CSHOLD_SHIFT 28
45#define SPIDAT1_CSNR_SHIFT 16
46
47/* SPIDELAY */
48#define SPI_C2TDELAY_SHIFT 24
49#define SPI_T2CDELAY_SHIFT 16
50
51/* SPIBUF */
52#define SPIBUF_RXEMPTY_MASK BIT(31)
53#define SPIBUF_TXFULL_MASK BIT(29)
54
55/* SPIDEF */
56#define SPIDEF_CSDEF0_MASK BIT(0)
57
Vignesh Rc1091e12016-07-06 09:58:56 +053058#ifndef CONFIG_DM_SPI
Jagan Teki742d53d2015-06-27 00:51:28 +053059#define SPI0_BUS 0
60#define SPI0_BASE CONFIG_SYS_SPI_BASE
61/*
62 * Define default SPI0_NUM_CS as 1 for existing platforms that uses this
63 * driver. Platform can configure number of CS using CONFIG_SYS_SPI0_NUM_CS
64 * if more than one CS is supported and by defining CONFIG_SYS_SPI0.
65 */
66#ifndef CONFIG_SYS_SPI0
67#define SPI0_NUM_CS 1
68#else
69#define SPI0_NUM_CS CONFIG_SYS_SPI0_NUM_CS
70#endif
71
72/*
73 * define CONFIG_SYS_SPI1 when platform has spi-1 device (bus #1) and
74 * CONFIG_SYS_SPI1_NUM_CS defines number of CS on this bus
75 */
76#ifdef CONFIG_SYS_SPI1
77#define SPI1_BUS 1
78#define SPI1_NUM_CS CONFIG_SYS_SPI1_NUM_CS
79#define SPI1_BASE CONFIG_SYS_SPI1_BASE
80#endif
81
82/*
83 * define CONFIG_SYS_SPI2 when platform has spi-2 device (bus #2) and
84 * CONFIG_SYS_SPI2_NUM_CS defines number of CS on this bus
85 */
86#ifdef CONFIG_SYS_SPI2
87#define SPI2_BUS 2
88#define SPI2_NUM_CS CONFIG_SYS_SPI2_NUM_CS
89#define SPI2_BASE CONFIG_SYS_SPI2_BASE
90#endif
Vignesh Rc1091e12016-07-06 09:58:56 +053091#endif
92
93DECLARE_GLOBAL_DATA_PTR;
Jagan Teki742d53d2015-06-27 00:51:28 +053094
Jagan Tekiccaa8fc2015-06-27 00:51:29 +053095/* davinci spi register set */
96struct davinci_spi_regs {
97 dv_reg gcr0; /* 0x00 */
98 dv_reg gcr1; /* 0x04 */
99 dv_reg int0; /* 0x08 */
100 dv_reg lvl; /* 0x0c */
101 dv_reg flg; /* 0x10 */
102 dv_reg pc0; /* 0x14 */
103 dv_reg pc1; /* 0x18 */
104 dv_reg pc2; /* 0x1c */
105 dv_reg pc3; /* 0x20 */
106 dv_reg pc4; /* 0x24 */
107 dv_reg pc5; /* 0x28 */
108 dv_reg rsvd[3];
109 dv_reg dat0; /* 0x38 */
110 dv_reg dat1; /* 0x3c */
111 dv_reg buf; /* 0x40 */
112 dv_reg emu; /* 0x44 */
113 dv_reg delay; /* 0x48 */
114 dv_reg def; /* 0x4c */
115 dv_reg fmt0; /* 0x50 */
116 dv_reg fmt1; /* 0x54 */
117 dv_reg fmt2; /* 0x58 */
118 dv_reg fmt3; /* 0x5c */
119 dv_reg intvec0; /* 0x60 */
120 dv_reg intvec1; /* 0x64 */
121};
122
123/* davinci spi slave */
Jagan Teki742d53d2015-06-27 00:51:28 +0530124struct davinci_spi_slave {
Vignesh Rc1091e12016-07-06 09:58:56 +0530125#ifndef CONFIG_DM_SPI
Jagan Teki742d53d2015-06-27 00:51:28 +0530126 struct spi_slave slave;
Vignesh Rc1091e12016-07-06 09:58:56 +0530127#endif
Jagan Teki742d53d2015-06-27 00:51:28 +0530128 struct davinci_spi_regs *regs;
Vignesh Rc1091e12016-07-06 09:58:56 +0530129 unsigned int freq; /* current SPI bus frequency */
130 unsigned int mode; /* current SPI mode used */
131 u8 num_cs; /* total no. of CS available */
132 u8 cur_cs; /* CS of current slave */
133 bool half_duplex; /* true, if master is half-duplex only */
Jagan Teki742d53d2015-06-27 00:51:28 +0530134};
135
Nick Thompson213e4762010-06-22 11:06:01 -0400136/*
137 * This functions needs to act like a macro to avoid pipeline reloads in the
138 * loops below. Use always_inline. This gains us about 160KiB/s and the bloat
139 * appears to be zero bytes (da830).
140 */
141__attribute__((always_inline))
142static inline u32 davinci_spi_xfer_data(struct davinci_spi_slave *ds, u32 data)
143{
144 u32 buf_reg_val;
145
146 /* send out data */
147 writel(data, &ds->regs->dat1);
148
149 /* wait for the data to clock in/out */
150 while ((buf_reg_val = readl(&ds->regs->buf)) & SPIBUF_RXEMPTY_MASK)
151 ;
152
153 return buf_reg_val;
154}
155
Vignesh Rc1091e12016-07-06 09:58:56 +0530156static int davinci_spi_read(struct davinci_spi_slave *ds, unsigned int len,
Nick Thompson213e4762010-06-22 11:06:01 -0400157 u8 *rxp, unsigned long flags)
158{
Nick Thompson213e4762010-06-22 11:06:01 -0400159 unsigned int data1_reg_val;
160
161 /* enable CS hold, CS[n] and clear the data bits */
162 data1_reg_val = ((1 << SPIDAT1_CSHOLD_SHIFT) |
Vignesh Rc1091e12016-07-06 09:58:56 +0530163 (ds->cur_cs << SPIDAT1_CSNR_SHIFT));
Nick Thompson213e4762010-06-22 11:06:01 -0400164
165 /* wait till TXFULL is deasserted */
166 while (readl(&ds->regs->buf) & SPIBUF_TXFULL_MASK)
167 ;
168
169 /* preload the TX buffer to avoid clock starvation */
170 writel(data1_reg_val, &ds->regs->dat1);
171
172 /* keep reading 1 byte until only 1 byte left */
173 while ((len--) > 1)
174 *rxp++ = davinci_spi_xfer_data(ds, data1_reg_val);
175
176 /* clear CS hold when we reach the end */
177 if (flags & SPI_XFER_END)
178 data1_reg_val &= ~(1 << SPIDAT1_CSHOLD_SHIFT);
179
180 /* read the last byte */
181 *rxp = davinci_spi_xfer_data(ds, data1_reg_val);
182
183 return 0;
184}
185
Vignesh Rc1091e12016-07-06 09:58:56 +0530186static int davinci_spi_write(struct davinci_spi_slave *ds, unsigned int len,
Nick Thompson4bbd91f2010-07-05 20:00:40 -0400187 const u8 *txp, unsigned long flags)
Nick Thompson213e4762010-06-22 11:06:01 -0400188{
Nick Thompson213e4762010-06-22 11:06:01 -0400189 unsigned int data1_reg_val;
190
191 /* enable CS hold and clear the data bits */
192 data1_reg_val = ((1 << SPIDAT1_CSHOLD_SHIFT) |
Vignesh Rc1091e12016-07-06 09:58:56 +0530193 (ds->cur_cs << SPIDAT1_CSNR_SHIFT));
Nick Thompson213e4762010-06-22 11:06:01 -0400194
195 /* wait till TXFULL is deasserted */
196 while (readl(&ds->regs->buf) & SPIBUF_TXFULL_MASK)
197 ;
198
199 /* preload the TX buffer to avoid clock starvation */
200 if (len > 2) {
201 writel(data1_reg_val | *txp++, &ds->regs->dat1);
202 len--;
203 }
204
205 /* keep writing 1 byte until only 1 byte left */
206 while ((len--) > 1)
207 davinci_spi_xfer_data(ds, data1_reg_val | *txp++);
208
209 /* clear CS hold when we reach the end */
210 if (flags & SPI_XFER_END)
211 data1_reg_val &= ~(1 << SPIDAT1_CSHOLD_SHIFT);
212
213 /* write the last byte */
214 davinci_spi_xfer_data(ds, data1_reg_val | *txp);
215
216 return 0;
217}
218
Vignesh Rc1091e12016-07-06 09:58:56 +0530219static int davinci_spi_read_write(struct davinci_spi_slave *ds, unsigned
220 int len, u8 *rxp, const u8 *txp,
221 unsigned long flags)
Nick Thompson213e4762010-06-22 11:06:01 -0400222{
Nick Thompson213e4762010-06-22 11:06:01 -0400223 unsigned int data1_reg_val;
224
225 /* enable CS hold and clear the data bits */
226 data1_reg_val = ((1 << SPIDAT1_CSHOLD_SHIFT) |
Vignesh Rc1091e12016-07-06 09:58:56 +0530227 (ds->cur_cs << SPIDAT1_CSNR_SHIFT));
Nick Thompson213e4762010-06-22 11:06:01 -0400228
229 /* wait till TXFULL is deasserted */
230 while (readl(&ds->regs->buf) & SPIBUF_TXFULL_MASK)
231 ;
232
233 /* keep reading and writing 1 byte until only 1 byte left */
234 while ((len--) > 1)
235 *rxp++ = davinci_spi_xfer_data(ds, data1_reg_val | *txp++);
236
237 /* clear CS hold when we reach the end */
238 if (flags & SPI_XFER_END)
239 data1_reg_val &= ~(1 << SPIDAT1_CSHOLD_SHIFT);
240
241 /* read and write the last byte */
242 *rxp = davinci_spi_xfer_data(ds, data1_reg_val | *txp);
243
244 return 0;
245}
Vignesh Rc1091e12016-07-06 09:58:56 +0530246
247
248static int __davinci_spi_claim_bus(struct davinci_spi_slave *ds, int cs)
249{
250 unsigned int mode = 0, scalar;
251
252 /* Enable the SPI hardware */
253 writel(SPIGCR0_SPIRST_MASK, &ds->regs->gcr0);
254 udelay(1000);
255 writel(SPIGCR0_SPIENA_MASK, &ds->regs->gcr0);
256
257 /* Set master mode, powered up and not activated */
258 writel(SPIGCR1_MASTER_MASK | SPIGCR1_CLKMOD_MASK, &ds->regs->gcr1);
259
260 /* CS, CLK, SIMO and SOMI are functional pins */
261 writel(((1 << cs) | SPIPC0_CLKFUN_MASK |
262 SPIPC0_DOFUN_MASK | SPIPC0_DIFUN_MASK), &ds->regs->pc0);
263
264 /* setup format */
265 scalar = ((CONFIG_SYS_SPI_CLK / ds->freq) - 1) & 0xFF;
266
267 /*
268 * Use following format:
269 * character length = 8,
270 * MSB shifted out first
271 */
272 if (ds->mode & SPI_CPOL)
273 mode |= SPI_CPOL;
274 if (!(ds->mode & SPI_CPHA))
275 mode |= SPI_CPHA;
276 writel(8 | (scalar << SPIFMT_PRESCALE_SHIFT) |
277 (mode << SPIFMT_PHASE_SHIFT), &ds->regs->fmt0);
278
279 /*
280 * Including a minor delay. No science here. Should be good even with
281 * no delay
282 */
283 writel((50 << SPI_C2TDELAY_SHIFT) |
284 (50 << SPI_T2CDELAY_SHIFT), &ds->regs->delay);
285
286 /* default chip select register */
287 writel(SPIDEF_CSDEF0_MASK, &ds->regs->def);
288
289 /* no interrupts */
290 writel(0, &ds->regs->int0);
291 writel(0, &ds->regs->lvl);
292
293 /* enable SPI */
294 writel((readl(&ds->regs->gcr1) | SPIGCR1_SPIENA_MASK), &ds->regs->gcr1);
295
296 return 0;
297}
298
299static int __davinci_spi_release_bus(struct davinci_spi_slave *ds)
300{
301 /* Disable the SPI hardware */
302 writel(SPIGCR0_SPIRST_MASK, &ds->regs->gcr0);
303
304 return 0;
305}
306
307static int __davinci_spi_xfer(struct davinci_spi_slave *ds,
308 unsigned int bitlen, const void *dout, void *din,
309 unsigned long flags)
310{
311 unsigned int len;
312
313 if (bitlen == 0)
314 /* Finish any previously submitted transfers */
315 goto out;
316
317 /*
318 * It's not clear how non-8-bit-aligned transfers are supposed to be
319 * represented as a stream of bytes...this is a limitation of
320 * the current SPI interface - here we terminate on receiving such a
321 * transfer request.
322 */
323 if (bitlen % 8) {
324 /* Errors always terminate an ongoing transfer */
325 flags |= SPI_XFER_END;
326 goto out;
327 }
328
329 len = bitlen / 8;
330
331 if (!dout)
332 return davinci_spi_read(ds, len, din, flags);
333 if (!din)
334 return davinci_spi_write(ds, len, dout, flags);
335 if (!ds->half_duplex)
336 return davinci_spi_read_write(ds, len, din, dout, flags);
337
338 printf("SPI full duplex not supported\n");
339 flags |= SPI_XFER_END;
340
341out:
342 if (flags & SPI_XFER_END) {
343 u8 dummy = 0;
344 davinci_spi_write(ds, 1, &dummy, flags);
345 }
346 return 0;
347}
348
349#ifndef CONFIG_DM_SPI
350
351static inline struct davinci_spi_slave *to_davinci_spi(struct spi_slave *slave)
352{
353 return container_of(slave, struct davinci_spi_slave, slave);
354}
Nick Thompson213e4762010-06-22 11:06:01 -0400355
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530356int spi_cs_is_valid(unsigned int bus, unsigned int cs)
357{
358 int ret = 0;
359
360 switch (bus) {
361 case SPI0_BUS:
362 if (cs < SPI0_NUM_CS)
363 ret = 1;
364 break;
365#ifdef CONFIG_SYS_SPI1
366 case SPI1_BUS:
367 if (cs < SPI1_NUM_CS)
368 ret = 1;
369 break;
370#endif
371#ifdef CONFIG_SYS_SPI2
372 case SPI2_BUS:
373 if (cs < SPI2_NUM_CS)
374 ret = 1;
375 break;
376#endif
377 default:
378 /* Invalid bus number. Do nothing */
379 break;
380 }
381 return ret;
382}
383
384void spi_cs_activate(struct spi_slave *slave)
385{
386 /* do nothing */
387}
388
389void spi_cs_deactivate(struct spi_slave *slave)
390{
391 /* do nothing */
392}
393
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530394struct spi_slave *spi_setup_slave(unsigned int bus, unsigned int cs,
395 unsigned int max_hz, unsigned int mode)
396{
397 struct davinci_spi_slave *ds;
398
399 if (!spi_cs_is_valid(bus, cs))
400 return NULL;
401
402 ds = spi_alloc_slave(struct davinci_spi_slave, bus, cs);
403 if (!ds)
404 return NULL;
405
406 switch (bus) {
407 case SPI0_BUS:
408 ds->regs = (struct davinci_spi_regs *)SPI0_BASE;
409 break;
410#ifdef CONFIG_SYS_SPI1
411 case SPI1_BUS:
412 ds->regs = (struct davinci_spi_regs *)SPI1_BASE;
413 break;
414#endif
415#ifdef CONFIG_SYS_SPI2
416 case SPI2_BUS:
417 ds->regs = (struct davinci_spi_regs *)SPI2_BASE;
418 break;
419#endif
420 default: /* Invalid bus number */
421 return NULL;
422 }
423
424 ds->freq = max_hz;
Vignesh Rc1091e12016-07-06 09:58:56 +0530425 ds->mode = mode;
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530426
427 return &ds->slave;
428}
429
430void spi_free_slave(struct spi_slave *slave)
431{
432 struct davinci_spi_slave *ds = to_davinci_spi(slave);
433
434 free(ds);
435}
436
Vignesh Rc1091e12016-07-06 09:58:56 +0530437int spi_xfer(struct spi_slave *slave, unsigned int bitlen,
438 const void *dout, void *din, unsigned long flags)
439{
440 struct davinci_spi_slave *ds = to_davinci_spi(slave);
441
442 ds->cur_cs = slave->cs;
443
444 return __davinci_spi_xfer(ds, bitlen, dout, din, flags);
445}
446
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530447int spi_claim_bus(struct spi_slave *slave)
448{
449 struct davinci_spi_slave *ds = to_davinci_spi(slave);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530450
Vignesh Rc1091e12016-07-06 09:58:56 +0530451#ifdef CONFIG_SPI_HALF_DUPLEX
452 ds->half_duplex = true;
453#else
454 ds->half_duplex = false;
455#endif
456 return __davinci_spi_claim_bus(ds, ds->slave.cs);
457}
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530458
Vignesh Rc1091e12016-07-06 09:58:56 +0530459void spi_release_bus(struct spi_slave *slave)
460{
461 struct davinci_spi_slave *ds = to_davinci_spi(slave);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530462
Vignesh Rc1091e12016-07-06 09:58:56 +0530463 __davinci_spi_release_bus(ds);
464}
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530465
Vignesh Rc1091e12016-07-06 09:58:56 +0530466#else
467static int davinci_spi_set_speed(struct udevice *bus, uint max_hz)
468{
469 struct davinci_spi_slave *ds = dev_get_priv(bus);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530470
Vignesh Rc1091e12016-07-06 09:58:56 +0530471 debug("%s speed %u\n", __func__, max_hz);
472 if (max_hz > CONFIG_SYS_SPI_CLK / 2)
473 return -EINVAL;
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530474
Vignesh Rc1091e12016-07-06 09:58:56 +0530475 ds->freq = max_hz;
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530476
Vignesh Rc1091e12016-07-06 09:58:56 +0530477 return 0;
478}
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530479
Vignesh Rc1091e12016-07-06 09:58:56 +0530480static int davinci_spi_set_mode(struct udevice *bus, uint mode)
481{
482 struct davinci_spi_slave *ds = dev_get_priv(bus);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530483
Vignesh Rc1091e12016-07-06 09:58:56 +0530484 debug("%s mode %u\n", __func__, mode);
485 ds->mode = mode;
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530486
487 return 0;
488}
489
Vignesh Rc1091e12016-07-06 09:58:56 +0530490static int davinci_spi_claim_bus(struct udevice *dev)
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530491{
Vignesh Rc1091e12016-07-06 09:58:56 +0530492 struct dm_spi_slave_platdata *slave_plat =
493 dev_get_parent_platdata(dev);
494 struct udevice *bus = dev->parent;
495 struct davinci_spi_slave *ds = dev_get_priv(bus);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530496
Vignesh Rc1091e12016-07-06 09:58:56 +0530497 if (slave_plat->cs >= ds->num_cs) {
498 printf("Invalid SPI chipselect\n");
499 return -EINVAL;
500 }
501 ds->half_duplex = slave_plat->mode & SPI_PREAMBLE;
502
503 return __davinci_spi_claim_bus(ds, slave_plat->cs);
Jagan Tekiccaa8fc2015-06-27 00:51:29 +0530504}
505
Vignesh Rc1091e12016-07-06 09:58:56 +0530506static int davinci_spi_release_bus(struct udevice *dev)
Sekhar Nori4708b172010-01-27 11:10:40 -0500507{
Vignesh Rc1091e12016-07-06 09:58:56 +0530508 struct davinci_spi_slave *ds = dev_get_priv(dev->parent);
Sekhar Nori4708b172010-01-27 11:10:40 -0500509
Vignesh Rc1091e12016-07-06 09:58:56 +0530510 return __davinci_spi_release_bus(ds);
511}
Sekhar Nori4708b172010-01-27 11:10:40 -0500512
Vignesh Rc1091e12016-07-06 09:58:56 +0530513static int davinci_spi_xfer(struct udevice *dev, unsigned int bitlen,
514 const void *dout, void *din,
515 unsigned long flags)
516{
517 struct dm_spi_slave_platdata *slave =
518 dev_get_parent_platdata(dev);
519 struct udevice *bus = dev->parent;
520 struct davinci_spi_slave *ds = dev_get_priv(bus);
521
522 if (slave->cs >= ds->num_cs) {
523 printf("Invalid SPI chipselect\n");
524 return -EINVAL;
Sekhar Nori4708b172010-01-27 11:10:40 -0500525 }
Vignesh Rc1091e12016-07-06 09:58:56 +0530526 ds->cur_cs = slave->cs;
Sekhar Nori4708b172010-01-27 11:10:40 -0500527
Vignesh Rc1091e12016-07-06 09:58:56 +0530528 return __davinci_spi_xfer(ds, bitlen, dout, din, flags);
529}
Sekhar Nori4708b172010-01-27 11:10:40 -0500530
Jagan Tekia147f662018-09-03 23:00:23 +0530531static const struct dm_spi_ops davinci_spi_ops = {
532 .claim_bus = davinci_spi_claim_bus,
533 .release_bus = davinci_spi_release_bus,
534 .xfer = davinci_spi_xfer,
535 .set_speed = davinci_spi_set_speed,
536 .set_mode = davinci_spi_set_mode,
537};
538
Vignesh Rc1091e12016-07-06 09:58:56 +0530539static int davinci_spi_probe(struct udevice *bus)
540{
Jagan Tekia147f662018-09-03 23:00:23 +0530541 struct davinci_spi_slave *ds = dev_get_priv(bus);
542 struct davinci_spi_platdata *plat = bus->platdata;
543 ds->regs = plat->regs;
544 ds->num_cs = plat->num_cs;
545
Vignesh Rc1091e12016-07-06 09:58:56 +0530546 return 0;
547}
Sekhar Nori4708b172010-01-27 11:10:40 -0500548
Jagan Tekia147f662018-09-03 23:00:23 +0530549#if CONFIG_IS_ENABLED(OF_CONTROL) && !CONFIG_IS_ENABLED(OF_PLATDATA)
Vignesh Rc1091e12016-07-06 09:58:56 +0530550static int davinci_ofdata_to_platadata(struct udevice *bus)
551{
Jagan Tekia147f662018-09-03 23:00:23 +0530552 struct davinci_spi_platdata *plat = bus->platdata;
553 fdt_addr_t addr;
Vignesh Rc1091e12016-07-06 09:58:56 +0530554
Jagan Tekia147f662018-09-03 23:00:23 +0530555 addr = devfdt_get_addr(bus);
556 if (addr == FDT_ADDR_T_NONE)
Vignesh Rc1091e12016-07-06 09:58:56 +0530557 return -EINVAL;
Jagan Tekia147f662018-09-03 23:00:23 +0530558
559 plat->regs = (struct davinci_spi_regs *)addr;
560 plat->num_cs = fdtdec_get_int(gd->fdt_blob, dev_of_offset(bus), "num-cs", 4);
Vignesh Rc1091e12016-07-06 09:58:56 +0530561
Sekhar Nori4708b172010-01-27 11:10:40 -0500562 return 0;
563}
Vignesh Rc1091e12016-07-06 09:58:56 +0530564
Vignesh Rc1091e12016-07-06 09:58:56 +0530565static const struct udevice_id davinci_spi_ids[] = {
566 { .compatible = "ti,keystone-spi" },
567 { .compatible = "ti,dm6441-spi" },
Adam Forda2d2f562017-09-17 20:43:45 -0500568 { .compatible = "ti,da830-spi" },
Vignesh Rc1091e12016-07-06 09:58:56 +0530569 { }
570};
Jagan Tekia147f662018-09-03 23:00:23 +0530571#endif
Vignesh Rc1091e12016-07-06 09:58:56 +0530572
573U_BOOT_DRIVER(davinci_spi) = {
574 .name = "davinci_spi",
575 .id = UCLASS_SPI,
Jagan Tekia147f662018-09-03 23:00:23 +0530576#if CONFIG_IS_ENABLED(OF_CONTROL) && !CONFIG_IS_ENABLED(OF_PLATDATA)
Vignesh Rc1091e12016-07-06 09:58:56 +0530577 .of_match = davinci_spi_ids,
Vignesh Rc1091e12016-07-06 09:58:56 +0530578 .ofdata_to_platdata = davinci_ofdata_to_platadata,
Jagan Tekia147f662018-09-03 23:00:23 +0530579 .platdata_auto_alloc_size = sizeof(struct davinci_spi_platdata),
580#endif
Vignesh Rc1091e12016-07-06 09:58:56 +0530581 .probe = davinci_spi_probe,
Jagan Tekia147f662018-09-03 23:00:23 +0530582 .ops = &davinci_spi_ops,
583 .priv_auto_alloc_size = sizeof(struct davinci_spi_slave),
Vignesh Rc1091e12016-07-06 09:58:56 +0530584};
585#endif