0167-bcm2835-sdhost-Only-claim-one-DMA-channel.patch 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160
  1. From f76d188586952fcd3b55916f30c484c62c8fabab Mon Sep 17 00:00:00 2001
  2. From: Phil Elwell <phil@raspberrypi.org>
  3. Date: Mon, 7 Mar 2016 16:46:39 +0000
  4. Subject: [PATCH 167/381] bcm2835-sdhost: Only claim one DMA channel
  5. With both MMC controllers enabled there are few DMA channels left. The
  6. bcm2835-sdhost driver only uses DMA in one direction at a time, so it
  7. doesn't need to claim two channels.
  8. See: https://github.com/raspberrypi/linux/issues/1327
  9. Signed-off-by: Phil Elwell <phil@raspberrypi.org>
  10. ---
  11. arch/arm/boot/dts/bcm2708_common.dtsi | 5 +--
  12. drivers/mmc/host/bcm2835-sdhost.c | 70 ++++++++++++++++++++++++-----------
  13. 2 files changed, 50 insertions(+), 25 deletions(-)
  14. --- a/arch/arm/boot/dts/bcm2708_common.dtsi
  15. +++ b/arch/arm/boot/dts/bcm2708_common.dtsi
  16. @@ -136,9 +136,8 @@
  17. reg = <0x7e202000 0x100>;
  18. interrupts = <2 24>;
  19. clocks = <&clk_core>;
  20. - dmas = <&dma 13>,
  21. - <&dma 13>;
  22. - dma-names = "tx", "rx";
  23. + dmas = <&dma 13>;
  24. + dma-names = "rx-tx";
  25. brcm,overclock-50 = <0>;
  26. brcm,pio-limit = <1>;
  27. status = "disabled";
  28. --- a/drivers/mmc/host/bcm2835-sdhost.c
  29. +++ b/drivers/mmc/host/bcm2835-sdhost.c
  30. @@ -185,9 +185,10 @@ struct bcm2835_host {
  31. unsigned int debug:1; /* Enable debug output */
  32. /*DMA part*/
  33. - struct dma_chan *dma_chan_rx; /* DMA channel for reads */
  34. - struct dma_chan *dma_chan_tx; /* DMA channel for writes */
  35. - struct dma_chan *dma_chan; /* Channel in used */
  36. + struct dma_chan *dma_chan_rxtx; /* DMA channel for reads and writes */
  37. + struct dma_chan *dma_chan; /* Channel in use */
  38. + struct dma_slave_config dma_cfg_rx;
  39. + struct dma_slave_config dma_cfg_tx;
  40. struct dma_async_tx_descriptor *dma_desc;
  41. u32 dma_dir;
  42. u32 drain_words;
  43. @@ -771,12 +772,11 @@ static void bcm2835_sdhost_prepare_dma(s
  44. log_event("PRD<", (u32)data, 0);
  45. pr_debug("bcm2835_sdhost_prepare_dma()\n");
  46. + dma_chan = host->dma_chan_rxtx;
  47. if (data->flags & MMC_DATA_READ) {
  48. - dma_chan = host->dma_chan_rx;
  49. dir_data = DMA_FROM_DEVICE;
  50. dir_slave = DMA_DEV_TO_MEM;
  51. } else {
  52. - dma_chan = host->dma_chan_tx;
  53. dir_data = DMA_TO_DEVICE;
  54. dir_slave = DMA_MEM_TO_DEV;
  55. }
  56. @@ -813,6 +813,12 @@ static void bcm2835_sdhost_prepare_dma(s
  57. host->drain_words = len/4;
  58. }
  59. + /* The parameters have already been validated, so this will not fail */
  60. + (void)dmaengine_slave_config(dma_chan,
  61. + (dir_data == DMA_FROM_DEVICE) ?
  62. + &host->dma_cfg_rx :
  63. + &host->dma_cfg_tx);
  64. +
  65. len = dma_map_sg(dma_chan->device->dev, data->sg, data->sg_len,
  66. dir_data);
  67. @@ -1805,28 +1811,46 @@ int bcm2835_sdhost_add_host(struct bcm28
  68. spin_lock_init(&host->lock);
  69. if (host->allow_dma) {
  70. - if (IS_ERR_OR_NULL(host->dma_chan_tx) ||
  71. - IS_ERR_OR_NULL(host->dma_chan_rx)) {
  72. - pr_err("%s: unable to initialise DMA channels. "
  73. + if (IS_ERR_OR_NULL(host->dma_chan_rxtx)) {
  74. + pr_err("%s: unable to initialise DMA channel. "
  75. "Falling back to PIO\n",
  76. mmc_hostname(mmc));
  77. host->use_dma = false;
  78. } else {
  79. - host->use_dma = true;
  80. -
  81. cfg.src_addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
  82. cfg.dst_addr_width = DMA_SLAVE_BUSWIDTH_4_BYTES;
  83. cfg.slave_id = 13; /* DREQ channel */
  84. + /* Validate the slave configurations */
  85. +
  86. cfg.direction = DMA_MEM_TO_DEV;
  87. cfg.src_addr = 0;
  88. cfg.dst_addr = host->bus_addr + SDDATA;
  89. - ret = dmaengine_slave_config(host->dma_chan_tx, &cfg);
  90. - cfg.direction = DMA_DEV_TO_MEM;
  91. - cfg.src_addr = host->bus_addr + SDDATA;
  92. - cfg.dst_addr = 0;
  93. - ret = dmaengine_slave_config(host->dma_chan_rx, &cfg);
  94. + ret = dmaengine_slave_config(host->dma_chan_rxtx, &cfg);
  95. +
  96. + if (ret == 0) {
  97. + host->dma_cfg_tx = cfg;
  98. +
  99. + cfg.direction = DMA_DEV_TO_MEM;
  100. + cfg.src_addr = host->bus_addr + SDDATA;
  101. + cfg.dst_addr = 0;
  102. +
  103. + ret = dmaengine_slave_config(host->dma_chan_rxtx, &cfg);
  104. + }
  105. +
  106. + if (ret == 0) {
  107. + host->dma_cfg_rx = cfg;
  108. +
  109. + host->use_dma = true;
  110. + } else {
  111. + pr_err("%s: unable to configure DMA channel. "
  112. + "Falling back to PIO\n",
  113. + mmc_hostname(mmc));
  114. + dma_release_channel(host->dma_chan_rxtx);
  115. + host->dma_chan_rxtx = NULL;
  116. + host->use_dma = false;
  117. + }
  118. }
  119. } else {
  120. host->use_dma = false;
  121. @@ -1948,19 +1972,21 @@ static int bcm2835_sdhost_probe(struct p
  122. if (host->allow_dma) {
  123. if (node) {
  124. - host->dma_chan_tx =
  125. - dma_request_slave_channel(dev, "tx");
  126. - host->dma_chan_rx =
  127. - dma_request_slave_channel(dev, "rx");
  128. + host->dma_chan_rxtx =
  129. + dma_request_slave_channel(dev, "rx-tx");
  130. + if (!host->dma_chan_rxtx)
  131. + host->dma_chan_rxtx =
  132. + dma_request_slave_channel(dev, "tx");
  133. + if (!host->dma_chan_rxtx)
  134. + host->dma_chan_rxtx =
  135. + dma_request_slave_channel(dev, "rx");
  136. } else {
  137. dma_cap_mask_t mask;
  138. dma_cap_zero(mask);
  139. /* we don't care about the channel, any would work */
  140. dma_cap_set(DMA_SLAVE, mask);
  141. - host->dma_chan_tx =
  142. - dma_request_channel(mask, NULL, NULL);
  143. - host->dma_chan_rx =
  144. + host->dma_chan_rxtx =
  145. dma_request_channel(mask, NULL, NULL);
  146. }
  147. }