diff options
author | Mark Brown <broonie@linaro.org> | 2013-10-25 04:51:34 -0400 |
---|---|---|
committer | Mark Brown <broonie@linaro.org> | 2013-10-25 04:51:34 -0400 |
commit | 6c99db1eb880cd12c54c810abae7ea7976baf393 (patch) | |
tree | 29a0099e0b2b19db2e4ba87e70fce8c20faa1abe | |
parent | 8211e6b8facd9d0da3e8f6e51657cba8b0af19da (diff) | |
parent | 42e182f86222dee2679c19fb1ab5006354a3be62 (diff) |
Merge remote-tracking branch 'spi/topic/mxs' into spi-next
-rw-r--r-- | drivers/spi/spi-mxs.c | 189 |
1 files changed, 80 insertions, 109 deletions
diff --git a/drivers/spi/spi-mxs.c b/drivers/spi/spi-mxs.c index 312c7f99c4a7..de333059a9a7 100644 --- a/drivers/spi/spi-mxs.c +++ b/drivers/spi/spi-mxs.c | |||
@@ -57,34 +57,53 @@ | |||
57 | 57 | ||
58 | #define SG_MAXLEN 0xff00 | 58 | #define SG_MAXLEN 0xff00 |
59 | 59 | ||
60 | /* | ||
61 | * Flags for txrx functions. More efficient that using an argument register for | ||
62 | * each one. | ||
63 | */ | ||
64 | #define TXRX_WRITE (1<<0) /* This is a write */ | ||
65 | #define TXRX_DEASSERT_CS (1<<1) /* De-assert CS at end of txrx */ | ||
66 | |||
60 | struct mxs_spi { | 67 | struct mxs_spi { |
61 | struct mxs_ssp ssp; | 68 | struct mxs_ssp ssp; |
62 | struct completion c; | 69 | struct completion c; |
70 | unsigned int sck; /* Rate requested (vs actual) */ | ||
63 | }; | 71 | }; |
64 | 72 | ||
65 | static int mxs_spi_setup_transfer(struct spi_device *dev, | 73 | static int mxs_spi_setup_transfer(struct spi_device *dev, |
66 | struct spi_transfer *t) | 74 | const struct spi_transfer *t) |
67 | { | 75 | { |
68 | struct mxs_spi *spi = spi_master_get_devdata(dev->master); | 76 | struct mxs_spi *spi = spi_master_get_devdata(dev->master); |
69 | struct mxs_ssp *ssp = &spi->ssp; | 77 | struct mxs_ssp *ssp = &spi->ssp; |
70 | uint32_t hz = 0; | 78 | const unsigned int hz = min(dev->max_speed_hz, t->speed_hz); |
71 | 79 | ||
72 | hz = dev->max_speed_hz; | ||
73 | if (t && t->speed_hz) | ||
74 | hz = min(hz, t->speed_hz); | ||
75 | if (hz == 0) { | 80 | if (hz == 0) { |
76 | dev_err(&dev->dev, "Cannot continue with zero clock\n"); | 81 | dev_err(&dev->dev, "SPI clock rate of zero not allowed\n"); |
77 | return -EINVAL; | 82 | return -EINVAL; |
78 | } | 83 | } |
79 | 84 | ||
80 | mxs_ssp_set_clk_rate(ssp, hz); | 85 | if (hz != spi->sck) { |
86 | mxs_ssp_set_clk_rate(ssp, hz); | ||
87 | /* | ||
88 | * Save requested rate, hz, rather than the actual rate, | ||
89 | * ssp->clk_rate. Otherwise we would set the rate every trasfer | ||
90 | * when the actual rate is not quite the same as requested rate. | ||
91 | */ | ||
92 | spi->sck = hz; | ||
93 | /* | ||
94 | * Perhaps we should return an error if the actual clock is | ||
95 | * nowhere close to what was requested? | ||
96 | */ | ||
97 | } | ||
98 | |||
99 | writel(BM_SSP_CTRL0_LOCK_CS, | ||
100 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
81 | 101 | ||
82 | writel(BF_SSP_CTRL1_SSP_MODE(BV_SSP_CTRL1_SSP_MODE__SPI) | | 102 | writel(BF_SSP_CTRL1_SSP_MODE(BV_SSP_CTRL1_SSP_MODE__SPI) | |
83 | BF_SSP_CTRL1_WORD_LENGTH | 103 | BF_SSP_CTRL1_WORD_LENGTH(BV_SSP_CTRL1_WORD_LENGTH__EIGHT_BITS) | |
84 | (BV_SSP_CTRL1_WORD_LENGTH__EIGHT_BITS) | | 104 | ((dev->mode & SPI_CPOL) ? BM_SSP_CTRL1_POLARITY : 0) | |
85 | ((dev->mode & SPI_CPOL) ? BM_SSP_CTRL1_POLARITY : 0) | | 105 | ((dev->mode & SPI_CPHA) ? BM_SSP_CTRL1_PHASE : 0), |
86 | ((dev->mode & SPI_CPHA) ? BM_SSP_CTRL1_PHASE : 0), | 106 | ssp->base + HW_SSP_CTRL1(ssp)); |
87 | ssp->base + HW_SSP_CTRL1(ssp)); | ||
88 | 107 | ||
89 | writel(0x0, ssp->base + HW_SSP_CMD0); | 108 | writel(0x0, ssp->base + HW_SSP_CMD0); |
90 | writel(0x0, ssp->base + HW_SSP_CMD1); | 109 | writel(0x0, ssp->base + HW_SSP_CMD1); |
@@ -94,26 +113,15 @@ static int mxs_spi_setup_transfer(struct spi_device *dev, | |||
94 | 113 | ||
95 | static int mxs_spi_setup(struct spi_device *dev) | 114 | static int mxs_spi_setup(struct spi_device *dev) |
96 | { | 115 | { |
97 | int err = 0; | ||
98 | |||
99 | if (!dev->bits_per_word) | 116 | if (!dev->bits_per_word) |
100 | dev->bits_per_word = 8; | 117 | dev->bits_per_word = 8; |
101 | 118 | ||
102 | if (dev->mode & ~(SPI_CPOL | SPI_CPHA)) | 119 | return 0; |
103 | return -EINVAL; | ||
104 | |||
105 | err = mxs_spi_setup_transfer(dev, NULL); | ||
106 | if (err) { | ||
107 | dev_err(&dev->dev, | ||
108 | "Failed to setup transfer, error = %d\n", err); | ||
109 | } | ||
110 | |||
111 | return err; | ||
112 | } | 120 | } |
113 | 121 | ||
114 | static uint32_t mxs_spi_cs_to_reg(unsigned cs) | 122 | static u32 mxs_spi_cs_to_reg(unsigned cs) |
115 | { | 123 | { |
116 | uint32_t select = 0; | 124 | u32 select = 0; |
117 | 125 | ||
118 | /* | 126 | /* |
119 | * i.MX28 Datasheet: 17.10.1: HW_SSP_CTRL0 | 127 | * i.MX28 Datasheet: 17.10.1: HW_SSP_CTRL0 |
@@ -131,43 +139,11 @@ static uint32_t mxs_spi_cs_to_reg(unsigned cs) | |||
131 | return select; | 139 | return select; |
132 | } | 140 | } |
133 | 141 | ||
134 | static void mxs_spi_set_cs(struct mxs_spi *spi, unsigned cs) | ||
135 | { | ||
136 | const uint32_t mask = | ||
137 | BM_SSP_CTRL0_WAIT_FOR_CMD | BM_SSP_CTRL0_WAIT_FOR_IRQ; | ||
138 | uint32_t select; | ||
139 | struct mxs_ssp *ssp = &spi->ssp; | ||
140 | |||
141 | writel(mask, ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | ||
142 | select = mxs_spi_cs_to_reg(cs); | ||
143 | writel(select, ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
144 | } | ||
145 | |||
146 | static inline void mxs_spi_enable(struct mxs_spi *spi) | ||
147 | { | ||
148 | struct mxs_ssp *ssp = &spi->ssp; | ||
149 | |||
150 | writel(BM_SSP_CTRL0_LOCK_CS, | ||
151 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
152 | writel(BM_SSP_CTRL0_IGNORE_CRC, | ||
153 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | ||
154 | } | ||
155 | |||
156 | static inline void mxs_spi_disable(struct mxs_spi *spi) | ||
157 | { | ||
158 | struct mxs_ssp *ssp = &spi->ssp; | ||
159 | |||
160 | writel(BM_SSP_CTRL0_LOCK_CS, | ||
161 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | ||
162 | writel(BM_SSP_CTRL0_IGNORE_CRC, | ||
163 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
164 | } | ||
165 | |||
166 | static int mxs_ssp_wait(struct mxs_spi *spi, int offset, int mask, bool set) | 142 | static int mxs_ssp_wait(struct mxs_spi *spi, int offset, int mask, bool set) |
167 | { | 143 | { |
168 | const unsigned long timeout = jiffies + msecs_to_jiffies(SSP_TIMEOUT); | 144 | const unsigned long timeout = jiffies + msecs_to_jiffies(SSP_TIMEOUT); |
169 | struct mxs_ssp *ssp = &spi->ssp; | 145 | struct mxs_ssp *ssp = &spi->ssp; |
170 | uint32_t reg; | 146 | u32 reg; |
171 | 147 | ||
172 | do { | 148 | do { |
173 | reg = readl_relaxed(ssp->base + offset); | 149 | reg = readl_relaxed(ssp->base + offset); |
@@ -200,9 +176,9 @@ static irqreturn_t mxs_ssp_irq_handler(int irq, void *dev_id) | |||
200 | return IRQ_HANDLED; | 176 | return IRQ_HANDLED; |
201 | } | 177 | } |
202 | 178 | ||
203 | static int mxs_spi_txrx_dma(struct mxs_spi *spi, int cs, | 179 | static int mxs_spi_txrx_dma(struct mxs_spi *spi, |
204 | unsigned char *buf, int len, | 180 | unsigned char *buf, int len, |
205 | int *first, int *last, int write) | 181 | unsigned int flags) |
206 | { | 182 | { |
207 | struct mxs_ssp *ssp = &spi->ssp; | 183 | struct mxs_ssp *ssp = &spi->ssp; |
208 | struct dma_async_tx_descriptor *desc = NULL; | 184 | struct dma_async_tx_descriptor *desc = NULL; |
@@ -211,11 +187,11 @@ static int mxs_spi_txrx_dma(struct mxs_spi *spi, int cs, | |||
211 | const int sgs = DIV_ROUND_UP(len, desc_len); | 187 | const int sgs = DIV_ROUND_UP(len, desc_len); |
212 | int sg_count; | 188 | int sg_count; |
213 | int min, ret; | 189 | int min, ret; |
214 | uint32_t ctrl0; | 190 | u32 ctrl0; |
215 | struct page *vm_page; | 191 | struct page *vm_page; |
216 | void *sg_buf; | 192 | void *sg_buf; |
217 | struct { | 193 | struct { |
218 | uint32_t pio[4]; | 194 | u32 pio[4]; |
219 | struct scatterlist sg; | 195 | struct scatterlist sg; |
220 | } *dma_xfer; | 196 | } *dma_xfer; |
221 | 197 | ||
@@ -228,21 +204,25 @@ static int mxs_spi_txrx_dma(struct mxs_spi *spi, int cs, | |||
228 | 204 | ||
229 | INIT_COMPLETION(spi->c); | 205 | INIT_COMPLETION(spi->c); |
230 | 206 | ||
207 | /* Chip select was already programmed into CTRL0 */ | ||
231 | ctrl0 = readl(ssp->base + HW_SSP_CTRL0); | 208 | ctrl0 = readl(ssp->base + HW_SSP_CTRL0); |
232 | ctrl0 &= ~BM_SSP_CTRL0_XFER_COUNT; | 209 | ctrl0 &= ~(BM_SSP_CTRL0_XFER_COUNT | BM_SSP_CTRL0_IGNORE_CRC | |
233 | ctrl0 |= BM_SSP_CTRL0_DATA_XFER | mxs_spi_cs_to_reg(cs); | 210 | BM_SSP_CTRL0_READ); |
211 | ctrl0 |= BM_SSP_CTRL0_DATA_XFER; | ||
234 | 212 | ||
235 | if (*first) | 213 | if (!(flags & TXRX_WRITE)) |
236 | ctrl0 |= BM_SSP_CTRL0_LOCK_CS; | ||
237 | if (!write) | ||
238 | ctrl0 |= BM_SSP_CTRL0_READ; | 214 | ctrl0 |= BM_SSP_CTRL0_READ; |
239 | 215 | ||
240 | /* Queue the DMA data transfer. */ | 216 | /* Queue the DMA data transfer. */ |
241 | for (sg_count = 0; sg_count < sgs; sg_count++) { | 217 | for (sg_count = 0; sg_count < sgs; sg_count++) { |
218 | /* Prepare the transfer descriptor. */ | ||
242 | min = min(len, desc_len); | 219 | min = min(len, desc_len); |
243 | 220 | ||
244 | /* Prepare the transfer descriptor. */ | 221 | /* |
245 | if ((sg_count + 1 == sgs) && *last) | 222 | * De-assert CS on last segment if flag is set (i.e., no more |
223 | * transfers will follow) | ||
224 | */ | ||
225 | if ((sg_count + 1 == sgs) && (flags & TXRX_DEASSERT_CS)) | ||
246 | ctrl0 |= BM_SSP_CTRL0_IGNORE_CRC; | 226 | ctrl0 |= BM_SSP_CTRL0_IGNORE_CRC; |
247 | 227 | ||
248 | if (ssp->devid == IMX23_SSP) { | 228 | if (ssp->devid == IMX23_SSP) { |
@@ -267,7 +247,7 @@ static int mxs_spi_txrx_dma(struct mxs_spi *spi, int cs, | |||
267 | 247 | ||
268 | sg_init_one(&dma_xfer[sg_count].sg, sg_buf, min); | 248 | sg_init_one(&dma_xfer[sg_count].sg, sg_buf, min); |
269 | ret = dma_map_sg(ssp->dev, &dma_xfer[sg_count].sg, 1, | 249 | ret = dma_map_sg(ssp->dev, &dma_xfer[sg_count].sg, 1, |
270 | write ? DMA_TO_DEVICE : DMA_FROM_DEVICE); | 250 | (flags & TXRX_WRITE) ? DMA_TO_DEVICE : DMA_FROM_DEVICE); |
271 | 251 | ||
272 | len -= min; | 252 | len -= min; |
273 | buf += min; | 253 | buf += min; |
@@ -287,7 +267,7 @@ static int mxs_spi_txrx_dma(struct mxs_spi *spi, int cs, | |||
287 | 267 | ||
288 | desc = dmaengine_prep_slave_sg(ssp->dmach, | 268 | desc = dmaengine_prep_slave_sg(ssp->dmach, |
289 | &dma_xfer[sg_count].sg, 1, | 269 | &dma_xfer[sg_count].sg, 1, |
290 | write ? DMA_MEM_TO_DEV : DMA_DEV_TO_MEM, | 270 | (flags & TXRX_WRITE) ? DMA_MEM_TO_DEV : DMA_DEV_TO_MEM, |
291 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); | 271 | DMA_PREP_INTERRUPT | DMA_CTRL_ACK); |
292 | 272 | ||
293 | if (!desc) { | 273 | if (!desc) { |
@@ -324,7 +304,7 @@ err_vmalloc: | |||
324 | while (--sg_count >= 0) { | 304 | while (--sg_count >= 0) { |
325 | err_mapped: | 305 | err_mapped: |
326 | dma_unmap_sg(ssp->dev, &dma_xfer[sg_count].sg, 1, | 306 | dma_unmap_sg(ssp->dev, &dma_xfer[sg_count].sg, 1, |
327 | write ? DMA_TO_DEVICE : DMA_FROM_DEVICE); | 307 | (flags & TXRX_WRITE) ? DMA_TO_DEVICE : DMA_FROM_DEVICE); |
328 | } | 308 | } |
329 | 309 | ||
330 | kfree(dma_xfer); | 310 | kfree(dma_xfer); |
@@ -332,20 +312,19 @@ err_mapped: | |||
332 | return ret; | 312 | return ret; |
333 | } | 313 | } |
334 | 314 | ||
335 | static int mxs_spi_txrx_pio(struct mxs_spi *spi, int cs, | 315 | static int mxs_spi_txrx_pio(struct mxs_spi *spi, |
336 | unsigned char *buf, int len, | 316 | unsigned char *buf, int len, |
337 | int *first, int *last, int write) | 317 | unsigned int flags) |
338 | { | 318 | { |
339 | struct mxs_ssp *ssp = &spi->ssp; | 319 | struct mxs_ssp *ssp = &spi->ssp; |
340 | 320 | ||
341 | if (*first) | 321 | writel(BM_SSP_CTRL0_IGNORE_CRC, |
342 | mxs_spi_enable(spi); | 322 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); |
343 | |||
344 | mxs_spi_set_cs(spi, cs); | ||
345 | 323 | ||
346 | while (len--) { | 324 | while (len--) { |
347 | if (*last && len == 0) | 325 | if (len == 0 && (flags & TXRX_DEASSERT_CS)) |
348 | mxs_spi_disable(spi); | 326 | writel(BM_SSP_CTRL0_IGNORE_CRC, |
327 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
349 | 328 | ||
350 | if (ssp->devid == IMX23_SSP) { | 329 | if (ssp->devid == IMX23_SSP) { |
351 | writel(BM_SSP_CTRL0_XFER_COUNT, | 330 | writel(BM_SSP_CTRL0_XFER_COUNT, |
@@ -356,7 +335,7 @@ static int mxs_spi_txrx_pio(struct mxs_spi *spi, int cs, | |||
356 | writel(1, ssp->base + HW_SSP_XFER_SIZE); | 335 | writel(1, ssp->base + HW_SSP_XFER_SIZE); |
357 | } | 336 | } |
358 | 337 | ||
359 | if (write) | 338 | if (flags & TXRX_WRITE) |
360 | writel(BM_SSP_CTRL0_READ, | 339 | writel(BM_SSP_CTRL0_READ, |
361 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | 340 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); |
362 | else | 341 | else |
@@ -369,13 +348,13 @@ static int mxs_spi_txrx_pio(struct mxs_spi *spi, int cs, | |||
369 | if (mxs_ssp_wait(spi, HW_SSP_CTRL0, BM_SSP_CTRL0_RUN, 1)) | 348 | if (mxs_ssp_wait(spi, HW_SSP_CTRL0, BM_SSP_CTRL0_RUN, 1)) |
370 | return -ETIMEDOUT; | 349 | return -ETIMEDOUT; |
371 | 350 | ||
372 | if (write) | 351 | if (flags & TXRX_WRITE) |
373 | writel(*buf, ssp->base + HW_SSP_DATA(ssp)); | 352 | writel(*buf, ssp->base + HW_SSP_DATA(ssp)); |
374 | 353 | ||
375 | writel(BM_SSP_CTRL0_DATA_XFER, | 354 | writel(BM_SSP_CTRL0_DATA_XFER, |
376 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | 355 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); |
377 | 356 | ||
378 | if (!write) { | 357 | if (!(flags & TXRX_WRITE)) { |
379 | if (mxs_ssp_wait(spi, HW_SSP_STATUS(ssp), | 358 | if (mxs_ssp_wait(spi, HW_SSP_STATUS(ssp), |
380 | BM_SSP_STATUS_FIFO_EMPTY, 0)) | 359 | BM_SSP_STATUS_FIFO_EMPTY, 0)) |
381 | return -ETIMEDOUT; | 360 | return -ETIMEDOUT; |
@@ -400,14 +379,15 @@ static int mxs_spi_transfer_one(struct spi_master *master, | |||
400 | { | 379 | { |
401 | struct mxs_spi *spi = spi_master_get_devdata(master); | 380 | struct mxs_spi *spi = spi_master_get_devdata(master); |
402 | struct mxs_ssp *ssp = &spi->ssp; | 381 | struct mxs_ssp *ssp = &spi->ssp; |
403 | int first, last; | ||
404 | struct spi_transfer *t, *tmp_t; | 382 | struct spi_transfer *t, *tmp_t; |
383 | unsigned int flag; | ||
405 | int status = 0; | 384 | int status = 0; |
406 | int cs; | ||
407 | |||
408 | first = last = 0; | ||
409 | 385 | ||
410 | cs = m->spi->chip_select; | 386 | /* Program CS register bits here, it will be used for all transfers. */ |
387 | writel(BM_SSP_CTRL0_WAIT_FOR_CMD | BM_SSP_CTRL0_WAIT_FOR_IRQ, | ||
388 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_CLR); | ||
389 | writel(mxs_spi_cs_to_reg(m->spi->chip_select), | ||
390 | ssp->base + HW_SSP_CTRL0 + STMP_OFFSET_REG_SET); | ||
411 | 391 | ||
412 | list_for_each_entry_safe(t, tmp_t, &m->transfers, transfer_list) { | 392 | list_for_each_entry_safe(t, tmp_t, &m->transfers, transfer_list) { |
413 | 393 | ||
@@ -415,16 +395,9 @@ static int mxs_spi_transfer_one(struct spi_master *master, | |||
415 | if (status) | 395 | if (status) |
416 | break; | 396 | break; |
417 | 397 | ||
418 | if (&t->transfer_list == m->transfers.next) | 398 | /* De-assert on last transfer, inverted by cs_change flag */ |
419 | first = 1; | 399 | flag = (&t->transfer_list == m->transfers.prev) ^ t->cs_change ? |
420 | if (&t->transfer_list == m->transfers.prev) | 400 | TXRX_DEASSERT_CS : 0; |
421 | last = 1; | ||
422 | if ((t->rx_buf && t->tx_buf) || (t->rx_dma && t->tx_dma)) { | ||
423 | dev_err(ssp->dev, | ||
424 | "Cannot send and receive simultaneously\n"); | ||
425 | status = -EINVAL; | ||
426 | break; | ||
427 | } | ||
428 | 401 | ||
429 | /* | 402 | /* |
430 | * Small blocks can be transfered via PIO. | 403 | * Small blocks can be transfered via PIO. |
@@ -441,26 +414,26 @@ static int mxs_spi_transfer_one(struct spi_master *master, | |||
441 | STMP_OFFSET_REG_CLR); | 414 | STMP_OFFSET_REG_CLR); |
442 | 415 | ||
443 | if (t->tx_buf) | 416 | if (t->tx_buf) |
444 | status = mxs_spi_txrx_pio(spi, cs, | 417 | status = mxs_spi_txrx_pio(spi, |
445 | (void *)t->tx_buf, | 418 | (void *)t->tx_buf, |
446 | t->len, &first, &last, 1); | 419 | t->len, flag | TXRX_WRITE); |
447 | if (t->rx_buf) | 420 | if (t->rx_buf) |
448 | status = mxs_spi_txrx_pio(spi, cs, | 421 | status = mxs_spi_txrx_pio(spi, |
449 | t->rx_buf, t->len, | 422 | t->rx_buf, t->len, |
450 | &first, &last, 0); | 423 | flag); |
451 | } else { | 424 | } else { |
452 | writel(BM_SSP_CTRL1_DMA_ENABLE, | 425 | writel(BM_SSP_CTRL1_DMA_ENABLE, |
453 | ssp->base + HW_SSP_CTRL1(ssp) + | 426 | ssp->base + HW_SSP_CTRL1(ssp) + |
454 | STMP_OFFSET_REG_SET); | 427 | STMP_OFFSET_REG_SET); |
455 | 428 | ||
456 | if (t->tx_buf) | 429 | if (t->tx_buf) |
457 | status = mxs_spi_txrx_dma(spi, cs, | 430 | status = mxs_spi_txrx_dma(spi, |
458 | (void *)t->tx_buf, t->len, | 431 | (void *)t->tx_buf, t->len, |
459 | &first, &last, 1); | 432 | flag | TXRX_WRITE); |
460 | if (t->rx_buf) | 433 | if (t->rx_buf) |
461 | status = mxs_spi_txrx_dma(spi, cs, | 434 | status = mxs_spi_txrx_dma(spi, |
462 | t->rx_buf, t->len, | 435 | t->rx_buf, t->len, |
463 | &first, &last, 0); | 436 | flag); |
464 | } | 437 | } |
465 | 438 | ||
466 | if (status) { | 439 | if (status) { |
@@ -469,7 +442,6 @@ static int mxs_spi_transfer_one(struct spi_master *master, | |||
469 | } | 442 | } |
470 | 443 | ||
471 | m->actual_length += t->len; | 444 | m->actual_length += t->len; |
472 | first = last = 0; | ||
473 | } | 445 | } |
474 | 446 | ||
475 | m->status = status; | 447 | m->status = status; |
@@ -563,7 +535,6 @@ static int mxs_spi_probe(struct platform_device *pdev) | |||
563 | goto out_dma_release; | 535 | goto out_dma_release; |
564 | 536 | ||
565 | clk_set_rate(ssp->clk, clk_freq); | 537 | clk_set_rate(ssp->clk, clk_freq); |
566 | ssp->clk_rate = clk_get_rate(ssp->clk) / 1000; | ||
567 | 538 | ||
568 | ret = stmp_reset_block(ssp->base); | 539 | ret = stmp_reset_block(ssp->base); |
569 | if (ret) | 540 | if (ret) |