atmel_spi.c 4.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211
  1. /*
  2. * Copyright (C) 2007 Atmel Corporation
  3. *
  4. * SPDX-License-Identifier: GPL-2.0+
  5. */
  6. #include <common.h>
  7. #include <spi.h>
  8. #include <malloc.h>
  9. #include <asm/io.h>
  10. #include <asm/arch/clk.h>
  11. #include <asm/arch/hardware.h>
  12. #include "atmel_spi.h"
  13. static int spi_has_wdrbt(struct atmel_spi_slave *slave)
  14. {
  15. unsigned int ver;
  16. ver = spi_readl(slave, VERSION);
  17. return (ATMEL_SPI_VERSION_REV(ver) >= 0x210);
  18. }
  19. void spi_init()
  20. {
  21. }
  22. struct spi_slave *spi_setup_slave(unsigned int bus, unsigned int cs,
  23. unsigned int max_hz, unsigned int mode)
  24. {
  25. struct atmel_spi_slave *as;
  26. unsigned int scbr;
  27. u32 csrx;
  28. void *regs;
  29. if (!spi_cs_is_valid(bus, cs))
  30. return NULL;
  31. switch (bus) {
  32. case 0:
  33. regs = (void *)ATMEL_BASE_SPI0;
  34. break;
  35. #ifdef ATMEL_BASE_SPI1
  36. case 1:
  37. regs = (void *)ATMEL_BASE_SPI1;
  38. break;
  39. #endif
  40. #ifdef ATMEL_BASE_SPI2
  41. case 2:
  42. regs = (void *)ATMEL_BASE_SPI2;
  43. break;
  44. #endif
  45. #ifdef ATMEL_BASE_SPI3
  46. case 3:
  47. regs = (void *)ATMEL_BASE_SPI3;
  48. break;
  49. #endif
  50. default:
  51. return NULL;
  52. }
  53. scbr = (get_spi_clk_rate(bus) + max_hz - 1) / max_hz;
  54. if (scbr > ATMEL_SPI_CSRx_SCBR_MAX)
  55. /* Too low max SCK rate */
  56. return NULL;
  57. if (scbr < 1)
  58. scbr = 1;
  59. csrx = ATMEL_SPI_CSRx_SCBR(scbr);
  60. csrx |= ATMEL_SPI_CSRx_BITS(ATMEL_SPI_BITS_8);
  61. if (!(mode & SPI_CPHA))
  62. csrx |= ATMEL_SPI_CSRx_NCPHA;
  63. if (mode & SPI_CPOL)
  64. csrx |= ATMEL_SPI_CSRx_CPOL;
  65. as = spi_alloc_slave(struct atmel_spi_slave, bus, cs);
  66. if (!as)
  67. return NULL;
  68. as->regs = regs;
  69. as->mr = ATMEL_SPI_MR_MSTR | ATMEL_SPI_MR_MODFDIS
  70. | ATMEL_SPI_MR_PCS(~(1 << cs) & 0xf);
  71. if (spi_has_wdrbt(as))
  72. as->mr |= ATMEL_SPI_MR_WDRBT;
  73. spi_writel(as, CSR(cs), csrx);
  74. return &as->slave;
  75. }
  76. void spi_free_slave(struct spi_slave *slave)
  77. {
  78. struct atmel_spi_slave *as = to_atmel_spi(slave);
  79. free(as);
  80. }
  81. int spi_claim_bus(struct spi_slave *slave)
  82. {
  83. struct atmel_spi_slave *as = to_atmel_spi(slave);
  84. /* Enable the SPI hardware */
  85. spi_writel(as, CR, ATMEL_SPI_CR_SPIEN);
  86. /*
  87. * Select the slave. This should set SCK to the correct
  88. * initial state, etc.
  89. */
  90. spi_writel(as, MR, as->mr);
  91. return 0;
  92. }
  93. void spi_release_bus(struct spi_slave *slave)
  94. {
  95. struct atmel_spi_slave *as = to_atmel_spi(slave);
  96. /* Disable the SPI hardware */
  97. spi_writel(as, CR, ATMEL_SPI_CR_SPIDIS);
  98. }
  99. int spi_xfer(struct spi_slave *slave, unsigned int bitlen,
  100. const void *dout, void *din, unsigned long flags)
  101. {
  102. struct atmel_spi_slave *as = to_atmel_spi(slave);
  103. unsigned int len_tx;
  104. unsigned int len_rx;
  105. unsigned int len;
  106. u32 status;
  107. const u8 *txp = dout;
  108. u8 *rxp = din;
  109. u8 value;
  110. if (bitlen == 0)
  111. /* Finish any previously submitted transfers */
  112. goto out;
  113. /*
  114. * TODO: The controller can do non-multiple-of-8 bit
  115. * transfers, but this driver currently doesn't support it.
  116. *
  117. * It's also not clear how such transfers are supposed to be
  118. * represented as a stream of bytes...this is a limitation of
  119. * the current SPI interface.
  120. */
  121. if (bitlen % 8) {
  122. /* Errors always terminate an ongoing transfer */
  123. flags |= SPI_XFER_END;
  124. goto out;
  125. }
  126. len = bitlen / 8;
  127. /*
  128. * The controller can do automatic CS control, but it is
  129. * somewhat quirky, and it doesn't really buy us much anyway
  130. * in the context of U-Boot.
  131. */
  132. if (flags & SPI_XFER_BEGIN) {
  133. spi_cs_activate(slave);
  134. /*
  135. * sometimes the RDR is not empty when we get here,
  136. * in theory that should not happen, but it DOES happen.
  137. * Read it here to be on the safe side.
  138. * That also clears the OVRES flag. Required if the
  139. * following loop exits due to OVRES!
  140. */
  141. spi_readl(as, RDR);
  142. }
  143. for (len_tx = 0, len_rx = 0; len_rx < len; ) {
  144. status = spi_readl(as, SR);
  145. if (status & ATMEL_SPI_SR_OVRES)
  146. return -1;
  147. if (len_tx < len && (status & ATMEL_SPI_SR_TDRE)) {
  148. if (txp)
  149. value = *txp++;
  150. else
  151. value = 0;
  152. spi_writel(as, TDR, value);
  153. len_tx++;
  154. }
  155. if (status & ATMEL_SPI_SR_RDRF) {
  156. value = spi_readl(as, RDR);
  157. if (rxp)
  158. *rxp++ = value;
  159. len_rx++;
  160. }
  161. }
  162. out:
  163. if (flags & SPI_XFER_END) {
  164. /*
  165. * Wait until the transfer is completely done before
  166. * we deactivate CS.
  167. */
  168. do {
  169. status = spi_readl(as, SR);
  170. } while (!(status & ATMEL_SPI_SR_TXEMPTY));
  171. spi_cs_deactivate(slave);
  172. }
  173. return 0;
  174. }