diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2012-10-02 20:26:42 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2012-10-02 20:26:42 -0400 |
commit | 7fe0b14b725d6d09a1d9e1409bd465cb88b587f9 (patch) | |
tree | 89b5ffca03145618da92c75fb3cc1dda87dbb924 /drivers/mmc | |
parent | 7a9a2970b5c1c2ce73d4bb84edaa7ebf13e0c841 (diff) | |
parent | 536a53a300d0d40152796eefb0a9e6e36ca37f7d (diff) |
Merge tag 'spi-3.7' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/misc
Pull spi updates from Mark Brown:
"No framework work here, only a bunch of driver updates of varying
sizes:
- Factoring out of the core hardware support from the MXS MMC driver
by Marek Vasut to allow the hardware to also be used for SPI.
- Lots of error handling cleanups from Guenter Roeck
- Removal of the existing Tegra driver which is quite comprehensively
broken as detailed in the changelog for the removal.
- DT suppport for the PL022 and GPIO drivers.
- pinctrl support for OMAP and PL022."
Pulling from Mark Brown as Grant Likely is still busy moving.
* tag 'spi-3.7' of git://git.kernel.org/pub/scm/linux/kernel/git/broonie/misc: (53 commits)
spi: remove completely broken Tegra driver
spi/imx: set the inactive state of the clock according to the clock polarity
spi/pl022: get/put resources on suspend/resume
spi/pl022: use more managed resources
spi/pl022: Devicetree support w/o platform data
spi/s3c64xx: Don't free controller_data on non-dt platforms
spi: omap2-mcspi: add pinctrl support
spi/pl022: adopt pinctrl support
spi: omap2-mcspi: Cleanup the omap2_mcspi_txrx_dma function
spi/gpio: Fix stub for spi_gpio_probe_dt()
spi/mxs: Make the SPI block clock speed configurable via DT
spi: spi-sh-hspi: drop frees of devm_ alloc'd data
spi/pl022: Fix chipselects pointer computation
spi: spi-tle62x0: Use module_spi_driver macro
mxs/spi: Rework the mxs_ssp_timeout to be more readable
mxs/spi: Decrement the DMA/PIO border
mxs/spi: Increment the transfer length only if transfer succeeded
mxs/spi: Fix issues when doing long continuous transfer
spi: spi-gpio: Add DT bindings
spi: spi-gpio: store chipselect information in private structure
...
Diffstat (limited to 'drivers/mmc')
-rw-r--r-- | drivers/mmc/host/mxs-mmc.c | 323 |
1 files changed, 106 insertions, 217 deletions
diff --git a/drivers/mmc/host/mxs-mmc.c b/drivers/mmc/host/mxs-mmc.c index ad3fcea1269e..bb4c2bf04d09 100644 --- a/drivers/mmc/host/mxs-mmc.c +++ b/drivers/mmc/host/mxs-mmc.c | |||
@@ -41,91 +41,13 @@ | |||
41 | #include <linux/gpio.h> | 41 | #include <linux/gpio.h> |
42 | #include <linux/regulator/consumer.h> | 42 | #include <linux/regulator/consumer.h> |
43 | #include <linux/module.h> | 43 | #include <linux/module.h> |
44 | #include <linux/fsl/mxs-dma.h> | ||
45 | #include <linux/pinctrl/consumer.h> | 44 | #include <linux/pinctrl/consumer.h> |
46 | #include <linux/stmp_device.h> | 45 | #include <linux/stmp_device.h> |
47 | #include <linux/mmc/mxs-mmc.h> | 46 | #include <linux/mmc/mxs-mmc.h> |
47 | #include <linux/spi/mxs-spi.h> | ||
48 | 48 | ||
49 | #define DRIVER_NAME "mxs-mmc" | 49 | #define DRIVER_NAME "mxs-mmc" |
50 | 50 | ||
51 | /* card detect polling timeout */ | ||
52 | #define MXS_MMC_DETECT_TIMEOUT (HZ/2) | ||
53 | |||
54 | #define ssp_is_old(host) ((host)->devid == IMX23_MMC) | ||
55 | |||
56 | /* SSP registers */ | ||
57 | #define HW_SSP_CTRL0 0x000 | ||
58 | #define BM_SSP_CTRL0_RUN (1 << 29) | ||
59 | #define BM_SSP_CTRL0_SDIO_IRQ_CHECK (1 << 28) | ||
60 | #define BM_SSP_CTRL0_IGNORE_CRC (1 << 26) | ||
61 | #define BM_SSP_CTRL0_READ (1 << 25) | ||
62 | #define BM_SSP_CTRL0_DATA_XFER (1 << 24) | ||
63 | #define BP_SSP_CTRL0_BUS_WIDTH (22) | ||
64 | #define BM_SSP_CTRL0_BUS_WIDTH (0x3 << 22) | ||
65 | #define BM_SSP_CTRL0_WAIT_FOR_IRQ (1 << 21) | ||
66 | #define BM_SSP_CTRL0_LONG_RESP (1 << 19) | ||
67 | #define BM_SSP_CTRL0_GET_RESP (1 << 17) | ||
68 | #define BM_SSP_CTRL0_ENABLE (1 << 16) | ||
69 | #define BP_SSP_CTRL0_XFER_COUNT (0) | ||
70 | #define BM_SSP_CTRL0_XFER_COUNT (0xffff) | ||
71 | #define HW_SSP_CMD0 0x010 | ||
72 | #define BM_SSP_CMD0_DBL_DATA_RATE_EN (1 << 25) | ||
73 | #define BM_SSP_CMD0_SLOW_CLKING_EN (1 << 22) | ||
74 | #define BM_SSP_CMD0_CONT_CLKING_EN (1 << 21) | ||
75 | #define BM_SSP_CMD0_APPEND_8CYC (1 << 20) | ||
76 | #define BP_SSP_CMD0_BLOCK_SIZE (16) | ||
77 | #define BM_SSP_CMD0_BLOCK_SIZE (0xf << 16) | ||
78 | #define BP_SSP_CMD0_BLOCK_COUNT (8) | ||
79 | #define BM_SSP_CMD0_BLOCK_COUNT (0xff << 8) | ||
80 | #define BP_SSP_CMD0_CMD (0) | ||
81 | #define BM_SSP_CMD0_CMD (0xff) | ||
82 | #define HW_SSP_CMD1 0x020 | ||
83 | #define HW_SSP_XFER_SIZE 0x030 | ||
84 | #define HW_SSP_BLOCK_SIZE 0x040 | ||
85 | #define BP_SSP_BLOCK_SIZE_BLOCK_COUNT (4) | ||
86 | #define BM_SSP_BLOCK_SIZE_BLOCK_COUNT (0xffffff << 4) | ||
87 | #define BP_SSP_BLOCK_SIZE_BLOCK_SIZE (0) | ||
88 | #define BM_SSP_BLOCK_SIZE_BLOCK_SIZE (0xf) | ||
89 | #define HW_SSP_TIMING(h) (ssp_is_old(h) ? 0x050 : 0x070) | ||
90 | #define BP_SSP_TIMING_TIMEOUT (16) | ||
91 | #define BM_SSP_TIMING_TIMEOUT (0xffff << 16) | ||
92 | #define BP_SSP_TIMING_CLOCK_DIVIDE (8) | ||
93 | #define BM_SSP_TIMING_CLOCK_DIVIDE (0xff << 8) | ||
94 | #define BP_SSP_TIMING_CLOCK_RATE (0) | ||
95 | #define BM_SSP_TIMING_CLOCK_RATE (0xff) | ||
96 | #define HW_SSP_CTRL1(h) (ssp_is_old(h) ? 0x060 : 0x080) | ||
97 | #define BM_SSP_CTRL1_SDIO_IRQ (1 << 31) | ||
98 | #define BM_SSP_CTRL1_SDIO_IRQ_EN (1 << 30) | ||
99 | #define BM_SSP_CTRL1_RESP_ERR_IRQ (1 << 29) | ||
100 | #define BM_SSP_CTRL1_RESP_ERR_IRQ_EN (1 << 28) | ||
101 | #define BM_SSP_CTRL1_RESP_TIMEOUT_IRQ (1 << 27) | ||
102 | #define BM_SSP_CTRL1_RESP_TIMEOUT_IRQ_EN (1 << 26) | ||
103 | #define BM_SSP_CTRL1_DATA_TIMEOUT_IRQ (1 << 25) | ||
104 | #define BM_SSP_CTRL1_DATA_TIMEOUT_IRQ_EN (1 << 24) | ||
105 | #define BM_SSP_CTRL1_DATA_CRC_IRQ (1 << 23) | ||
106 | #define BM_SSP_CTRL1_DATA_CRC_IRQ_EN (1 << 22) | ||
107 | #define BM_SSP_CTRL1_FIFO_UNDERRUN_IRQ (1 << 21) | ||
108 | #define BM_SSP_CTRL1_FIFO_UNDERRUN_IRQ_EN (1 << 20) | ||
109 | #define BM_SSP_CTRL1_RECV_TIMEOUT_IRQ (1 << 17) | ||
110 | #define BM_SSP_CTRL1_RECV_TIMEOUT_IRQ_EN (1 << 16) | ||
111 | #define BM_SSP_CTRL1_FIFO_OVERRUN_IRQ (1 << 15) | ||
112 | #define BM_SSP_CTRL1_FIFO_OVERRUN_IRQ_EN (1 << 14) | ||
113 | #define BM_SSP_CTRL1_DMA_ENABLE (1 << 13) | ||
114 | #define BM_SSP_CTRL1_POLARITY (1 << 9) | ||
115 | #define BP_SSP_CTRL1_WORD_LENGTH (4) | ||
116 | #define BM_SSP_CTRL1_WORD_LENGTH (0xf << 4) | ||
117 | #define BP_SSP_CTRL1_SSP_MODE (0) | ||
118 | #define BM_SSP_CTRL1_SSP_MODE (0xf) | ||
119 | #define HW_SSP_SDRESP0(h) (ssp_is_old(h) ? 0x080 : 0x0a0) | ||
120 | #define HW_SSP_SDRESP1(h) (ssp_is_old(h) ? 0x090 : 0x0b0) | ||
121 | #define HW_SSP_SDRESP2(h) (ssp_is_old(h) ? 0x0a0 : 0x0c0) | ||
122 | #define HW_SSP_SDRESP3(h) (ssp_is_old(h) ? 0x0b0 : 0x0d0) | ||
123 | #define HW_SSP_STATUS(h) (ssp_is_old(h) ? 0x0c0 : 0x100) | ||
124 | #define BM_SSP_STATUS_CARD_DETECT (1 << 28) | ||
125 | #define BM_SSP_STATUS_SDIO_IRQ (1 << 17) | ||
126 | |||
127 | #define BF_SSP(value, field) (((value) << BP_SSP_##field) & BM_SSP_##field) | ||
128 | |||
129 | #define MXS_MMC_IRQ_BITS (BM_SSP_CTRL1_SDIO_IRQ | \ | 51 | #define MXS_MMC_IRQ_BITS (BM_SSP_CTRL1_SDIO_IRQ | \ |
130 | BM_SSP_CTRL1_RESP_ERR_IRQ | \ | 52 | BM_SSP_CTRL1_RESP_ERR_IRQ | \ |
131 | BM_SSP_CTRL1_RESP_TIMEOUT_IRQ | \ | 53 | BM_SSP_CTRL1_RESP_TIMEOUT_IRQ | \ |
@@ -135,31 +57,17 @@ | |||
135 | BM_SSP_CTRL1_RECV_TIMEOUT_IRQ | \ | 57 | BM_SSP_CTRL1_RECV_TIMEOUT_IRQ | \ |
136 | BM_SSP_CTRL1_FIFO_OVERRUN_IRQ) | 58 | BM_SSP_CTRL1_FIFO_OVERRUN_IRQ) |
137 | 59 | ||
138 | #define SSP_PIO_NUM 3 | 60 | /* card detect polling timeout */ |
139 | 61 | #define MXS_MMC_DETECT_TIMEOUT (HZ/2) | |
140 | enum mxs_mmc_id { | ||
141 | IMX23_MMC, | ||
142 | IMX28_MMC, | ||
143 | }; | ||
144 | 62 | ||
145 | struct mxs_mmc_host { | 63 | struct mxs_mmc_host { |
64 | struct mxs_ssp ssp; | ||
65 | |||
146 | struct mmc_host *mmc; | 66 | struct mmc_host *mmc; |
147 | struct mmc_request *mrq; | 67 | struct mmc_request *mrq; |
148 | struct mmc_command *cmd; | 68 | struct mmc_command *cmd; |
149 | struct mmc_data *data; | 69 | struct mmc_data *data; |
150 | 70 | ||
151 | void __iomem *base; | ||
152 | int dma_channel; | ||
153 | struct clk *clk; | ||
154 | unsigned int clk_rate; | ||
155 | |||
156 | struct dma_chan *dmach; | ||
157 | struct mxs_dma_data dma_data; | ||
158 | unsigned int dma_dir; | ||
159 | enum dma_transfer_direction slave_dirn; | ||
160 | u32 ssp_pio_words[SSP_PIO_NUM]; | ||
161 | |||
162 | enum mxs_mmc_id devid; | ||
163 | unsigned char bus_width; | 71 | unsigned char bus_width; |
164 | spinlock_t lock; | 72 | spinlock_t lock; |
165 | int sdio_irq_en; | 73 | int sdio_irq_en; |
@@ -186,16 +94,18 @@ static int mxs_mmc_get_ro(struct mmc_host *mmc) | |||
186 | static int mxs_mmc_get_cd(struct mmc_host *mmc) | 94 | static int mxs_mmc_get_cd(struct mmc_host *mmc) |
187 | { | 95 | { |
188 | struct mxs_mmc_host *host = mmc_priv(mmc); | 96 | struct mxs_mmc_host *host = mmc_priv(mmc); |
97 | struct mxs_ssp *ssp = &host->ssp; | ||
189 | 98 | ||
190 | return !(readl(host->base + HW_SSP_STATUS(host)) & | 99 | return !(readl(ssp->base + HW_SSP_STATUS(ssp)) & |
191 | BM_SSP_STATUS_CARD_DETECT); | 100 | BM_SSP_STATUS_CARD_DETECT); |
192 | } | 101 | } |
193 | 102 | ||
194 | static void mxs_mmc_reset(struct mxs_mmc_host *host) | 103 | static void mxs_mmc_reset(struct mxs_mmc_host *host) |
195 | { | 104 | { |
105 | struct mxs_ssp *ssp = &host->ssp; | ||
196 | u32 ctrl0, ctrl1; | 106 | u32 ctrl0, ctrl1; |
197 | 107 | ||
198 | stmp_reset_block(host->base); | 108 | stmp_reset_block(ssp->base); |
199 | 109 | ||
200 | ctrl0 = BM_SSP_CTRL0_IGNORE_CRC; | 110 | ctrl0 = BM_SSP_CTRL0_IGNORE_CRC; |
201 | ctrl1 = BF_SSP(0x3, CTRL1_SSP_MODE) | | 111 | ctrl1 = BF_SSP(0x3, CTRL1_SSP_MODE) | |
@@ -211,15 +121,15 @@ static void mxs_mmc_reset(struct mxs_mmc_host *host) | |||
211 | writel(BF_SSP(0xffff, TIMING_TIMEOUT) | | 121 | writel(BF_SSP(0xffff, TIMING_TIMEOUT) | |
212 | BF_SSP(2, TIMING_CLOCK_DIVIDE) | | 122 | BF_SSP(2, TIMING_CLOCK_DIVIDE) | |
213 | BF_SSP(0, TIMING_CLOCK_RATE), | 123 | BF_SSP(0, TIMING_CLOCK_RATE), |
214 | host->base + HW_SSP_TIMING(host)); | 124 | ssp->base + HW_SSP_TIMING(ssp)); |
215 | 125 | ||
216 | if (host->sdio_irq_en) { | 126 | if (host->sdio_irq_en) { |
217 | ctrl0 |= BM_SSP_CTRL0_SDIO_IRQ_CHECK; | 127 | ctrl0 |= BM_SSP_CTRL0_SDIO_IRQ_CHECK; |
218 | ctrl1 |= BM_SSP_CTRL1_SDIO_IRQ_EN; | 128 | ctrl1 |= BM_SSP_CTRL1_SDIO_IRQ_EN; |
219 | } | 129 | } |
220 | 130 | ||
221 | writel(ctrl0, host->base + HW_SSP_CTRL0); | 131 | writel(ctrl0, ssp->base + HW_SSP_CTRL0); |
222 | writel(ctrl1, host->base + HW_SSP_CTRL1(host)); | 132 | writel(ctrl1, ssp->base + HW_SSP_CTRL1(ssp)); |
223 | } | 133 | } |
224 | 134 | ||
225 | static void mxs_mmc_start_cmd(struct mxs_mmc_host *host, | 135 | static void mxs_mmc_start_cmd(struct mxs_mmc_host *host, |
@@ -230,21 +140,22 @@ static void mxs_mmc_request_done(struct mxs_mmc_host *host) | |||
230 | struct mmc_command *cmd = host->cmd; | 140 | struct mmc_command *cmd = host->cmd; |
231 | struct mmc_data *data = host->data; | 141 | struct mmc_data *data = host->data; |
232 | struct mmc_request *mrq = host->mrq; | 142 | struct mmc_request *mrq = host->mrq; |
143 | struct mxs_ssp *ssp = &host->ssp; | ||
233 | 144 | ||
234 | if (mmc_resp_type(cmd) & MMC_RSP_PRESENT) { | 145 | if (mmc_resp_type(cmd) & MMC_RSP_PRESENT) { |
235 | if (mmc_resp_type(cmd) & MMC_RSP_136) { | 146 | if (mmc_resp_type(cmd) & MMC_RSP_136) { |
236 | cmd->resp[3] = readl(host->base + HW_SSP_SDRESP0(host)); | 147 | cmd->resp[3] = readl(ssp->base + HW_SSP_SDRESP0(ssp)); |
237 | cmd->resp[2] = readl(host->base + HW_SSP_SDRESP1(host)); | 148 | cmd->resp[2] = readl(ssp->base + HW_SSP_SDRESP1(ssp)); |
238 | cmd->resp[1] = readl(host->base + HW_SSP_SDRESP2(host)); | 149 | cmd->resp[1] = readl(ssp->base + HW_SSP_SDRESP2(ssp)); |
239 | cmd->resp[0] = readl(host->base + HW_SSP_SDRESP3(host)); | 150 | cmd->resp[0] = readl(ssp->base + HW_SSP_SDRESP3(ssp)); |
240 | } else { | 151 | } else { |
241 | cmd->resp[0] = readl(host->base + HW_SSP_SDRESP0(host)); | 152 | cmd->resp[0] = readl(ssp->base + HW_SSP_SDRESP0(ssp)); |
242 | } | 153 | } |
243 | } | 154 | } |
244 | 155 | ||
245 | if (data) { | 156 | if (data) { |
246 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, | 157 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, |
247 | data->sg_len, host->dma_dir); | 158 | data->sg_len, ssp->dma_dir); |
248 | /* | 159 | /* |
249 | * If there was an error on any block, we mark all | 160 | * If there was an error on any block, we mark all |
250 | * data blocks as being in error. | 161 | * data blocks as being in error. |
@@ -277,13 +188,14 @@ static irqreturn_t mxs_mmc_irq_handler(int irq, void *dev_id) | |||
277 | struct mxs_mmc_host *host = dev_id; | 188 | struct mxs_mmc_host *host = dev_id; |
278 | struct mmc_command *cmd = host->cmd; | 189 | struct mmc_command *cmd = host->cmd; |
279 | struct mmc_data *data = host->data; | 190 | struct mmc_data *data = host->data; |
191 | struct mxs_ssp *ssp = &host->ssp; | ||
280 | u32 stat; | 192 | u32 stat; |
281 | 193 | ||
282 | spin_lock(&host->lock); | 194 | spin_lock(&host->lock); |
283 | 195 | ||
284 | stat = readl(host->base + HW_SSP_CTRL1(host)); | 196 | stat = readl(ssp->base + HW_SSP_CTRL1(ssp)); |
285 | writel(stat & MXS_MMC_IRQ_BITS, | 197 | writel(stat & MXS_MMC_IRQ_BITS, |
286 | host->base + HW_SSP_CTRL1(host) + STMP_OFFSET_REG_CLR); | 198 | ssp->base + HW_SSP_CTRL1(ssp) + STMP_OFFSET_REG_CLR); |
287 | 199 | ||
288 | spin_unlock(&host->lock); | 200 | spin_unlock(&host->lock); |
289 | 201 | ||
@@ -312,6 +224,7 @@ static irqreturn_t mxs_mmc_irq_handler(int irq, void *dev_id) | |||
312 | static struct dma_async_tx_descriptor *mxs_mmc_prep_dma( | 224 | static struct dma_async_tx_descriptor *mxs_mmc_prep_dma( |
313 | struct mxs_mmc_host *host, unsigned long flags) | 225 | struct mxs_mmc_host *host, unsigned long flags) |
314 | { | 226 | { |
227 | struct mxs_ssp *ssp = &host->ssp; | ||
315 | struct dma_async_tx_descriptor *desc; | 228 | struct dma_async_tx_descriptor *desc; |
316 | struct mmc_data *data = host->data; | 229 | struct mmc_data *data = host->data; |
317 | struct scatterlist * sgl; | 230 | struct scatterlist * sgl; |
@@ -320,24 +233,24 @@ static struct dma_async_tx_descriptor *mxs_mmc_prep_dma( | |||
320 | if (data) { | 233 | if (data) { |
321 | /* data */ | 234 | /* data */ |
322 | dma_map_sg(mmc_dev(host->mmc), data->sg, | 235 | dma_map_sg(mmc_dev(host->mmc), data->sg, |
323 | data->sg_len, host->dma_dir); | 236 | data->sg_len, ssp->dma_dir); |
324 | sgl = data->sg; | 237 | sgl = data->sg; |
325 | sg_len = data->sg_len; | 238 | sg_len = data->sg_len; |
326 | } else { | 239 | } else { |
327 | /* pio */ | 240 | /* pio */ |
328 | sgl = (struct scatterlist *) host->ssp_pio_words; | 241 | sgl = (struct scatterlist *) ssp->ssp_pio_words; |
329 | sg_len = SSP_PIO_NUM; | 242 | sg_len = SSP_PIO_NUM; |
330 | } | 243 | } |
331 | 244 | ||
332 | desc = dmaengine_prep_slave_sg(host->dmach, | 245 | desc = dmaengine_prep_slave_sg(ssp->dmach, |
333 | sgl, sg_len, host->slave_dirn, flags); | 246 | sgl, sg_len, ssp->slave_dirn, flags); |
334 | if (desc) { | 247 | if (desc) { |
335 | desc->callback = mxs_mmc_dma_irq_callback; | 248 | desc->callback = mxs_mmc_dma_irq_callback; |
336 | desc->callback_param = host; | 249 | desc->callback_param = host; |
337 | } else { | 250 | } else { |
338 | if (data) | 251 | if (data) |
339 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, | 252 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, |
340 | data->sg_len, host->dma_dir); | 253 | data->sg_len, ssp->dma_dir); |
341 | } | 254 | } |
342 | 255 | ||
343 | return desc; | 256 | return desc; |
@@ -345,6 +258,7 @@ static struct dma_async_tx_descriptor *mxs_mmc_prep_dma( | |||
345 | 258 | ||
346 | static void mxs_mmc_bc(struct mxs_mmc_host *host) | 259 | static void mxs_mmc_bc(struct mxs_mmc_host *host) |
347 | { | 260 | { |
261 | struct mxs_ssp *ssp = &host->ssp; | ||
348 | struct mmc_command *cmd = host->cmd; | 262 | struct mmc_command *cmd = host->cmd; |
349 | struct dma_async_tx_descriptor *desc; | 263 | struct dma_async_tx_descriptor *desc; |
350 | u32 ctrl0, cmd0, cmd1; | 264 | u32 ctrl0, cmd0, cmd1; |
@@ -358,17 +272,17 @@ static void mxs_mmc_bc(struct mxs_mmc_host *host) | |||
358 | cmd0 |= BM_SSP_CMD0_CONT_CLKING_EN | BM_SSP_CMD0_SLOW_CLKING_EN; | 272 | cmd0 |= BM_SSP_CMD0_CONT_CLKING_EN | BM_SSP_CMD0_SLOW_CLKING_EN; |
359 | } | 273 | } |
360 | 274 | ||
361 | host->ssp_pio_words[0] = ctrl0; | 275 | ssp->ssp_pio_words[0] = ctrl0; |
362 | host->ssp_pio_words[1] = cmd0; | 276 | ssp->ssp_pio_words[1] = cmd0; |
363 | host->ssp_pio_words[2] = cmd1; | 277 | ssp->ssp_pio_words[2] = cmd1; |
364 | host->dma_dir = DMA_NONE; | 278 | ssp->dma_dir = DMA_NONE; |
365 | host->slave_dirn = DMA_TRANS_NONE; | 279 | ssp->slave_dirn = DMA_TRANS_NONE; |
366 | desc = mxs_mmc_prep_dma(host, DMA_CTRL_ACK); | 280 | desc = mxs_mmc_prep_dma(host, DMA_CTRL_ACK); |
367 | if (!desc) | 281 | if (!desc) |
368 | goto out; | 282 | goto out; |
369 | 283 | ||
370 | dmaengine_submit(desc); | 284 | dmaengine_submit(desc); |
371 | dma_async_issue_pending(host->dmach); | 285 | dma_async_issue_pending(ssp->dmach); |
372 | return; | 286 | return; |
373 | 287 | ||
374 | out: | 288 | out: |
@@ -378,6 +292,7 @@ out: | |||
378 | 292 | ||
379 | static void mxs_mmc_ac(struct mxs_mmc_host *host) | 293 | static void mxs_mmc_ac(struct mxs_mmc_host *host) |
380 | { | 294 | { |
295 | struct mxs_ssp *ssp = &host->ssp; | ||
381 | struct mmc_command *cmd = host->cmd; | 296 | struct mmc_command *cmd = host->cmd; |
382 | struct dma_async_tx_descriptor *desc; | 297 | struct dma_async_tx_descriptor *desc; |
383 | u32 ignore_crc, get_resp, long_resp; | 298 | u32 ignore_crc, get_resp, long_resp; |
@@ -399,17 +314,17 @@ static void mxs_mmc_ac(struct mxs_mmc_host *host) | |||
399 | cmd0 |= BM_SSP_CMD0_CONT_CLKING_EN | BM_SSP_CMD0_SLOW_CLKING_EN; | 314 | cmd0 |= BM_SSP_CMD0_CONT_CLKING_EN | BM_SSP_CMD0_SLOW_CLKING_EN; |
400 | } | 315 | } |
401 | 316 | ||
402 | host->ssp_pio_words[0] = ctrl0; | 317 | ssp->ssp_pio_words[0] = ctrl0; |
403 | host->ssp_pio_words[1] = cmd0; | 318 | ssp->ssp_pio_words[1] = cmd0; |
404 | host->ssp_pio_words[2] = cmd1; | 319 | ssp->ssp_pio_words[2] = cmd1; |
405 | host->dma_dir = DMA_NONE; | 320 | ssp->dma_dir = DMA_NONE; |
406 | host->slave_dirn = DMA_TRANS_NONE; | 321 | ssp->slave_dirn = DMA_TRANS_NONE; |
407 | desc = mxs_mmc_prep_dma(host, DMA_CTRL_ACK); | 322 | desc = mxs_mmc_prep_dma(host, DMA_CTRL_ACK); |
408 | if (!desc) | 323 | if (!desc) |
409 | goto out; | 324 | goto out; |
410 | 325 | ||
411 | dmaengine_submit(desc); | 326 | dmaengine_submit(desc); |
412 | dma_async_issue_pending(host->dmach); | 327 | dma_async_issue_pending(ssp->dmach); |
413 | return; | 328 | return; |
414 | 329 | ||
415 | out: | 330 | out: |
@@ -447,6 +362,8 @@ static void mxs_mmc_adtc(struct mxs_mmc_host *host) | |||
447 | unsigned int data_size = 0, log2_blksz; | 362 | unsigned int data_size = 0, log2_blksz; |
448 | unsigned int blocks = data->blocks; | 363 | unsigned int blocks = data->blocks; |
449 | 364 | ||
365 | struct mxs_ssp *ssp = &host->ssp; | ||
366 | |||
450 | u32 ignore_crc, get_resp, long_resp, read; | 367 | u32 ignore_crc, get_resp, long_resp, read; |
451 | u32 ctrl0, cmd0, cmd1, val; | 368 | u32 ctrl0, cmd0, cmd1, val; |
452 | 369 | ||
@@ -489,15 +406,15 @@ static void mxs_mmc_adtc(struct mxs_mmc_host *host) | |||
489 | blocks = 1; | 406 | blocks = 1; |
490 | 407 | ||
491 | /* xfer count, block size and count need to be set differently */ | 408 | /* xfer count, block size and count need to be set differently */ |
492 | if (ssp_is_old(host)) { | 409 | if (ssp_is_old(ssp)) { |
493 | ctrl0 |= BF_SSP(data_size, CTRL0_XFER_COUNT); | 410 | ctrl0 |= BF_SSP(data_size, CTRL0_XFER_COUNT); |
494 | cmd0 |= BF_SSP(log2_blksz, CMD0_BLOCK_SIZE) | | 411 | cmd0 |= BF_SSP(log2_blksz, CMD0_BLOCK_SIZE) | |
495 | BF_SSP(blocks - 1, CMD0_BLOCK_COUNT); | 412 | BF_SSP(blocks - 1, CMD0_BLOCK_COUNT); |
496 | } else { | 413 | } else { |
497 | writel(data_size, host->base + HW_SSP_XFER_SIZE); | 414 | writel(data_size, ssp->base + HW_SSP_XFER_SIZE); |
498 | writel(BF_SSP(log2_blksz, BLOCK_SIZE_BLOCK_SIZE) | | 415 | writel(BF_SSP(log2_blksz, BLOCK_SIZE_BLOCK_SIZE) | |
499 | BF_SSP(blocks - 1, BLOCK_SIZE_BLOCK_COUNT), | 416 | BF_SSP(blocks - 1, BLOCK_SIZE_BLOCK_COUNT), |
500 | host->base + HW_SSP_BLOCK_SIZE); | 417 | ssp->base + HW_SSP_BLOCK_SIZE); |
501 | } | 418 | } |
502 | 419 | ||
503 | if ((cmd->opcode == MMC_STOP_TRANSMISSION) || | 420 | if ((cmd->opcode == MMC_STOP_TRANSMISSION) || |
@@ -512,18 +429,18 @@ static void mxs_mmc_adtc(struct mxs_mmc_host *host) | |||
512 | } | 429 | } |
513 | 430 | ||
514 | /* set the timeout count */ | 431 | /* set the timeout count */ |
515 | timeout = mxs_ns_to_ssp_ticks(host->clk_rate, data->timeout_ns); | 432 | timeout = mxs_ns_to_ssp_ticks(ssp->clk_rate, data->timeout_ns); |
516 | val = readl(host->base + HW_SSP_TIMING(host)); | 433 | val = readl(ssp->base + HW_SSP_TIMING(ssp)); |
517 | val &= ~(BM_SSP_TIMING_TIMEOUT); | 434 | val &= ~(BM_SSP_TIMING_TIMEOUT); |
518 | val |= BF_SSP(timeout, TIMING_TIMEOUT); | 435 | val |= BF_SSP(timeout, TIMING_TIMEOUT); |
519 | writel(val, host->base + HW_SSP_TIMING(host)); | 436 | writel(val, ssp->base + HW_SSP_TIMING(ssp)); |
520 | 437 | ||
521 | /* pio */ | 438 | /* pio */ |
522 | host->ssp_pio_words[0] = ctrl0; | 439 | ssp->ssp_pio_words[0] = ctrl0; |
523 | host->ssp_pio_words[1] = cmd0; | 440 | ssp->ssp_pio_words[1] = cmd0; |
524 | host->ssp_pio_words[2] = cmd1; | 441 | ssp->ssp_pio_words[2] = cmd1; |
525 | host->dma_dir = DMA_NONE; | 442 | ssp->dma_dir = DMA_NONE; |
526 | host->slave_dirn = DMA_TRANS_NONE; | 443 | ssp->slave_dirn = DMA_TRANS_NONE; |
527 | desc = mxs_mmc_prep_dma(host, 0); | 444 | desc = mxs_mmc_prep_dma(host, 0); |
528 | if (!desc) | 445 | if (!desc) |
529 | goto out; | 446 | goto out; |
@@ -531,14 +448,14 @@ static void mxs_mmc_adtc(struct mxs_mmc_host *host) | |||
531 | /* append data sg */ | 448 | /* append data sg */ |
532 | WARN_ON(host->data != NULL); | 449 | WARN_ON(host->data != NULL); |
533 | host->data = data; | 450 | host->data = data; |
534 | host->dma_dir = dma_data_dir; | 451 | ssp->dma_dir = dma_data_dir; |
535 | host->slave_dirn = slave_dirn; | 452 | ssp->slave_dirn = slave_dirn; |
536 | desc = mxs_mmc_prep_dma(host, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); | 453 | desc = mxs_mmc_prep_dma(host, DMA_PREP_INTERRUPT | DMA_CTRL_ACK); |
537 | if (!desc) | 454 | if (!desc) |
538 | goto out; | 455 | goto out; |
539 | 456 | ||
540 | dmaengine_submit(desc); | 457 | dmaengine_submit(desc); |
541 | dma_async_issue_pending(host->dmach); | 458 | dma_async_issue_pending(ssp->dmach); |
542 | return; | 459 | return; |
543 | out: | 460 | out: |
544 | dev_warn(mmc_dev(host->mmc), | 461 | dev_warn(mmc_dev(host->mmc), |
@@ -579,42 +496,6 @@ static void mxs_mmc_request(struct mmc_host *mmc, struct mmc_request *mrq) | |||
579 | mxs_mmc_start_cmd(host, mrq->cmd); | 496 | mxs_mmc_start_cmd(host, mrq->cmd); |
580 | } | 497 | } |
581 | 498 | ||
582 | static void mxs_mmc_set_clk_rate(struct mxs_mmc_host *host, unsigned int rate) | ||
583 | { | ||
584 | unsigned int ssp_clk, ssp_sck; | ||
585 | u32 clock_divide, clock_rate; | ||
586 | u32 val; | ||
587 | |||
588 | ssp_clk = clk_get_rate(host->clk); | ||
589 | |||
590 | for (clock_divide = 2; clock_divide <= 254; clock_divide += 2) { | ||
591 | clock_rate = DIV_ROUND_UP(ssp_clk, rate * clock_divide); | ||
592 | clock_rate = (clock_rate > 0) ? clock_rate - 1 : 0; | ||
593 | if (clock_rate <= 255) | ||
594 | break; | ||
595 | } | ||
596 | |||
597 | if (clock_divide > 254) { | ||
598 | dev_err(mmc_dev(host->mmc), | ||
599 | "%s: cannot set clock to %d\n", __func__, rate); | ||
600 | return; | ||
601 | } | ||
602 | |||
603 | ssp_sck = ssp_clk / clock_divide / (1 + clock_rate); | ||
604 | |||
605 | val = readl(host->base + HW_SSP_TIMING(host)); | ||
606 | val &= ~(BM_SSP_TIMING_CLOCK_DIVIDE | BM_SSP_TIMING_CLOCK_RATE); | ||
607 | val |= BF_SSP(clock_divide, TIMING_CLOCK_DIVIDE); | ||
608 | val |= BF_SSP(clock_rate, TIMING_CLOCK_RATE); | ||
609 | writel(val, host->base + HW_SSP_TIMING(host)); | ||
610 | |||
611 | host->clk_rate = ssp_sck; | ||
612 | |||
613 | dev_dbg(mmc_dev(host->mmc), | ||
614 | "%s: clock_divide %d, clock_rate %d, ssp_clk %d, rate_actual %d, rate_requested %d\n", | ||
615 | __func__, clock_divide, clock_rate, ssp_clk, ssp_sck, rate); | ||
616 | } | ||
617 | |||
618 | static void mxs_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | 499 | static void mxs_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) |
619 | { | 500 | { |
620 | struct mxs_mmc_host *host = mmc_priv(mmc); | 501 | struct mxs_mmc_host *host = mmc_priv(mmc); |
@@ -627,12 +508,13 @@ static void mxs_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
627 | host->bus_width = 0; | 508 | host->bus_width = 0; |
628 | 509 | ||
629 | if (ios->clock) | 510 | if (ios->clock) |
630 | mxs_mmc_set_clk_rate(host, ios->clock); | 511 | mxs_ssp_set_clk_rate(&host->ssp, ios->clock); |
631 | } | 512 | } |
632 | 513 | ||
633 | static void mxs_mmc_enable_sdio_irq(struct mmc_host *mmc, int enable) | 514 | static void mxs_mmc_enable_sdio_irq(struct mmc_host *mmc, int enable) |
634 | { | 515 | { |
635 | struct mxs_mmc_host *host = mmc_priv(mmc); | 516 | struct mxs_mmc_host *host = mmc_priv(mmc); |
517 | struct mxs_ssp *ssp = &host->ssp; | ||
636 | unsigned long flags; | 518 | unsigned long flags; |
637 | 519 | ||
638 | spin_lock_irqsave(&host->lock, flags); | 520 | spin_lock_irqsave(&host->lock, flags); |
@@ -641,19 +523,19 @@ static void mxs_mmc_enable_sdio_irq(struct mmc_host *mmc, int enable) | |||
641 | 523 | ||
642 | if (enable) { | 524 | if (enable) { |
643 | writel(BM_SSP_CTRL0_SDIO_IRQ_CHECK, | 525 | writel(BM_SSP_CTRL0_SDIO_IRQ_CHECK, |
644 | host->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | 526 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); |
645 | writel(BM_SSP_CTRL1_SDIO_IRQ_EN, | 527 | writel(BM_SSP_CTRL1_SDIO_IRQ_EN, |
646 | host->base + HW_SSP_CTRL1(host) + STMP_OFFSET_REG_SET); | 528 | host->base + HW_SSP_CTRL1(host) + STMP_OFFSET_REG_SET); |
647 | } else { | 529 | } else { |
648 | writel(BM_SSP_CTRL0_SDIO_IRQ_CHECK, | 530 | writel(BM_SSP_CTRL0_SDIO_IRQ_CHECK, |
649 | host->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | 531 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); |
650 | writel(BM_SSP_CTRL1_SDIO_IRQ_EN, | 532 | writel(BM_SSP_CTRL1_SDIO_IRQ_EN, |
651 | host->base + HW_SSP_CTRL1(host) + STMP_OFFSET_REG_CLR); | 533 | ssp->base + HW_SSP_CTRL1(ssp) + STMP_OFFSET_REG_CLR); |
652 | } | 534 | } |
653 | 535 | ||
654 | spin_unlock_irqrestore(&host->lock, flags); | 536 | spin_unlock_irqrestore(&host->lock, flags); |
655 | 537 | ||
656 | if (enable && readl(host->base + HW_SSP_STATUS(host)) & | 538 | if (enable && readl(ssp->base + HW_SSP_STATUS(ssp)) & |
657 | BM_SSP_STATUS_SDIO_IRQ) | 539 | BM_SSP_STATUS_SDIO_IRQ) |
658 | mmc_signal_sdio_irq(host->mmc); | 540 | mmc_signal_sdio_irq(host->mmc); |
659 | 541 | ||
@@ -670,34 +552,35 @@ static const struct mmc_host_ops mxs_mmc_ops = { | |||
670 | static bool mxs_mmc_dma_filter(struct dma_chan *chan, void *param) | 552 | static bool mxs_mmc_dma_filter(struct dma_chan *chan, void *param) |
671 | { | 553 | { |
672 | struct mxs_mmc_host *host = param; | 554 | struct mxs_mmc_host *host = param; |
555 | struct mxs_ssp *ssp = &host->ssp; | ||
673 | 556 | ||
674 | if (!mxs_dma_is_apbh(chan)) | 557 | if (!mxs_dma_is_apbh(chan)) |
675 | return false; | 558 | return false; |
676 | 559 | ||
677 | if (chan->chan_id != host->dma_channel) | 560 | if (chan->chan_id != ssp->dma_channel) |
678 | return false; | 561 | return false; |
679 | 562 | ||
680 | chan->private = &host->dma_data; | 563 | chan->private = &ssp->dma_data; |
681 | 564 | ||
682 | return true; | 565 | return true; |
683 | } | 566 | } |
684 | 567 | ||
685 | static struct platform_device_id mxs_mmc_ids[] = { | 568 | static struct platform_device_id mxs_ssp_ids[] = { |
686 | { | 569 | { |
687 | .name = "imx23-mmc", | 570 | .name = "imx23-mmc", |
688 | .driver_data = IMX23_MMC, | 571 | .driver_data = IMX23_SSP, |
689 | }, { | 572 | }, { |
690 | .name = "imx28-mmc", | 573 | .name = "imx28-mmc", |
691 | .driver_data = IMX28_MMC, | 574 | .driver_data = IMX28_SSP, |
692 | }, { | 575 | }, { |
693 | /* sentinel */ | 576 | /* sentinel */ |
694 | } | 577 | } |
695 | }; | 578 | }; |
696 | MODULE_DEVICE_TABLE(platform, mxs_mmc_ids); | 579 | MODULE_DEVICE_TABLE(platform, mxs_ssp_ids); |
697 | 580 | ||
698 | static const struct of_device_id mxs_mmc_dt_ids[] = { | 581 | static const struct of_device_id mxs_mmc_dt_ids[] = { |
699 | { .compatible = "fsl,imx23-mmc", .data = (void *) IMX23_MMC, }, | 582 | { .compatible = "fsl,imx23-mmc", .data = (void *) IMX23_SSP, }, |
700 | { .compatible = "fsl,imx28-mmc", .data = (void *) IMX28_MMC, }, | 583 | { .compatible = "fsl,imx28-mmc", .data = (void *) IMX28_SSP, }, |
701 | { /* sentinel */ } | 584 | { /* sentinel */ } |
702 | }; | 585 | }; |
703 | MODULE_DEVICE_TABLE(of, mxs_mmc_dt_ids); | 586 | MODULE_DEVICE_TABLE(of, mxs_mmc_dt_ids); |
@@ -716,6 +599,7 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
716 | dma_cap_mask_t mask; | 599 | dma_cap_mask_t mask; |
717 | struct regulator *reg_vmmc; | 600 | struct regulator *reg_vmmc; |
718 | enum of_gpio_flags flags; | 601 | enum of_gpio_flags flags; |
602 | struct mxs_ssp *ssp; | ||
719 | 603 | ||
720 | iores = platform_get_resource(pdev, IORESOURCE_MEM, 0); | 604 | iores = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
721 | dmares = platform_get_resource(pdev, IORESOURCE_DMA, 0); | 605 | dmares = platform_get_resource(pdev, IORESOURCE_DMA, 0); |
@@ -729,28 +613,30 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
729 | return -ENOMEM; | 613 | return -ENOMEM; |
730 | 614 | ||
731 | host = mmc_priv(mmc); | 615 | host = mmc_priv(mmc); |
732 | host->base = devm_request_and_ioremap(&pdev->dev, iores); | 616 | ssp = &host->ssp; |
733 | if (!host->base) { | 617 | ssp->dev = &pdev->dev; |
618 | ssp->base = devm_request_and_ioremap(&pdev->dev, iores); | ||
619 | if (!ssp->base) { | ||
734 | ret = -EADDRNOTAVAIL; | 620 | ret = -EADDRNOTAVAIL; |
735 | goto out_mmc_free; | 621 | goto out_mmc_free; |
736 | } | 622 | } |
737 | 623 | ||
738 | if (np) { | 624 | if (np) { |
739 | host->devid = (enum mxs_mmc_id) of_id->data; | 625 | ssp->devid = (enum mxs_ssp_id) of_id->data; |
740 | /* | 626 | /* |
741 | * TODO: This is a temporary solution and should be changed | 627 | * TODO: This is a temporary solution and should be changed |
742 | * to use generic DMA binding later when the helpers get in. | 628 | * to use generic DMA binding later when the helpers get in. |
743 | */ | 629 | */ |
744 | ret = of_property_read_u32(np, "fsl,ssp-dma-channel", | 630 | ret = of_property_read_u32(np, "fsl,ssp-dma-channel", |
745 | &host->dma_channel); | 631 | &ssp->dma_channel); |
746 | if (ret) { | 632 | if (ret) { |
747 | dev_err(mmc_dev(host->mmc), | 633 | dev_err(mmc_dev(host->mmc), |
748 | "failed to get dma channel\n"); | 634 | "failed to get dma channel\n"); |
749 | goto out_mmc_free; | 635 | goto out_mmc_free; |
750 | } | 636 | } |
751 | } else { | 637 | } else { |
752 | host->devid = pdev->id_entry->driver_data; | 638 | ssp->devid = pdev->id_entry->driver_data; |
753 | host->dma_channel = dmares->start; | 639 | ssp->dma_channel = dmares->start; |
754 | } | 640 | } |
755 | 641 | ||
756 | host->mmc = mmc; | 642 | host->mmc = mmc; |
@@ -772,20 +658,20 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
772 | goto out_mmc_free; | 658 | goto out_mmc_free; |
773 | } | 659 | } |
774 | 660 | ||
775 | host->clk = clk_get(&pdev->dev, NULL); | 661 | ssp->clk = clk_get(&pdev->dev, NULL); |
776 | if (IS_ERR(host->clk)) { | 662 | if (IS_ERR(ssp->clk)) { |
777 | ret = PTR_ERR(host->clk); | 663 | ret = PTR_ERR(ssp->clk); |
778 | goto out_mmc_free; | 664 | goto out_mmc_free; |
779 | } | 665 | } |
780 | clk_prepare_enable(host->clk); | 666 | clk_prepare_enable(ssp->clk); |
781 | 667 | ||
782 | mxs_mmc_reset(host); | 668 | mxs_mmc_reset(host); |
783 | 669 | ||
784 | dma_cap_zero(mask); | 670 | dma_cap_zero(mask); |
785 | dma_cap_set(DMA_SLAVE, mask); | 671 | dma_cap_set(DMA_SLAVE, mask); |
786 | host->dma_data.chan_irq = irq_dma; | 672 | ssp->dma_data.chan_irq = irq_dma; |
787 | host->dmach = dma_request_channel(mask, mxs_mmc_dma_filter, host); | 673 | ssp->dmach = dma_request_channel(mask, mxs_mmc_dma_filter, host); |
788 | if (!host->dmach) { | 674 | if (!ssp->dmach) { |
789 | dev_err(mmc_dev(host->mmc), | 675 | dev_err(mmc_dev(host->mmc), |
790 | "%s: failed to request dma\n", __func__); | 676 | "%s: failed to request dma\n", __func__); |
791 | goto out_clk_put; | 677 | goto out_clk_put; |
@@ -822,9 +708,9 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
822 | 708 | ||
823 | mmc->max_segs = 52; | 709 | mmc->max_segs = 52; |
824 | mmc->max_blk_size = 1 << 0xf; | 710 | mmc->max_blk_size = 1 << 0xf; |
825 | mmc->max_blk_count = (ssp_is_old(host)) ? 0xff : 0xffffff; | 711 | mmc->max_blk_count = (ssp_is_old(ssp)) ? 0xff : 0xffffff; |
826 | mmc->max_req_size = (ssp_is_old(host)) ? 0xffff : 0xffffffff; | 712 | mmc->max_req_size = (ssp_is_old(ssp)) ? 0xffff : 0xffffffff; |
827 | mmc->max_seg_size = dma_get_max_seg_size(host->dmach->device->dev); | 713 | mmc->max_seg_size = dma_get_max_seg_size(ssp->dmach->device->dev); |
828 | 714 | ||
829 | platform_set_drvdata(pdev, mmc); | 715 | platform_set_drvdata(pdev, mmc); |
830 | 716 | ||
@@ -844,11 +730,11 @@ static int mxs_mmc_probe(struct platform_device *pdev) | |||
844 | return 0; | 730 | return 0; |
845 | 731 | ||
846 | out_free_dma: | 732 | out_free_dma: |
847 | if (host->dmach) | 733 | if (ssp->dmach) |
848 | dma_release_channel(host->dmach); | 734 | dma_release_channel(ssp->dmach); |
849 | out_clk_put: | 735 | out_clk_put: |
850 | clk_disable_unprepare(host->clk); | 736 | clk_disable_unprepare(ssp->clk); |
851 | clk_put(host->clk); | 737 | clk_put(ssp->clk); |
852 | out_mmc_free: | 738 | out_mmc_free: |
853 | mmc_free_host(mmc); | 739 | mmc_free_host(mmc); |
854 | return ret; | 740 | return ret; |
@@ -858,16 +744,17 @@ static int mxs_mmc_remove(struct platform_device *pdev) | |||
858 | { | 744 | { |
859 | struct mmc_host *mmc = platform_get_drvdata(pdev); | 745 | struct mmc_host *mmc = platform_get_drvdata(pdev); |
860 | struct mxs_mmc_host *host = mmc_priv(mmc); | 746 | struct mxs_mmc_host *host = mmc_priv(mmc); |
747 | struct mxs_ssp *ssp = &host->ssp; | ||
861 | 748 | ||
862 | mmc_remove_host(mmc); | 749 | mmc_remove_host(mmc); |
863 | 750 | ||
864 | platform_set_drvdata(pdev, NULL); | 751 | platform_set_drvdata(pdev, NULL); |
865 | 752 | ||
866 | if (host->dmach) | 753 | if (ssp->dmach) |
867 | dma_release_channel(host->dmach); | 754 | dma_release_channel(ssp->dmach); |
868 | 755 | ||
869 | clk_disable_unprepare(host->clk); | 756 | clk_disable_unprepare(ssp->clk); |
870 | clk_put(host->clk); | 757 | clk_put(ssp->clk); |
871 | 758 | ||
872 | mmc_free_host(mmc); | 759 | mmc_free_host(mmc); |
873 | 760 | ||
@@ -879,11 +766,12 @@ static int mxs_mmc_suspend(struct device *dev) | |||
879 | { | 766 | { |
880 | struct mmc_host *mmc = dev_get_drvdata(dev); | 767 | struct mmc_host *mmc = dev_get_drvdata(dev); |
881 | struct mxs_mmc_host *host = mmc_priv(mmc); | 768 | struct mxs_mmc_host *host = mmc_priv(mmc); |
769 | struct mxs_ssp *ssp = &host->ssp; | ||
882 | int ret = 0; | 770 | int ret = 0; |
883 | 771 | ||
884 | ret = mmc_suspend_host(mmc); | 772 | ret = mmc_suspend_host(mmc); |
885 | 773 | ||
886 | clk_disable_unprepare(host->clk); | 774 | clk_disable_unprepare(ssp->clk); |
887 | 775 | ||
888 | return ret; | 776 | return ret; |
889 | } | 777 | } |
@@ -892,9 +780,10 @@ static int mxs_mmc_resume(struct device *dev) | |||
892 | { | 780 | { |
893 | struct mmc_host *mmc = dev_get_drvdata(dev); | 781 | struct mmc_host *mmc = dev_get_drvdata(dev); |
894 | struct mxs_mmc_host *host = mmc_priv(mmc); | 782 | struct mxs_mmc_host *host = mmc_priv(mmc); |
783 | struct mxs_ssp *ssp = &host->ssp; | ||
895 | int ret = 0; | 784 | int ret = 0; |
896 | 785 | ||
897 | clk_prepare_enable(host->clk); | 786 | clk_prepare_enable(ssp->clk); |
898 | 787 | ||
899 | ret = mmc_resume_host(mmc); | 788 | ret = mmc_resume_host(mmc); |
900 | 789 | ||
@@ -910,7 +799,7 @@ static const struct dev_pm_ops mxs_mmc_pm_ops = { | |||
910 | static struct platform_driver mxs_mmc_driver = { | 799 | static struct platform_driver mxs_mmc_driver = { |
911 | .probe = mxs_mmc_probe, | 800 | .probe = mxs_mmc_probe, |
912 | .remove = mxs_mmc_remove, | 801 | .remove = mxs_mmc_remove, |
913 | .id_table = mxs_mmc_ids, | 802 | .id_table = mxs_ssp_ids, |
914 | .driver = { | 803 | .driver = { |
915 | .name = DRIVER_NAME, | 804 | .name = DRIVER_NAME, |
916 | .owner = THIS_MODULE, | 805 | .owner = THIS_MODULE, |