2 * linux/drivers/mmc/moxasd.c - Moxa CPU SD/MMC driver
4 * Copyright (C) 2005 Moxa Tech., All Rights Reserved.
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
11 #include <linux/config.h>
12 #include <asm/arch/moxa.h>
13 #include <asm/arch/cpe_int.h>
14 #include <linux/module.h>
15 #include <linux/init.h>
16 #include <linux/ioport.h>
17 #include <linux/device.h>
18 #include <linux/delay.h>
19 #include <linux/interrupt.h>
20 #include <linux/blkdev.h>
21 #include <linux/dma-mapping.h>
22 #include <linux/mmc/host.h>
23 #include <linux/mmc/protocol.h>
28 #include <asm/sizes.h>
32 #define MSD_RETRY_COUNT 10000
33 //#define CONFIG_MMC_DEBUG
34 #ifdef CONFIG_MMC_DEBUG
35 #define DBG(x...) printk(x)
44 #ifdef MSD_SUPPORT_GET_CLOCK
47 struct mmc_request *mrq;
48 struct mmc_data *data;
50 struct scatterlist *cur_sg; /* Current SG entry */
51 unsigned int num_sg; /* Number of entries left */
52 void *mapped_sg; /* vaddr of mapped sg */
53 unsigned int offset; /* Offset into current entry */
54 unsigned int remain; /* Data left in curren entry */
55 int size; /* Total size of transfer */
57 struct tasklet_struct card_change_tasklet;
58 struct tasklet_struct fifo_run_tasklet;
61 static inline void moxasd_init_sg(struct moxasd_host* host, struct mmc_data* data)
64 * Get info. about SG list from data structure.
66 host->cur_sg = data->sg;
67 host->num_sg = data->sg_len;
70 host->remain = host->cur_sg->length;
73 static inline int moxasd_next_sg(struct moxasd_host* host)
76 * Skip to next SG entry.
84 if (host->num_sg > 0) {
86 host->remain = host->cur_sg->length;
92 static inline char *moxasd_kmap_sg(struct moxasd_host* host)
94 host->mapped_sg = kmap_atomic(host->cur_sg->page, KM_BIO_SRC_IRQ) +
96 return host->mapped_sg;
99 static inline void moxasd_check_data_crc(struct moxasd_host *host, struct mmc_data *data)
103 status = readl(&host->reg->status);
104 if ( status & MSD_DATA_CRC_OK ) {
105 writel(MSD_CLR_DATA_CRC_OK, &host->reg->clear);
107 if ( status & MSD_DATA_CRC_FAIL ) {
108 writel(MSD_CLR_DATA_CRC_FAIL, &host->reg->clear);
109 data->error = MMC_ERR_TIMEOUT;
110 DBG("moxasd_check_data_crc data CRC fail !\n");
112 if ( status & MSD_DATA_END ) {
113 writel(MSD_CLR_DATA_END, &host->reg->clear);
117 static inline int moxasd_wait_fifo_ready(struct moxasd_host *host, unsigned int flags)
122 while ( retry++ < MSD_RETRY_COUNT ) {
123 status = readl(&host->reg->status);
124 if ( status & MSD_CARD_DETECT ) { // card is removed
125 DBG("moxasd_wait_fifo_ready card is removed !\n");
128 if ( flags & MMC_DATA_WRITE ) {
129 if ( status & MSD_FIFO_URUN ) {
130 writel(MSD_CLR_FIFO_URUN, &host->reg->clear);
134 if ( status & MSD_FIFO_ORUN ) {
135 writel(MSD_CLR_FIFO_ORUN, &host->reg->clear);
139 if ( status & MSD_DATA_TIMEOUT ) {
140 writel(MSD_CLR_DATA_TIMEOUT, &host->reg->clear);
141 DBG("moxasd_wait_fifo_ready data timeout error !\n");
149 static void moxasd_do_fifo(struct moxasd_host *host, struct mmc_data *data)
154 if ( !moxasd_wait_fifo_ready(host, data->flags) ) { // FIFO fail
155 data->error = MMC_ERR_TIMEOUT;
156 host->size = data->bytes_xfered;
159 buffer = moxasd_kmap_sg(host) + host->offset;
160 if ( host->remain >= MSD_FIFO_LENB )
161 wcnt = MSD_FIFO_LENW;
163 wcnt = host->remain >> 2;
164 if ( data->flags & MMC_DATA_WRITE ) {
165 for ( i=0; i<wcnt; i++, buffer+=4 )
166 writel(*(unsigned int *)buffer, &host->reg->data_window);
168 for ( i=0; i<wcnt; i++, buffer+=4 )
169 *(unsigned int *)buffer = readl(&host->reg->data_window);
172 host->offset += wcnt;
173 host->remain -= wcnt;
174 data->bytes_xfered += wcnt;
175 kunmap_atomic(host->mapped_sg, KM_BIO_SRC_IRQ);
176 if ( host->remain <= 0 ) {
177 if ( !moxasd_next_sg(host) ) {
178 host->size = data->bytes_xfered;
179 data->error = MMC_ERR_NONE;
184 static void moxasd_request_done(struct moxasd_host *host)
186 struct mmc_request *mrq=host->mrq;
188 spin_lock_bh(&host->lock);
190 spin_unlock_bh(&host->lock);
195 mmc_request_done(host->mmc, mrq);
196 spin_unlock_bh(&host->lock);
199 static void moxasd_prepare_data(struct moxasd_host *host, struct mmc_data *data)
201 unsigned int timeout, datactrl;
205 // initialize the timeout value
206 timeout = (host->mmc->f_max/1000000) * (data->timeout_ns/1000);
207 timeout += data->timeout_clks;
208 writel(timeout, &host->reg->data_timer);
210 // initialize the data size
211 host->size = data->blocks << data->blksz_bits;
212 writel(host->size, &host->reg->data_length);
214 // initialize the data control
215 datactrl = data->blksz_bits & MSD_BLK_SIZE_MASK;
216 if ( data->flags & MMC_DATA_WRITE ) {
217 datactrl |= MSD_DATA_WRITE;
219 #ifdef MSD_SUPPORT_DMA
220 datactrl |= MSD_DMA_EN;
222 datactrl |= MSD_DATA_EN;
223 writel(datactrl, &host->reg->data_control);
224 moxasd_init_sg(host, data);
227 static void moxasd_send_command(struct moxasd_host *host, struct mmc_command *cmd)
229 unsigned int status, cmdctrl;
232 // first clear status
233 writel(MSD_CLR_RSP_TIMEOUT|MSD_CLR_RSP_CRC_OK|MSD_CLR_RSP_CRC_FAIL|MSD_CLR_CMD_SENT, &host->reg->clear);
236 writel(cmd->arg, &host->reg->argument);
239 cmdctrl = cmd->opcode & MSD_CMD_IDX_MASK;
240 if ( cmdctrl == SD_APP_SET_BUS_WIDTH ||
241 cmdctrl == SD_APP_OP_COND ||
242 cmdctrl == SD_APP_SEND_SCR ) // this is SD application specific command
243 cmdctrl |= MSD_APP_CMD;
244 if ( cmd->flags & MMC_RSP_LONG )
245 cmdctrl |= (MSD_LONG_RSP|MSD_NEED_RSP);
246 if ( cmd->flags & MMC_RSP_SHORT )
247 cmdctrl |= MSD_NEED_RSP;
248 writel(cmdctrl|MSD_CMD_EN, &host->reg->command);
251 while ( retry++ < MSD_RETRY_COUNT ) {
252 status = readl(&host->reg->status);
253 if ( status & MSD_CARD_DETECT ) {
254 DBG("moxasd_send_command error for card reomved\n");
255 cmd->error = MMC_ERR_TIMEOUT;
258 if ( cmdctrl & MSD_NEED_RSP ) {
259 if ( status & MSD_RSP_TIMEOUT ) {
260 writel(MSD_CLR_RSP_TIMEOUT, &host->reg->clear);
261 DBG("moxasd_send_command rsp timeout error !\n");
262 cmd->error = MMC_ERR_TIMEOUT;
266 if ( status & MSD_RSP_CRC_FAIL ) {
268 if ( (cmd->flags&MMC_RSP_CRC) && (status&MSD_RSP_CRC_FAIL) ) {
270 writel(MSD_CLR_RSP_CRC_FAIL, &host->reg->clear);
271 DBG("moxasd_send_command rsp CRC fail error !\n");
272 cmd->error = MMC_ERR_BADCRC;
275 if ( status & MSD_RSP_CRC_OK ) {
276 writel(MSD_CLR_RSP_CRC_OK, &host->reg->clear);
278 cmd->resp[0] = readl(&host->reg->response0);
279 cmd->resp[1] = readl(&host->reg->response1);
280 cmd->resp[2] = readl(&host->reg->response2);
281 cmd->resp[3] = readl(&host->reg->response3);
282 cmd->error = MMC_ERR_NONE;
286 if ( status & MSD_CMD_SENT ) {
287 writel(MSD_CLR_CMD_SENT, &host->reg->clear);
288 cmd->error = MMC_ERR_NONE;
293 cmd->error = MMC_ERR_TIMEOUT;
296 static irqreturn_t moxasd_irq(int irq, void *devid, struct pt_regs *regs)
298 struct moxasd_host *host=devid;
301 status = readl(&host->reg->status);
302 if ( status & MSD_CARD_CHANGE ) { // has card inserted or removed
303 tasklet_schedule(&host->card_change_tasklet);
305 if ( status & (MSD_FIFO_ORUN|MSD_FIFO_URUN) ) {
306 DBG("moxasd_irq FIFO\n");
307 tasklet_schedule(&host->fifo_run_tasklet);
313 static void card_change(unsigned long param)
315 struct moxasd_host *host=(struct moxasd_host *)param;
319 status = readl(&host->reg->status);
320 if ( status & MSD_CARD_DETECT ) { // card inserted
321 if ( host->reg->clock_control & MSD_CLK_SD ) { // SD
322 host->mmc->f_max = 25000000;
323 host->mmc->mode = MMC_MODE_SD;
325 host->mmc->f_max = 20000000;
326 host->mmc->mode = MMC_MODE_MMC;
329 } else { // card remove
334 writel(MSD_CLR_CARD_CHANGE, &host->reg->clear);
336 mmc_detect_change(host->mmc, msecs_to_jiffies(delay));
339 static void fifo_run(unsigned long param)
341 struct moxasd_host *host=(struct moxasd_host *)param;
342 struct mmc_data *data;
344 //spin_lock_bh(&host->lock);
345 if ( host->mrq == NULL ) {
346 //spin_unlock_bh(&host->lock);
349 if ( host->data == NULL ) {
353 moxasd_do_fifo(host, data);
354 if ( host->size == data->bytes_xfered ) {
355 // maybe need to check the data is OK or fail
356 if ( data->error == MMC_ERR_NONE ) {
357 moxasd_check_data_crc(host, data);
360 moxasd_send_command(host, data->stop);
362 DBG("moxasd_fifo_run finished data read/write\n");
364 tasklet_schedule(&host->fifo_run_tasklet);
365 //spin_unlock_bh(&host->lock);
370 //spin_unlock_bh(&host->lock);
371 moxasd_request_done(host);
374 static void moxasd_request(struct mmc_host *mmc, struct mmc_request *mrq)
376 struct moxasd_host *host=mmc_priv(mmc);
377 struct mmc_command *cmd;
379 spin_lock_bh(&host->lock);
383 // if no card inserted, return timeout error
384 if ( readl(&host->reg->status) & MSD_CARD_DETECT ) {
385 cmd->error = MMC_ERR_TIMEOUT;
389 // request include data or not
391 moxasd_prepare_data(host, cmd->data);
394 // do request command
395 moxasd_send_command(host, cmd);
397 if ( cmd->data && cmd->error == MMC_ERR_NONE ) {
398 //tasklet_schedule(&host->fifo_run_tasklet);
399 spin_unlock_bh(&host->lock);
404 spin_unlock_bh(&host->lock);
405 moxasd_request_done(host);
408 #define MIN_POWER (MMC_VDD_360 - MSD_SD_POWER_MASK)
409 static void moxasd_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
411 struct moxasd_host *host=mmc_priv(mmc);
413 spin_lock_bh(&host->lock);
416 #ifdef MSD_SUPPORT_GET_CLOCK
417 div = (host->sysclk / (host->mmc->f_max * 2)) - 1;
419 div = (APB_CLK / (host->mmc->f_max * 2)) - 1;
421 if ( div > MSD_CLK_DIV_MASK )
422 div = MSD_CLK_DIV_MASK;
425 if ( host->mmc->mode == MMC_MODE_SD )
427 writel(div, &host->reg->clock_control);
428 } else if ( !(readl(&host->reg->clock_control) & MSD_CLK_DIS) ) {
430 * Ensure that the clock is off.
432 writel(readl(&host->reg->clock_control)|MSD_CLK_DIS, &host->reg->clock_control);
435 if ( ios->power_mode == MMC_POWER_OFF ) {
436 writel(readl(&host->reg->power_control)&~MSD_SD_POWER_ON, &host->reg->power_control);
438 unsigned short power;
439 if ( ios->vdd < MIN_POWER )
442 power = ios->vdd - MIN_POWER;
443 writel(MSD_SD_POWER_ON|(unsigned int)power, &host->reg->power_control);
447 if ( ios->bus_width == MMC_BUS_WIDTH_1 ) {
448 writel(MSD_SINGLE_BUS, &host->reg->bus_width);
450 writel(MSD_WIDE_BUS, &host->reg->bus_width);
453 spin_unlock_bh(&host->lock);
457 * To check write protect or not. Return 0 for none, 1 for write protect.
459 static int moxasd_get_ro(struct mmc_host *mmc)
461 struct moxasd_host *host=mmc_priv(mmc);
463 if ( readl(&host->reg->status) & MSD_WRITE_PROT )
469 static struct mmc_host_ops moxasd_ops = {
470 .request = moxasd_request,
471 .set_ios = moxasd_set_ios,
472 .get_ro = moxasd_get_ro,
475 static int moxasd_probe(struct device *dev)
477 struct mmc_host *mmc;
478 struct moxasd_host *host=NULL;
481 mmc = mmc_alloc_host(sizeof(struct moxasd_host), dev);
487 mmc->ops = &moxasd_ops;
489 mmc->f_max = 25000000;
490 mmc->mode = MMC_MODE_SD;
492 mmc->ocr_avail = 0xffff00; // support 2.0v - 3.6v power
494 mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
495 mmc->caps = MMC_CAP_4_BIT_DATA;
496 mmc->max_hw_segs = 128;
497 mmc->max_phys_segs = 128;
498 mmc->max_sectors = 128;
499 mmc->max_seg_size = mmc->max_sectors * 512;
502 host = mmc_priv(mmc);
504 spin_lock_init(&host->lock);
505 tasklet_init(&host->card_change_tasklet, card_change, (unsigned long)host);
506 tasklet_init(&host->fifo_run_tasklet, fifo_run, (unsigned long)host);
507 host->reg = (moxasd_reg *)CPE_SD_BASE;
509 #ifdef MSD_SUPPORT_GET_CLOCK
512 unsigned int mul, val, div;
513 mul = (*(volatile unsigned int *)(CPE_PMU_BASE+0x30) >> 3) & 0x1ff;
514 val = (*(volatile unsigned int *)(CPE_PMU_BASE+0x0c) >> 4) & 0x7;
516 case 0 : div = 2; break;
517 case 1 : div = 3; break;
518 case 2 : div = 4; break;
519 case 3 : div = 6; break;
520 case 4 : div = 8; break;
521 default : div = 2; break;
523 host->sysclk = (38684*mul + 10000) / (div * 10000);
524 host->sysclk = (host->sysclk * 1000000) / 2;
528 // change I/O multiplexing to SD, so the GPIO 17-10 will be fail
529 *(volatile unsigned int *)(CPE_PMU_BASE+0x100) &= (~(0xff<<10));
532 * Ensure that the host controller is shut down, and setup
535 writel(0, &host->reg->interrupt_mask); // disable all interrupt
536 writel(MSD_SDC_RST, &host->reg->command); // reset chip
537 while ( readl(&host->reg->command) & MSD_SDC_RST); // wait for reset finished
538 writel(0, &host->reg->interrupt_mask); // disable all interrupt
540 // to check any card inserted or not
541 if ( !(readl(&host->reg->status) & MSD_CARD_DETECT) ) { // is inserted
542 if ( readl(&host->reg->clock_control) & MSD_CLK_SD ) { // is SD card
543 mmc->f_max = 25000000;
544 mmc->mode = MMC_MODE_SD;
545 } else { // is MMC card
546 mmc->f_max = 20000000;
547 mmc->mode = MMC_MODE_MMC;
551 mmc->caps = MMC_CAP_4_BIT_DATA;
552 writel(MSD_WIDE_BUS, &host->reg->bus_width);
554 cpe_int_set_irq(IRQ_SD, EDGE, H_ACTIVE);
555 ret = request_irq(IRQ_SD, moxasd_irq, SA_INTERRUPT, "MOXASD", host);
559 writel(MSD_INT_CARD_CHANGE|MSD_INT_FIFO_ORUN|MSD_INT_FIFO_URUN, &host->reg->interrupt_mask);
560 dev_set_drvdata(dev, mmc);
572 static int moxasd_remove(struct device *dev)
574 struct mmc_host *mmc=dev_get_drvdata(dev);
576 dev_set_drvdata(dev, NULL);
579 struct moxasd_host *host=mmc_priv(mmc);
581 mmc_remove_host(mmc);
584 writel(0, &host->reg->interrupt_mask);
585 writel(0, &host->reg->power_control);
586 writel(readl(&host->reg->clock_control)|MSD_CLK_DIS, &host->reg->clock_control);
588 free_irq(IRQ_SD, host);
589 tasklet_kill(&host->card_change_tasklet);
590 tasklet_kill(&host->fifo_run_tasklet);
597 static struct platform_device moxasd_device = {
602 static struct device_driver moxasd_driver = {
604 .bus = &platform_bus_type,
605 .probe = moxasd_probe,
606 .remove = moxasd_remove,
609 static int __init moxasd_init(void)
611 printk("Moxa CPU SD/MMC Device Driver V1.0 initialize.\n");
612 platform_device_register(&moxasd_device);
613 return driver_register(&moxasd_driver);
616 static void __exit moxasd_exit(void)
618 platform_device_unregister(&moxasd_device);
619 driver_unregister(&moxasd_driver);
622 module_init(moxasd_init);
623 module_exit(moxasd_exit);
625 MODULE_DESCRIPTION("Moxa CPU SD/Multimedia Card Interface Driver");
626 MODULE_LICENSE("GPL");