• Home
  • Raw
  • Download

Lines Matching +full:jz4780 +full:- +full:mmc

1 // SPDX-License-Identifier: GPL-2.0-or-later
3 * Copyright (C) 2009-2010, Lars-Peter Clausen <lars@metafoo.de>
6 * JZ4740 SD/MMC controller driver
13 #include <linux/dma-mapping.h>
18 #include <linux/mmc/host.h>
19 #include <linux/mmc/slot-gpio.h>
129 * The MMC core allows to prepare a mmc_request while another mmc_request
130 * is in-flight. This is used via the pre_req/post_req hooks.
148 struct mmc_host *mmc; member
189 if (host->version >= JZ_MMC_JZ4725B) in jz4740_mmc_write_irq_mask()
190 return writel(val, host->base + JZ_REG_MMC_IMASK); in jz4740_mmc_write_irq_mask()
192 return writew(val, host->base + JZ_REG_MMC_IMASK); in jz4740_mmc_write_irq_mask()
198 if (host->version >= JZ_MMC_JZ4780) in jz4740_mmc_write_irq_reg()
199 writel(val, host->base + JZ_REG_MMC_IREG); in jz4740_mmc_write_irq_reg()
201 writew(val, host->base + JZ_REG_MMC_IREG); in jz4740_mmc_write_irq_reg()
206 if (host->version >= JZ_MMC_JZ4780) in jz4740_mmc_read_irq_reg()
207 return readl(host->base + JZ_REG_MMC_IREG); in jz4740_mmc_read_irq_reg()
209 return readw(host->base + JZ_REG_MMC_IREG); in jz4740_mmc_read_irq_reg()
212 /*----------------------------------------------------------------------------*/
217 if (!host->use_dma) in jz4740_mmc_release_dma_channels()
220 dma_release_channel(host->dma_tx); in jz4740_mmc_release_dma_channels()
221 dma_release_channel(host->dma_rx); in jz4740_mmc_release_dma_channels()
226 host->dma_tx = dma_request_chan(mmc_dev(host->mmc), "tx"); in jz4740_mmc_acquire_dma_channels()
227 if (IS_ERR(host->dma_tx)) { in jz4740_mmc_acquire_dma_channels()
228 dev_err(mmc_dev(host->mmc), "Failed to get dma_tx channel\n"); in jz4740_mmc_acquire_dma_channels()
229 return PTR_ERR(host->dma_tx); in jz4740_mmc_acquire_dma_channels()
232 host->dma_rx = dma_request_chan(mmc_dev(host->mmc), "rx"); in jz4740_mmc_acquire_dma_channels()
233 if (IS_ERR(host->dma_rx)) { in jz4740_mmc_acquire_dma_channels()
234 dev_err(mmc_dev(host->mmc), "Failed to get dma_rx channel\n"); in jz4740_mmc_acquire_dma_channels()
235 dma_release_channel(host->dma_tx); in jz4740_mmc_acquire_dma_channels()
236 return PTR_ERR(host->dma_rx); in jz4740_mmc_acquire_dma_channels()
243 if (host->dma_tx) { in jz4740_mmc_acquire_dma_channels()
244 struct device *dev = host->dma_tx->device->dev; in jz4740_mmc_acquire_dma_channels()
247 if (max_seg_size < host->mmc->max_seg_size) in jz4740_mmc_acquire_dma_channels()
248 host->mmc->max_seg_size = max_seg_size; in jz4740_mmc_acquire_dma_channels()
251 if (host->dma_rx) { in jz4740_mmc_acquire_dma_channels()
252 struct device *dev = host->dma_rx->device->dev; in jz4740_mmc_acquire_dma_channels()
255 if (max_seg_size < host->mmc->max_seg_size) in jz4740_mmc_acquire_dma_channels()
256 host->mmc->max_seg_size = max_seg_size; in jz4740_mmc_acquire_dma_channels()
265 return (data->flags & MMC_DATA_READ) ? host->dma_rx : host->dma_tx; in jz4740_mmc_get_dma_chan()
274 dma_unmap_sg(chan->device->dev, data->sg, data->sg_len, dir); in jz4740_mmc_dma_unmap()
275 data->host_cookie = COOKIE_UNMAPPED; in jz4740_mmc_dma_unmap()
279 * A request can be in-flight when this is called.
289 if (data->host_cookie == COOKIE_PREMAPPED) in jz4740_mmc_prepare_dma_data()
290 return data->sg_count; in jz4740_mmc_prepare_dma_data()
292 sg_count = dma_map_sg(chan->device->dev, in jz4740_mmc_prepare_dma_data()
293 data->sg, in jz4740_mmc_prepare_dma_data()
294 data->sg_len, in jz4740_mmc_prepare_dma_data()
298 dev_err(mmc_dev(host->mmc), in jz4740_mmc_prepare_dma_data()
300 return -EINVAL; in jz4740_mmc_prepare_dma_data()
303 data->sg_count = sg_count; in jz4740_mmc_prepare_dma_data()
304 data->host_cookie = cookie; in jz4740_mmc_prepare_dma_data()
306 return data->sg_count; in jz4740_mmc_prepare_dma_data()
322 if (data->flags & MMC_DATA_WRITE) { in jz4740_mmc_start_dma_transfer()
324 conf.dst_addr = host->mem_res->start + JZ_REG_MMC_TXFIFO; in jz4740_mmc_start_dma_transfer()
327 conf.src_addr = host->mem_res->start + JZ_REG_MMC_RXFIFO; in jz4740_mmc_start_dma_transfer()
335 desc = dmaengine_prep_slave_sg(chan, data->sg, sg_count, in jz4740_mmc_start_dma_transfer()
339 dev_err(mmc_dev(host->mmc), in jz4740_mmc_start_dma_transfer()
351 if (data->host_cookie == COOKIE_MAPPED) in jz4740_mmc_start_dma_transfer()
353 return -ENOMEM; in jz4740_mmc_start_dma_transfer()
356 static void jz4740_mmc_pre_request(struct mmc_host *mmc, in jz4740_mmc_pre_request() argument
359 struct jz4740_mmc_host *host = mmc_priv(mmc); in jz4740_mmc_pre_request()
360 struct mmc_data *data = mrq->data; in jz4740_mmc_pre_request()
362 if (!host->use_dma) in jz4740_mmc_pre_request()
365 data->host_cookie = COOKIE_UNMAPPED; in jz4740_mmc_pre_request()
367 data->host_cookie = COOKIE_UNMAPPED; in jz4740_mmc_pre_request()
370 static void jz4740_mmc_post_request(struct mmc_host *mmc, in jz4740_mmc_post_request() argument
374 struct jz4740_mmc_host *host = mmc_priv(mmc); in jz4740_mmc_post_request()
375 struct mmc_data *data = mrq->data; in jz4740_mmc_post_request()
377 if (data && data->host_cookie != COOKIE_UNMAPPED) in jz4740_mmc_post_request()
387 /*----------------------------------------------------------------------------*/
394 spin_lock_irqsave(&host->lock, flags); in jz4740_mmc_set_irq_enabled()
396 host->irq_mask &= ~irq; in jz4740_mmc_set_irq_enabled()
398 host->irq_mask |= irq; in jz4740_mmc_set_irq_enabled()
400 jz4740_mmc_write_irq_mask(host, host->irq_mask); in jz4740_mmc_set_irq_enabled()
401 spin_unlock_irqrestore(&host->lock, flags); in jz4740_mmc_set_irq_enabled()
412 writew(val, host->base + JZ_REG_MMC_STRPCL); in jz4740_mmc_clock_enable()
420 writew(JZ_MMC_STRPCL_CLOCK_STOP, host->base + JZ_REG_MMC_STRPCL); in jz4740_mmc_clock_disable()
422 status = readl(host->base + JZ_REG_MMC_STATUS); in jz4740_mmc_clock_disable()
423 } while (status & JZ_MMC_STATUS_CLK_EN && --timeout); in jz4740_mmc_clock_disable()
431 writew(JZ_MMC_STRPCL_RESET, host->base + JZ_REG_MMC_STRPCL); in jz4740_mmc_reset()
434 status = readl(host->base + JZ_REG_MMC_STATUS); in jz4740_mmc_reset()
435 } while (status & JZ_MMC_STATUS_IS_RESETTING && --timeout); in jz4740_mmc_reset()
443 req = host->req; in jz4740_mmc_request_done()
444 data = req->data; in jz4740_mmc_request_done()
445 host->req = NULL; in jz4740_mmc_request_done()
447 if (data && data->host_cookie == COOKIE_MAPPED) in jz4740_mmc_request_done()
449 mmc_request_done(host->mmc, req); in jz4740_mmc_request_done()
460 } while (!(status & irq) && --timeout); in jz4740_mmc_poll_irq()
463 set_bit(0, &host->waiting); in jz4740_mmc_poll_irq()
464 mod_timer(&host->timeout_timer, in jz4740_mmc_poll_irq()
478 status = readl(host->base + JZ_REG_MMC_STATUS); in jz4740_mmc_transfer_check_state()
481 host->req->cmd->error = -ETIMEDOUT; in jz4740_mmc_transfer_check_state()
482 data->error = -ETIMEDOUT; in jz4740_mmc_transfer_check_state()
484 host->req->cmd->error = -EIO; in jz4740_mmc_transfer_check_state()
485 data->error = -EIO; in jz4740_mmc_transfer_check_state()
489 host->req->cmd->error = -ETIMEDOUT; in jz4740_mmc_transfer_check_state()
490 data->error = -ETIMEDOUT; in jz4740_mmc_transfer_check_state()
492 host->req->cmd->error = -EIO; in jz4740_mmc_transfer_check_state()
493 data->error = -EIO; in jz4740_mmc_transfer_check_state()
501 struct sg_mapping_iter *miter = &host->miter; in jz4740_mmc_write_data()
502 void __iomem *fifo_addr = host->base + JZ_REG_MMC_TXFIFO; in jz4740_mmc_write_data()
508 buf = miter->addr; in jz4740_mmc_write_data()
509 i = miter->length / 4; in jz4740_mmc_write_data()
526 --j; in jz4740_mmc_write_data()
536 --i; in jz4740_mmc_write_data()
539 data->bytes_xfered += miter->length; in jz4740_mmc_write_data()
546 miter->consumed = (void *)buf - miter->addr; in jz4740_mmc_write_data()
547 data->bytes_xfered += miter->consumed; in jz4740_mmc_write_data()
556 struct sg_mapping_iter *miter = &host->miter; in jz4740_mmc_read_data()
557 void __iomem *fifo_addr = host->base + JZ_REG_MMC_RXFIFO; in jz4740_mmc_read_data()
565 buf = miter->addr; in jz4740_mmc_read_data()
566 i = miter->length; in jz4740_mmc_read_data()
584 --j; in jz4740_mmc_read_data()
594 i -= 4; in jz4740_mmc_read_data()
601 data->bytes_xfered += miter->length; in jz4740_mmc_read_data()
605 flush_dcache_page(miter->page); in jz4740_mmc_read_data()
612 status = readl(host->base + JZ_REG_MMC_STATUS); in jz4740_mmc_read_data()
613 while (!(status & JZ_MMC_STATUS_DATA_FIFO_EMPTY) && --timeout) { in jz4740_mmc_read_data()
615 status = readl(host->base + JZ_REG_MMC_STATUS); in jz4740_mmc_read_data()
621 miter->consumed = (void *)buf - miter->addr; in jz4740_mmc_read_data()
622 data->bytes_xfered += miter->consumed; in jz4740_mmc_read_data()
632 if (!test_and_clear_bit(0, &host->waiting)) in jz4740_mmc_timeout()
637 host->req->cmd->error = -ETIMEDOUT; in jz4740_mmc_timeout()
646 void __iomem *fifo_addr = host->base + JZ_REG_MMC_RESP_FIFO; in jz4740_mmc_read_response()
648 if (cmd->flags & MMC_RSP_136) { in jz4740_mmc_read_response()
651 cmd->resp[i] = tmp << 24; in jz4740_mmc_read_response()
653 cmd->resp[i] |= tmp << 8; in jz4740_mmc_read_response()
655 cmd->resp[i] |= tmp >> 8; in jz4740_mmc_read_response()
658 cmd->resp[0] = readw(fifo_addr) << 24; in jz4740_mmc_read_response()
659 cmd->resp[0] |= readw(fifo_addr) << 8; in jz4740_mmc_read_response()
660 cmd->resp[0] |= readw(fifo_addr) & 0xff; in jz4740_mmc_read_response()
667 uint32_t cmdat = host->cmdat; in jz4740_mmc_send_command()
669 host->cmdat &= ~JZ_MMC_CMDAT_INIT; in jz4740_mmc_send_command()
672 host->cmd = cmd; in jz4740_mmc_send_command()
674 if (cmd->flags & MMC_RSP_BUSY) in jz4740_mmc_send_command()
692 if (cmd->data) { in jz4740_mmc_send_command()
694 if (cmd->data->flags & MMC_DATA_WRITE) in jz4740_mmc_send_command()
696 if (host->use_dma) { in jz4740_mmc_send_command()
698 * The 4780's MMC controller has integrated DMA ability in jz4740_mmc_send_command()
706 if (host->version >= JZ_MMC_JZ4780) { in jz4740_mmc_send_command()
708 host->base + JZ_REG_MMC_DMAC); in jz4740_mmc_send_command()
712 } else if (host->version >= JZ_MMC_JZ4780) { in jz4740_mmc_send_command()
713 writel(0, host->base + JZ_REG_MMC_DMAC); in jz4740_mmc_send_command()
716 writew(cmd->data->blksz, host->base + JZ_REG_MMC_BLKLEN); in jz4740_mmc_send_command()
717 writew(cmd->data->blocks, host->base + JZ_REG_MMC_NOB); in jz4740_mmc_send_command()
720 writeb(cmd->opcode, host->base + JZ_REG_MMC_CMD); in jz4740_mmc_send_command()
721 writel(cmd->arg, host->base + JZ_REG_MMC_ARG); in jz4740_mmc_send_command()
722 writel(cmdat, host->base + JZ_REG_MMC_CMDAT); in jz4740_mmc_send_command()
729 struct mmc_command *cmd = host->req->cmd; in jz_mmc_prepare_data_transfer()
730 struct mmc_data *data = cmd->data; in jz_mmc_prepare_data_transfer()
733 if (data->flags & MMC_DATA_READ) in jz_mmc_prepare_data_transfer()
738 sg_miter_start(&host->miter, data->sg, data->sg_len, direction); in jz_mmc_prepare_data_transfer()
745 struct mmc_command *cmd = host->req->cmd; in jz_mmc_irq_worker()
746 struct mmc_request *req = host->req; in jz_mmc_irq_worker()
747 struct mmc_data *data = cmd->data; in jz_mmc_irq_worker()
750 if (cmd->error) in jz_mmc_irq_worker()
751 host->state = JZ4740_MMC_STATE_DONE; in jz_mmc_irq_worker()
753 switch (host->state) { in jz_mmc_irq_worker()
755 if (cmd->flags & MMC_RSP_PRESENT) in jz_mmc_irq_worker()
765 if (host->use_dma) { in jz_mmc_irq_worker()
773 data->bytes_xfered = data->blocks * data->blksz; in jz_mmc_irq_worker()
774 } else if (data->flags & MMC_DATA_READ) in jz_mmc_irq_worker()
785 host->state = JZ4740_MMC_STATE_TRANSFER_DATA; in jz_mmc_irq_worker()
793 host->state = JZ4740_MMC_STATE_SEND_STOP; in jz_mmc_irq_worker()
800 if (!req->stop) in jz_mmc_irq_worker()
803 jz4740_mmc_send_command(host, req->stop); in jz_mmc_irq_worker()
805 if (mmc_resp_type(req->stop) & MMC_RSP_BUSY) { in jz_mmc_irq_worker()
809 host->state = JZ4740_MMC_STATE_DONE; in jz_mmc_irq_worker()
826 struct mmc_command *cmd = host->cmd; in jz_mmc_irq()
829 status = readl(host->base + JZ_REG_MMC_STATUS); in jz_mmc_irq()
833 irq_reg &= ~host->irq_mask; in jz_mmc_irq()
843 mmc_signal_sdio_irq(host->mmc); in jz_mmc_irq()
847 if (host->req && cmd && irq_reg) { in jz_mmc_irq()
848 if (test_and_clear_bit(0, &host->waiting)) { in jz_mmc_irq()
849 del_timer(&host->timeout_timer); in jz_mmc_irq()
852 cmd->error = -ETIMEDOUT; in jz_mmc_irq()
854 cmd->error = -EIO; in jz_mmc_irq()
857 if (cmd->data) in jz_mmc_irq()
858 cmd->data->error = -EIO; in jz_mmc_irq()
859 cmd->error = -EIO; in jz_mmc_irq()
878 clk_set_rate(host->clk, host->mmc->f_max); in jz4740_mmc_set_clock_rate()
880 real_rate = clk_get_rate(host->clk); in jz4740_mmc_set_clock_rate()
887 writew(div, host->base + JZ_REG_MMC_CLKRT); in jz4740_mmc_set_clock_rate()
890 if (host->version >= JZ_MMC_X1000) { in jz4740_mmc_set_clock_rate()
894 host->base + JZ_REG_MMC_LPM); in jz4740_mmc_set_clock_rate()
895 } else if (host->version >= JZ_MMC_JZ4760) { in jz4740_mmc_set_clock_rate()
898 host->base + JZ_REG_MMC_LPM); in jz4740_mmc_set_clock_rate()
899 } else if (host->version >= JZ_MMC_JZ4725B) in jz4740_mmc_set_clock_rate()
901 host->base + JZ_REG_MMC_LPM); in jz4740_mmc_set_clock_rate()
907 static void jz4740_mmc_request(struct mmc_host *mmc, struct mmc_request *req) in jz4740_mmc_request() argument
909 struct jz4740_mmc_host *host = mmc_priv(mmc); in jz4740_mmc_request()
911 host->req = req; in jz4740_mmc_request()
916 host->state = JZ4740_MMC_STATE_READ_RESPONSE; in jz4740_mmc_request()
917 set_bit(0, &host->waiting); in jz4740_mmc_request()
918 mod_timer(&host->timeout_timer, in jz4740_mmc_request()
920 jz4740_mmc_send_command(host, req->cmd); in jz4740_mmc_request()
923 static void jz4740_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) in jz4740_mmc_set_ios() argument
925 struct jz4740_mmc_host *host = mmc_priv(mmc); in jz4740_mmc_set_ios()
926 if (ios->clock) in jz4740_mmc_set_ios()
927 jz4740_mmc_set_clock_rate(host, ios->clock); in jz4740_mmc_set_ios()
929 switch (ios->power_mode) { in jz4740_mmc_set_ios()
932 if (!IS_ERR(mmc->supply.vmmc)) in jz4740_mmc_set_ios()
933 mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, ios->vdd); in jz4740_mmc_set_ios()
934 host->cmdat |= JZ_MMC_CMDAT_INIT; in jz4740_mmc_set_ios()
935 clk_prepare_enable(host->clk); in jz4740_mmc_set_ios()
940 if (!IS_ERR(mmc->supply.vmmc)) in jz4740_mmc_set_ios()
941 mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, 0); in jz4740_mmc_set_ios()
942 clk_disable_unprepare(host->clk); in jz4740_mmc_set_ios()
946 switch (ios->bus_width) { in jz4740_mmc_set_ios()
948 host->cmdat &= ~JZ_MMC_CMDAT_BUS_WIDTH_MASK; in jz4740_mmc_set_ios()
951 host->cmdat &= ~JZ_MMC_CMDAT_BUS_WIDTH_MASK; in jz4740_mmc_set_ios()
952 host->cmdat |= JZ_MMC_CMDAT_BUS_WIDTH_4BIT; in jz4740_mmc_set_ios()
955 host->cmdat &= ~JZ_MMC_CMDAT_BUS_WIDTH_MASK; in jz4740_mmc_set_ios()
956 host->cmdat |= JZ_MMC_CMDAT_BUS_WIDTH_8BIT; in jz4740_mmc_set_ios()
963 static void jz4740_mmc_enable_sdio_irq(struct mmc_host *mmc, int enable) in jz4740_mmc_enable_sdio_irq() argument
965 struct jz4740_mmc_host *host = mmc_priv(mmc); in jz4740_mmc_enable_sdio_irq()
980 { .compatible = "ingenic,jz4740-mmc", .data = (void *) JZ_MMC_JZ4740 },
981 { .compatible = "ingenic,jz4725b-mmc", .data = (void *)JZ_MMC_JZ4725B },
982 { .compatible = "ingenic,jz4760-mmc", .data = (void *) JZ_MMC_JZ4760 },
983 { .compatible = "ingenic,jz4780-mmc", .data = (void *) JZ_MMC_JZ4780 },
984 { .compatible = "ingenic,x1000-mmc", .data = (void *) JZ_MMC_X1000 },
992 struct mmc_host *mmc; in jz4740_mmc_probe() local
996 mmc = mmc_alloc_host(sizeof(struct jz4740_mmc_host), &pdev->dev); in jz4740_mmc_probe()
997 if (!mmc) { in jz4740_mmc_probe()
998 dev_err(&pdev->dev, "Failed to alloc mmc host structure\n"); in jz4740_mmc_probe()
999 return -ENOMEM; in jz4740_mmc_probe()
1002 host = mmc_priv(mmc); in jz4740_mmc_probe()
1004 match = of_match_device(jz4740_mmc_of_match, &pdev->dev); in jz4740_mmc_probe()
1006 host->version = (enum jz4740_mmc_version)match->data; in jz4740_mmc_probe()
1009 host->version = JZ_MMC_JZ4740; in jz4740_mmc_probe()
1012 ret = mmc_of_parse(mmc); in jz4740_mmc_probe()
1014 dev_err_probe(&pdev->dev, ret, "could not parse device properties\n"); in jz4740_mmc_probe()
1018 mmc_regulator_get_supply(mmc); in jz4740_mmc_probe()
1020 host->irq = platform_get_irq(pdev, 0); in jz4740_mmc_probe()
1021 if (host->irq < 0) { in jz4740_mmc_probe()
1022 ret = host->irq; in jz4740_mmc_probe()
1026 host->clk = devm_clk_get(&pdev->dev, "mmc"); in jz4740_mmc_probe()
1027 if (IS_ERR(host->clk)) { in jz4740_mmc_probe()
1028 ret = PTR_ERR(host->clk); in jz4740_mmc_probe()
1029 dev_err(&pdev->dev, "Failed to get mmc clock\n"); in jz4740_mmc_probe()
1033 host->mem_res = platform_get_resource(pdev, IORESOURCE_MEM, 0); in jz4740_mmc_probe()
1034 host->base = devm_ioremap_resource(&pdev->dev, host->mem_res); in jz4740_mmc_probe()
1035 if (IS_ERR(host->base)) { in jz4740_mmc_probe()
1036 ret = PTR_ERR(host->base); in jz4740_mmc_probe()
1037 dev_err(&pdev->dev, "Failed to ioremap base memory\n"); in jz4740_mmc_probe()
1041 mmc->ops = &jz4740_mmc_ops; in jz4740_mmc_probe()
1042 if (!mmc->f_max) in jz4740_mmc_probe()
1043 mmc->f_max = JZ_MMC_CLK_RATE; in jz4740_mmc_probe()
1051 if (host->version == JZ_MMC_JZ4760 && mmc->f_max > JZ_MMC_CLK_RATE) in jz4740_mmc_probe()
1052 mmc->f_max = JZ_MMC_CLK_RATE; in jz4740_mmc_probe()
1054 mmc->f_min = mmc->f_max / 128; in jz4740_mmc_probe()
1055 mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34; in jz4740_mmc_probe()
1059 * future improvement should instead respect the cmd->busy_timeout. in jz4740_mmc_probe()
1061 mmc->max_busy_timeout = JZ_MMC_REQ_TIMEOUT_MS; in jz4740_mmc_probe()
1063 mmc->max_blk_size = (1 << 10) - 1; in jz4740_mmc_probe()
1064 mmc->max_blk_count = (1 << 15) - 1; in jz4740_mmc_probe()
1065 mmc->max_req_size = mmc->max_blk_size * mmc->max_blk_count; in jz4740_mmc_probe()
1067 mmc->max_segs = 128; in jz4740_mmc_probe()
1068 mmc->max_seg_size = mmc->max_req_size; in jz4740_mmc_probe()
1070 host->mmc = mmc; in jz4740_mmc_probe()
1071 host->pdev = pdev; in jz4740_mmc_probe()
1072 spin_lock_init(&host->lock); in jz4740_mmc_probe()
1073 host->irq_mask = ~0; in jz4740_mmc_probe()
1077 ret = request_threaded_irq(host->irq, jz_mmc_irq, jz_mmc_irq_worker, 0, in jz4740_mmc_probe()
1078 dev_name(&pdev->dev), host); in jz4740_mmc_probe()
1080 dev_err(&pdev->dev, "Failed to request irq: %d\n", ret); in jz4740_mmc_probe()
1085 timer_setup(&host->timeout_timer, jz4740_mmc_timeout, 0); in jz4740_mmc_probe()
1088 if (ret == -EPROBE_DEFER) in jz4740_mmc_probe()
1090 host->use_dma = !ret; in jz4740_mmc_probe()
1093 ret = mmc_add_host(mmc); in jz4740_mmc_probe()
1096 dev_err(&pdev->dev, "Failed to add mmc host: %d\n", ret); in jz4740_mmc_probe()
1099 dev_info(&pdev->dev, "Ingenic SD/MMC card driver registered\n"); in jz4740_mmc_probe()
1101 dev_info(&pdev->dev, "Using %s, %d-bit mode\n", in jz4740_mmc_probe()
1102 host->use_dma ? "DMA" : "PIO", in jz4740_mmc_probe()
1103 (mmc->caps & MMC_CAP_8_BIT_DATA) ? 8 : in jz4740_mmc_probe()
1104 ((mmc->caps & MMC_CAP_4_BIT_DATA) ? 4 : 1)); in jz4740_mmc_probe()
1109 if (host->use_dma) in jz4740_mmc_probe()
1112 free_irq(host->irq, host); in jz4740_mmc_probe()
1114 mmc_free_host(mmc); in jz4740_mmc_probe()
1123 del_timer_sync(&host->timeout_timer); in jz4740_mmc_remove()
1127 mmc_remove_host(host->mmc); in jz4740_mmc_remove()
1129 free_irq(host->irq, host); in jz4740_mmc_remove()
1131 if (host->use_dma) in jz4740_mmc_remove()
1134 mmc_free_host(host->mmc); in jz4740_mmc_remove()
1156 .name = "jz4740-mmc",
1165 MODULE_DESCRIPTION("JZ4740 SD/MMC controller driver");
1167 MODULE_AUTHOR("Lars-Peter Clausen <lars@metafoo.de>");