diff options
Diffstat (limited to 'drivers/mmc/host/au1xmmc.c')
-rw-r--r-- | drivers/mmc/host/au1xmmc.c | 233 |
1 files changed, 141 insertions, 92 deletions
diff --git a/drivers/mmc/host/au1xmmc.c b/drivers/mmc/host/au1xmmc.c index 16b5640d826e..fcbaf40e3553 100644 --- a/drivers/mmc/host/au1xmmc.c +++ b/drivers/mmc/host/au1xmmc.c | |||
@@ -49,20 +49,104 @@ | |||
49 | #include <asm/mach-au1x00/au1xxx_dbdma.h> | 49 | #include <asm/mach-au1x00/au1xxx_dbdma.h> |
50 | #include <asm/mach-au1x00/au1100_mmc.h> | 50 | #include <asm/mach-au1x00/au1100_mmc.h> |
51 | 51 | ||
52 | #include <au1xxx.h> | ||
53 | #include "au1xmmc.h" | ||
54 | |||
55 | #define DRIVER_NAME "au1xxx-mmc" | 52 | #define DRIVER_NAME "au1xxx-mmc" |
56 | 53 | ||
57 | /* Set this to enable special debugging macros */ | 54 | /* Set this to enable special debugging macros */ |
58 | /* #define DEBUG */ | 55 | /* #define DEBUG */ |
59 | 56 | ||
60 | #ifdef DEBUG | 57 | #ifdef DEBUG |
61 | #define DBG(fmt, idx, args...) printk("au1xx(%d): DEBUG: " fmt, idx, ##args) | 58 | #define DBG(fmt, idx, args...) \ |
59 | printk(KERN_DEBUG "au1xmmc(%d): DEBUG: " fmt, idx, ##args) | ||
62 | #else | 60 | #else |
63 | #define DBG(fmt, idx, args...) | 61 | #define DBG(fmt, idx, args...) do {} while (0) |
64 | #endif | 62 | #endif |
65 | 63 | ||
64 | /* Hardware definitions */ | ||
65 | #define AU1XMMC_DESCRIPTOR_COUNT 1 | ||
66 | #define AU1XMMC_DESCRIPTOR_SIZE 2048 | ||
67 | |||
68 | #define AU1XMMC_OCR (MMC_VDD_27_28 | MMC_VDD_28_29 | MMC_VDD_29_30 | \ | ||
69 | MMC_VDD_30_31 | MMC_VDD_31_32 | MMC_VDD_32_33 | \ | ||
70 | MMC_VDD_33_34 | MMC_VDD_34_35 | MMC_VDD_35_36) | ||
71 | |||
72 | /* This gives us a hard value for the stop command that we can write directly | ||
73 | * to the command register. | ||
74 | */ | ||
75 | #define STOP_CMD \ | ||
76 | (SD_CMD_RT_1B | SD_CMD_CT_7 | (0xC << SD_CMD_CI_SHIFT) | SD_CMD_GO) | ||
77 | |||
78 | /* This is the set of interrupts that we configure by default. */ | ||
79 | #define AU1XMMC_INTERRUPTS \ | ||
80 | (SD_CONFIG_SC | SD_CONFIG_DT | SD_CONFIG_RAT | \ | ||
81 | SD_CONFIG_CR | SD_CONFIG_I) | ||
82 | |||
83 | /* The poll event (looking for insert/remove events runs twice a second. */ | ||
84 | #define AU1XMMC_DETECT_TIMEOUT (HZ/2) | ||
85 | |||
86 | struct au1xmmc_host { | ||
87 | struct mmc_host *mmc; | ||
88 | struct mmc_request *mrq; | ||
89 | |||
90 | u32 flags; | ||
91 | u32 iobase; | ||
92 | u32 clock; | ||
93 | u32 bus_width; | ||
94 | u32 power_mode; | ||
95 | |||
96 | int status; | ||
97 | |||
98 | struct { | ||
99 | int len; | ||
100 | int dir; | ||
101 | } dma; | ||
102 | |||
103 | struct { | ||
104 | int index; | ||
105 | int offset; | ||
106 | int len; | ||
107 | } pio; | ||
108 | |||
109 | u32 tx_chan; | ||
110 | u32 rx_chan; | ||
111 | |||
112 | int irq; | ||
113 | |||
114 | struct timer_list timer; | ||
115 | struct tasklet_struct finish_task; | ||
116 | struct tasklet_struct data_task; | ||
117 | struct au1xmmc_platform_data *platdata; | ||
118 | struct platform_device *pdev; | ||
119 | struct resource *ioarea; | ||
120 | }; | ||
121 | |||
122 | /* Status flags used by the host structure */ | ||
123 | #define HOST_F_XMIT 0x0001 | ||
124 | #define HOST_F_RECV 0x0002 | ||
125 | #define HOST_F_DMA 0x0010 | ||
126 | #define HOST_F_ACTIVE 0x0100 | ||
127 | #define HOST_F_STOP 0x1000 | ||
128 | |||
129 | #define HOST_S_IDLE 0x0001 | ||
130 | #define HOST_S_CMD 0x0002 | ||
131 | #define HOST_S_DATA 0x0003 | ||
132 | #define HOST_S_STOP 0x0004 | ||
133 | |||
134 | /* Easy access macros */ | ||
135 | #define HOST_STATUS(h) ((h)->iobase + SD_STATUS) | ||
136 | #define HOST_CONFIG(h) ((h)->iobase + SD_CONFIG) | ||
137 | #define HOST_ENABLE(h) ((h)->iobase + SD_ENABLE) | ||
138 | #define HOST_TXPORT(h) ((h)->iobase + SD_TXPORT) | ||
139 | #define HOST_RXPORT(h) ((h)->iobase + SD_RXPORT) | ||
140 | #define HOST_CMDARG(h) ((h)->iobase + SD_CMDARG) | ||
141 | #define HOST_BLKSIZE(h) ((h)->iobase + SD_BLKSIZE) | ||
142 | #define HOST_CMD(h) ((h)->iobase + SD_CMD) | ||
143 | #define HOST_CONFIG2(h) ((h)->iobase + SD_CONFIG2) | ||
144 | #define HOST_TIMEOUT(h) ((h)->iobase + SD_TIMEOUT) | ||
145 | #define HOST_DEBUG(h) ((h)->iobase + SD_DEBUG) | ||
146 | |||
147 | #define DMA_CHANNEL(h) \ | ||
148 | (((h)->flags & HOST_F_XMIT) ? (h)->tx_chan : (h)->rx_chan) | ||
149 | |||
66 | static inline void IRQ_ON(struct au1xmmc_host *host, u32 mask) | 150 | static inline void IRQ_ON(struct au1xmmc_host *host, u32 mask) |
67 | { | 151 | { |
68 | u32 val = au_readl(HOST_CONFIG(host)); | 152 | u32 val = au_readl(HOST_CONFIG(host)); |
@@ -141,7 +225,6 @@ static int au1xmmc_card_readonly(struct mmc_host *mmc) | |||
141 | 225 | ||
142 | static void au1xmmc_finish_request(struct au1xmmc_host *host) | 226 | static void au1xmmc_finish_request(struct au1xmmc_host *host) |
143 | { | 227 | { |
144 | |||
145 | struct mmc_request *mrq = host->mrq; | 228 | struct mmc_request *mrq = host->mrq; |
146 | 229 | ||
147 | host->mrq = NULL; | 230 | host->mrq = NULL; |
@@ -215,18 +298,14 @@ static int au1xmmc_send_command(struct au1xmmc_host *host, int wait, | |||
215 | au_sync(); | 298 | au_sync(); |
216 | 299 | ||
217 | /* Wait for the command to go on the line */ | 300 | /* Wait for the command to go on the line */ |
218 | 301 | while (au_readl(HOST_CMD(host)) & SD_CMD_GO) | |
219 | while(1) { | 302 | /* nop */; |
220 | if (!(au_readl(HOST_CMD(host)) & SD_CMD_GO)) | ||
221 | break; | ||
222 | } | ||
223 | 303 | ||
224 | /* Wait for the command to come back */ | 304 | /* Wait for the command to come back */ |
225 | |||
226 | if (wait) { | 305 | if (wait) { |
227 | u32 status = au_readl(HOST_STATUS(host)); | 306 | u32 status = au_readl(HOST_STATUS(host)); |
228 | 307 | ||
229 | while(!(status & SD_STATUS_CR)) | 308 | while (!(status & SD_STATUS_CR)) |
230 | status = au_readl(HOST_STATUS(host)); | 309 | status = au_readl(HOST_STATUS(host)); |
231 | 310 | ||
232 | /* Clear the CR status */ | 311 | /* Clear the CR status */ |
@@ -240,12 +319,11 @@ static int au1xmmc_send_command(struct au1xmmc_host *host, int wait, | |||
240 | 319 | ||
241 | static void au1xmmc_data_complete(struct au1xmmc_host *host, u32 status) | 320 | static void au1xmmc_data_complete(struct au1xmmc_host *host, u32 status) |
242 | { | 321 | { |
243 | |||
244 | struct mmc_request *mrq = host->mrq; | 322 | struct mmc_request *mrq = host->mrq; |
245 | struct mmc_data *data; | 323 | struct mmc_data *data; |
246 | u32 crc; | 324 | u32 crc; |
247 | 325 | ||
248 | WARN_ON(host->status != HOST_S_DATA && host->status != HOST_S_STOP); | 326 | WARN_ON((host->status != HOST_S_DATA) && (host->status != HOST_S_STOP)); |
249 | 327 | ||
250 | if (host->mrq == NULL) | 328 | if (host->mrq == NULL) |
251 | return; | 329 | return; |
@@ -256,15 +334,13 @@ static void au1xmmc_data_complete(struct au1xmmc_host *host, u32 status) | |||
256 | status = au_readl(HOST_STATUS(host)); | 334 | status = au_readl(HOST_STATUS(host)); |
257 | 335 | ||
258 | /* The transaction is really over when the SD_STATUS_DB bit is clear */ | 336 | /* The transaction is really over when the SD_STATUS_DB bit is clear */ |
259 | 337 | while ((host->flags & HOST_F_XMIT) && (status & SD_STATUS_DB)) | |
260 | while((host->flags & HOST_F_XMIT) && (status & SD_STATUS_DB)) | ||
261 | status = au_readl(HOST_STATUS(host)); | 338 | status = au_readl(HOST_STATUS(host)); |
262 | 339 | ||
263 | data->error = 0; | 340 | data->error = 0; |
264 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, data->sg_len, host->dma.dir); | 341 | dma_unmap_sg(mmc_dev(host->mmc), data->sg, data->sg_len, host->dma.dir); |
265 | 342 | ||
266 | /* Process any errors */ | 343 | /* Process any errors */ |
267 | |||
268 | crc = (status & (SD_STATUS_WC | SD_STATUS_RC)); | 344 | crc = (status & (SD_STATUS_WC | SD_STATUS_RC)); |
269 | if (host->flags & HOST_F_XMIT) | 345 | if (host->flags & HOST_F_XMIT) |
270 | crc |= ((status & 0x07) == 0x02) ? 0 : 1; | 346 | crc |= ((status & 0x07) == 0x02) ? 0 : 1; |
@@ -282,15 +358,13 @@ static void au1xmmc_data_complete(struct au1xmmc_host *host, u32 status) | |||
282 | #ifdef CONFIG_SOC_AU1200 /* DBDMA */ | 358 | #ifdef CONFIG_SOC_AU1200 /* DBDMA */ |
283 | u32 chan = DMA_CHANNEL(host); | 359 | u32 chan = DMA_CHANNEL(host); |
284 | 360 | ||
285 | chan_tab_t *c = *((chan_tab_t **) chan); | 361 | chan_tab_t *c = *((chan_tab_t **)chan); |
286 | au1x_dma_chan_t *cp = c->chan_ptr; | 362 | au1x_dma_chan_t *cp = c->chan_ptr; |
287 | data->bytes_xfered = cp->ddma_bytecnt; | 363 | data->bytes_xfered = cp->ddma_bytecnt; |
288 | #endif | 364 | #endif |
289 | } | 365 | } else |
290 | else | ||
291 | data->bytes_xfered = | 366 | data->bytes_xfered = |
292 | (data->blocks * data->blksz) - | 367 | (data->blocks * data->blksz) - host->pio.len; |
293 | host->pio.len; | ||
294 | } | 368 | } |
295 | 369 | ||
296 | au1xmmc_finish_request(host); | 370 | au1xmmc_finish_request(host); |
@@ -298,7 +372,7 @@ static void au1xmmc_data_complete(struct au1xmmc_host *host, u32 status) | |||
298 | 372 | ||
299 | static void au1xmmc_tasklet_data(unsigned long param) | 373 | static void au1xmmc_tasklet_data(unsigned long param) |
300 | { | 374 | { |
301 | struct au1xmmc_host *host = (struct au1xmmc_host *) param; | 375 | struct au1xmmc_host *host = (struct au1xmmc_host *)param; |
302 | 376 | ||
303 | u32 status = au_readl(HOST_STATUS(host)); | 377 | u32 status = au_readl(HOST_STATUS(host)); |
304 | au1xmmc_data_complete(host, status); | 378 | au1xmmc_data_complete(host, status); |
@@ -308,11 +382,10 @@ static void au1xmmc_tasklet_data(unsigned long param) | |||
308 | 382 | ||
309 | static void au1xmmc_send_pio(struct au1xmmc_host *host) | 383 | static void au1xmmc_send_pio(struct au1xmmc_host *host) |
310 | { | 384 | { |
311 | 385 | struct mmc_data *data; | |
312 | struct mmc_data *data = 0; | 386 | int sg_len, max, count; |
313 | int sg_len, max, count = 0; | 387 | unsigned char *sg_ptr, val; |
314 | unsigned char *sg_ptr; | 388 | u32 status; |
315 | u32 status = 0; | ||
316 | struct scatterlist *sg; | 389 | struct scatterlist *sg; |
317 | 390 | ||
318 | data = host->mrq->data; | 391 | data = host->mrq->data; |
@@ -327,14 +400,12 @@ static void au1xmmc_send_pio(struct au1xmmc_host *host) | |||
327 | /* This is the space left inside the buffer */ | 400 | /* This is the space left inside the buffer */ |
328 | sg_len = data->sg[host->pio.index].length - host->pio.offset; | 401 | sg_len = data->sg[host->pio.index].length - host->pio.offset; |
329 | 402 | ||
330 | /* Check to if we need less then the size of the sg_buffer */ | 403 | /* Check if we need less than the size of the sg_buffer */ |
331 | |||
332 | max = (sg_len > host->pio.len) ? host->pio.len : sg_len; | 404 | max = (sg_len > host->pio.len) ? host->pio.len : sg_len; |
333 | if (max > AU1XMMC_MAX_TRANSFER) max = AU1XMMC_MAX_TRANSFER; | 405 | if (max > AU1XMMC_MAX_TRANSFER) |
334 | 406 | max = AU1XMMC_MAX_TRANSFER; | |
335 | for(count = 0; count < max; count++ ) { | ||
336 | unsigned char val; | ||
337 | 407 | ||
408 | for (count = 0; count < max; count++) { | ||
338 | status = au_readl(HOST_STATUS(host)); | 409 | status = au_readl(HOST_STATUS(host)); |
339 | 410 | ||
340 | if (!(status & SD_STATUS_TH)) | 411 | if (!(status & SD_STATUS_TH)) |
@@ -342,7 +413,7 @@ static void au1xmmc_send_pio(struct au1xmmc_host *host) | |||
342 | 413 | ||
343 | val = *sg_ptr++; | 414 | val = *sg_ptr++; |
344 | 415 | ||
345 | au_writel((unsigned long) val, HOST_TXPORT(host)); | 416 | au_writel((unsigned long)val, HOST_TXPORT(host)); |
346 | au_sync(); | 417 | au_sync(); |
347 | } | 418 | } |
348 | 419 | ||
@@ -366,11 +437,10 @@ static void au1xmmc_send_pio(struct au1xmmc_host *host) | |||
366 | 437 | ||
367 | static void au1xmmc_receive_pio(struct au1xmmc_host *host) | 438 | static void au1xmmc_receive_pio(struct au1xmmc_host *host) |
368 | { | 439 | { |
369 | 440 | struct mmc_data *data; | |
370 | struct mmc_data *data = 0; | 441 | int max, count, sg_len = 0; |
371 | int sg_len = 0, max = 0, count = 0; | 442 | unsigned char *sg_ptr = NULL; |
372 | unsigned char *sg_ptr = 0; | 443 | u32 status, val; |
373 | u32 status = 0; | ||
374 | struct scatterlist *sg; | 444 | struct scatterlist *sg; |
375 | 445 | ||
376 | data = host->mrq->data; | 446 | data = host->mrq->data; |
@@ -387,15 +457,15 @@ static void au1xmmc_receive_pio(struct au1xmmc_host *host) | |||
387 | /* This is the space left inside the buffer */ | 457 | /* This is the space left inside the buffer */ |
388 | sg_len = sg_dma_len(&data->sg[host->pio.index]) - host->pio.offset; | 458 | sg_len = sg_dma_len(&data->sg[host->pio.index]) - host->pio.offset; |
389 | 459 | ||
390 | /* Check to if we need less then the size of the sg_buffer */ | 460 | /* Check if we need less than the size of the sg_buffer */ |
391 | if (sg_len < max) max = sg_len; | 461 | if (sg_len < max) |
462 | max = sg_len; | ||
392 | } | 463 | } |
393 | 464 | ||
394 | if (max > AU1XMMC_MAX_TRANSFER) | 465 | if (max > AU1XMMC_MAX_TRANSFER) |
395 | max = AU1XMMC_MAX_TRANSFER; | 466 | max = AU1XMMC_MAX_TRANSFER; |
396 | 467 | ||
397 | for(count = 0; count < max; count++ ) { | 468 | for (count = 0; count < max; count++) { |
398 | u32 val; | ||
399 | status = au_readl(HOST_STATUS(host)); | 469 | status = au_readl(HOST_STATUS(host)); |
400 | 470 | ||
401 | if (!(status & SD_STATUS_NE)) | 471 | if (!(status & SD_STATUS_NE)) |
@@ -421,7 +491,7 @@ static void au1xmmc_receive_pio(struct au1xmmc_host *host) | |||
421 | val = au_readl(HOST_RXPORT(host)); | 491 | val = au_readl(HOST_RXPORT(host)); |
422 | 492 | ||
423 | if (sg_ptr) | 493 | if (sg_ptr) |
424 | *sg_ptr++ = (unsigned char) (val & 0xFF); | 494 | *sg_ptr++ = (unsigned char)(val & 0xFF); |
425 | } | 495 | } |
426 | 496 | ||
427 | host->pio.len -= count; | 497 | host->pio.len -= count; |
@@ -433,7 +503,7 @@ static void au1xmmc_receive_pio(struct au1xmmc_host *host) | |||
433 | } | 503 | } |
434 | 504 | ||
435 | if (host->pio.len == 0) { | 505 | if (host->pio.len == 0) { |
436 | //IRQ_OFF(host, SD_CONFIG_RA | SD_CONFIG_RF); | 506 | /* IRQ_OFF(host, SD_CONFIG_RA | SD_CONFIG_RF); */ |
437 | IRQ_OFF(host, SD_CONFIG_NE); | 507 | IRQ_OFF(host, SD_CONFIG_NE); |
438 | 508 | ||
439 | if (host->flags & HOST_F_STOP) | 509 | if (host->flags & HOST_F_STOP) |
@@ -443,17 +513,15 @@ static void au1xmmc_receive_pio(struct au1xmmc_host *host) | |||
443 | } | 513 | } |
444 | } | 514 | } |
445 | 515 | ||
446 | /* static void au1xmmc_cmd_complete | 516 | /* This is called when a command has been completed - grab the response |
447 | This is called when a command has been completed - grab the response | 517 | * and check for errors. Then start the data transfer if it is indicated. |
448 | and check for errors. Then start the data transfer if it is indicated. | 518 | */ |
449 | */ | ||
450 | |||
451 | static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) | 519 | static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) |
452 | { | 520 | { |
453 | |||
454 | struct mmc_request *mrq = host->mrq; | 521 | struct mmc_request *mrq = host->mrq; |
455 | struct mmc_command *cmd; | 522 | struct mmc_command *cmd; |
456 | int trans; | 523 | u32 r[4]; |
524 | int i, trans; | ||
457 | 525 | ||
458 | if (!host->mrq) | 526 | if (!host->mrq) |
459 | return; | 527 | return; |
@@ -463,9 +531,6 @@ static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) | |||
463 | 531 | ||
464 | if (cmd->flags & MMC_RSP_PRESENT) { | 532 | if (cmd->flags & MMC_RSP_PRESENT) { |
465 | if (cmd->flags & MMC_RSP_136) { | 533 | if (cmd->flags & MMC_RSP_136) { |
466 | u32 r[4]; | ||
467 | int i; | ||
468 | |||
469 | r[0] = au_readl(host->iobase + SD_RESP3); | 534 | r[0] = au_readl(host->iobase + SD_RESP3); |
470 | r[1] = au_readl(host->iobase + SD_RESP2); | 535 | r[1] = au_readl(host->iobase + SD_RESP2); |
471 | r[2] = au_readl(host->iobase + SD_RESP1); | 536 | r[2] = au_readl(host->iobase + SD_RESP1); |
@@ -473,10 +538,9 @@ static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) | |||
473 | 538 | ||
474 | /* The CRC is omitted from the response, so really | 539 | /* The CRC is omitted from the response, so really |
475 | * we only got 120 bytes, but the engine expects | 540 | * we only got 120 bytes, but the engine expects |
476 | * 128 bits, so we have to shift things up | 541 | * 128 bits, so we have to shift things up. |
477 | */ | 542 | */ |
478 | 543 | for (i = 0; i < 4; i++) { | |
479 | for(i = 0; i < 4; i++) { | ||
480 | cmd->resp[i] = (r[i] & 0x00FFFFFF) << 8; | 544 | cmd->resp[i] = (r[i] & 0x00FFFFFF) << 8; |
481 | if (i != 3) | 545 | if (i != 3) |
482 | cmd->resp[i] |= (r[i + 1] & 0xFF000000) >> 24; | 546 | cmd->resp[i] |= (r[i + 1] & 0xFF000000) >> 24; |
@@ -487,22 +551,20 @@ static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) | |||
487 | * our response omits the CRC, our data ends up | 551 | * our response omits the CRC, our data ends up |
488 | * being shifted 8 bits to the right. In this case, | 552 | * being shifted 8 bits to the right. In this case, |
489 | * that means that the OSR data starts at bit 31, | 553 | * that means that the OSR data starts at bit 31, |
490 | * so we can just read RESP0 and return that | 554 | * so we can just read RESP0 and return that. |
491 | */ | 555 | */ |
492 | cmd->resp[0] = au_readl(host->iobase + SD_RESP0); | 556 | cmd->resp[0] = au_readl(host->iobase + SD_RESP0); |
493 | } | 557 | } |
494 | } | 558 | } |
495 | 559 | ||
496 | /* Figure out errors */ | 560 | /* Figure out errors */ |
497 | |||
498 | if (status & (SD_STATUS_SC | SD_STATUS_WC | SD_STATUS_RC)) | 561 | if (status & (SD_STATUS_SC | SD_STATUS_WC | SD_STATUS_RC)) |
499 | cmd->error = -EILSEQ; | 562 | cmd->error = -EILSEQ; |
500 | 563 | ||
501 | trans = host->flags & (HOST_F_XMIT | HOST_F_RECV); | 564 | trans = host->flags & (HOST_F_XMIT | HOST_F_RECV); |
502 | 565 | ||
503 | if (!trans || cmd->error) { | 566 | if (!trans || cmd->error) { |
504 | 567 | IRQ_OFF(host, SD_CONFIG_TH | SD_CONFIG_RA | SD_CONFIG_RF); | |
505 | IRQ_OFF(host, SD_CONFIG_TH | SD_CONFIG_RA|SD_CONFIG_RF); | ||
506 | tasklet_schedule(&host->finish_task); | 568 | tasklet_schedule(&host->finish_task); |
507 | return; | 569 | return; |
508 | } | 570 | } |
@@ -529,18 +591,15 @@ static void au1xmmc_cmd_complete(struct au1xmmc_host *host, u32 status) | |||
529 | 591 | ||
530 | static void au1xmmc_set_clock(struct au1xmmc_host *host, int rate) | 592 | static void au1xmmc_set_clock(struct au1xmmc_host *host, int rate) |
531 | { | 593 | { |
532 | |||
533 | unsigned int pbus = get_au1x00_speed(); | 594 | unsigned int pbus = get_au1x00_speed(); |
534 | unsigned int divisor; | 595 | unsigned int divisor; |
535 | u32 config; | 596 | u32 config; |
536 | 597 | ||
537 | /* From databook: | 598 | /* From databook: |
538 | divisor = ((((cpuclock / sbus_divisor) / 2) / mmcclock) / 2) - 1 | 599 | * divisor = ((((cpuclock / sbus_divisor) / 2) / mmcclock) / 2) - 1 |
539 | */ | 600 | */ |
540 | |||
541 | pbus /= ((au_readl(SYS_POWERCTRL) & 0x3) + 2); | 601 | pbus /= ((au_readl(SYS_POWERCTRL) & 0x3) + 2); |
542 | pbus /= 2; | 602 | pbus /= 2; |
543 | |||
544 | divisor = ((pbus / rate) / 2) - 1; | 603 | divisor = ((pbus / rate) / 2) - 1; |
545 | 604 | ||
546 | config = au_readl(HOST_CONFIG(host)); | 605 | config = au_readl(HOST_CONFIG(host)); |
@@ -552,8 +611,8 @@ static void au1xmmc_set_clock(struct au1xmmc_host *host, int rate) | |||
552 | au_sync(); | 611 | au_sync(); |
553 | } | 612 | } |
554 | 613 | ||
555 | static int | 614 | static int au1xmmc_prepare_data(struct au1xmmc_host *host, |
556 | au1xmmc_prepare_data(struct au1xmmc_host *host, struct mmc_data *data) | 615 | struct mmc_data *data) |
557 | { | 616 | { |
558 | int datalen = data->blocks * data->blksz; | 617 | int datalen = data->blocks * data->blksz; |
559 | 618 | ||
@@ -582,7 +641,7 @@ au1xmmc_prepare_data(struct au1xmmc_host *host, struct mmc_data *data) | |||
582 | 641 | ||
583 | au1xxx_dbdma_stop(channel); | 642 | au1xxx_dbdma_stop(channel); |
584 | 643 | ||
585 | for(i = 0; i < host->dma.len; i++) { | 644 | for (i = 0; i < host->dma.len; i++) { |
586 | u32 ret = 0, flags = DDMA_FLAGS_NOIE; | 645 | u32 ret = 0, flags = DDMA_FLAGS_NOIE; |
587 | struct scatterlist *sg = &data->sg[i]; | 646 | struct scatterlist *sg = &data->sg[i]; |
588 | int sg_len = sg->length; | 647 | int sg_len = sg->length; |
@@ -592,14 +651,12 @@ au1xmmc_prepare_data(struct au1xmmc_host *host, struct mmc_data *data) | |||
592 | if (i == host->dma.len - 1) | 651 | if (i == host->dma.len - 1) |
593 | flags = DDMA_FLAGS_IE; | 652 | flags = DDMA_FLAGS_IE; |
594 | 653 | ||
595 | if (host->flags & HOST_F_XMIT){ | 654 | if (host->flags & HOST_F_XMIT) { |
596 | ret = au1xxx_dbdma_put_source_flags(channel, | 655 | ret = au1xxx_dbdma_put_source_flags(channel, |
597 | (void *) sg_virt(sg), len, flags); | 656 | (void *)sg_virt(sg), len, flags); |
598 | } | 657 | } else { |
599 | else { | 658 | ret = au1xxx_dbdma_put_dest_flags(channel, |
600 | ret = au1xxx_dbdma_put_dest_flags(channel, | 659 | (void *)sg_virt(sg), len, flags); |
601 | (void *) sg_virt(sg), | ||
602 | len, flags); | ||
603 | } | 660 | } |
604 | 661 | ||
605 | if (!ret) | 662 | if (!ret) |
@@ -608,8 +665,7 @@ au1xmmc_prepare_data(struct au1xmmc_host *host, struct mmc_data *data) | |||
608 | datalen -= len; | 665 | datalen -= len; |
609 | } | 666 | } |
610 | #endif | 667 | #endif |
611 | } | 668 | } else { |
612 | else { | ||
613 | host->pio.index = 0; | 669 | host->pio.index = 0; |
614 | host->pio.offset = 0; | 670 | host->pio.offset = 0; |
615 | host->pio.len = datalen; | 671 | host->pio.len = datalen; |
@@ -618,7 +674,7 @@ au1xmmc_prepare_data(struct au1xmmc_host *host, struct mmc_data *data) | |||
618 | IRQ_ON(host, SD_CONFIG_TH); | 674 | IRQ_ON(host, SD_CONFIG_TH); |
619 | else | 675 | else |
620 | IRQ_ON(host, SD_CONFIG_NE); | 676 | IRQ_ON(host, SD_CONFIG_NE); |
621 | //IRQ_ON(host, SD_CONFIG_RA|SD_CONFIG_RF); | 677 | /* IRQ_ON(host, SD_CONFIG_RA | SD_CONFIG_RF); */ |
622 | } | 678 | } |
623 | 679 | ||
624 | return 0; | 680 | return 0; |
@@ -629,15 +685,10 @@ dataerr: | |||
629 | return -ETIMEDOUT; | 685 | return -ETIMEDOUT; |
630 | } | 686 | } |
631 | 687 | ||
632 | /* static void au1xmmc_request | 688 | /* This actually starts a command or data transaction */ |
633 | This actually starts a command or data transaction | ||
634 | */ | ||
635 | |||
636 | static void au1xmmc_request(struct mmc_host* mmc, struct mmc_request* mrq) | 689 | static void au1xmmc_request(struct mmc_host* mmc, struct mmc_request* mrq) |
637 | { | 690 | { |
638 | |||
639 | struct au1xmmc_host *host = mmc_priv(mmc); | 691 | struct au1xmmc_host *host = mmc_priv(mmc); |
640 | unsigned int flags = 0; | ||
641 | int ret = 0; | 692 | int ret = 0; |
642 | 693 | ||
643 | WARN_ON(irqs_disabled()); | 694 | WARN_ON(irqs_disabled()); |
@@ -648,7 +699,6 @@ static void au1xmmc_request(struct mmc_host* mmc, struct mmc_request* mrq) | |||
648 | 699 | ||
649 | if (mrq->data) { | 700 | if (mrq->data) { |
650 | FLUSH_FIFO(host); | 701 | FLUSH_FIFO(host); |
651 | flags = mrq->data->flags; | ||
652 | ret = au1xmmc_prepare_data(host, mrq->data); | 702 | ret = au1xmmc_prepare_data(host, mrq->data); |
653 | } | 703 | } |
654 | 704 | ||
@@ -663,7 +713,6 @@ static void au1xmmc_request(struct mmc_host* mmc, struct mmc_request* mrq) | |||
663 | 713 | ||
664 | static void au1xmmc_reset_controller(struct au1xmmc_host *host) | 714 | static void au1xmmc_reset_controller(struct au1xmmc_host *host) |
665 | { | 715 | { |
666 | |||
667 | /* Apply the clock */ | 716 | /* Apply the clock */ |
668 | au_writel(SD_ENABLE_CE, HOST_ENABLE(host)); | 717 | au_writel(SD_ENABLE_CE, HOST_ENABLE(host)); |
669 | au_sync_delay(1); | 718 | au_sync_delay(1); |
@@ -693,7 +742,7 @@ static void au1xmmc_reset_controller(struct au1xmmc_host *host) | |||
693 | } | 742 | } |
694 | 743 | ||
695 | 744 | ||
696 | static void au1xmmc_set_ios(struct mmc_host* mmc, struct mmc_ios* ios) | 745 | static void au1xmmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) |
697 | { | 746 | { |
698 | struct au1xmmc_host *host = mmc_priv(mmc); | 747 | struct au1xmmc_host *host = mmc_priv(mmc); |
699 | u32 config2; | 748 | u32 config2; |