Commit 01e4f958 authored by Alexander Shiyan's avatar Alexander Shiyan Committed by Chris Ball

mmc: mxcmmc: Convert to devm-* API

Replace existing resource handling in the driver with managed
device resource, this ensures more consistent error values and
simplifies error paths.
Signed-off-by: default avatarAlexander Shiyan <shc_work@mail.ru>
Signed-off-by: default avatarUlf Hansson <ulf.hansson@linaro.org>
Signed-off-by: default avatarChris Ball <chris@printf.net>
parent 15a2e2ab
...@@ -124,9 +124,8 @@ enum mxcmci_type { ...@@ -124,9 +124,8 @@ enum mxcmci_type {
struct mxcmci_host { struct mxcmci_host {
struct mmc_host *mmc; struct mmc_host *mmc;
struct resource *res;
void __iomem *base; void __iomem *base;
int irq; dma_addr_t phys_base;
int detect_irq; int detect_irq;
struct dma_chan *dma; struct dma_chan *dma;
struct dma_async_tx_descriptor *desc; struct dma_async_tx_descriptor *desc;
...@@ -241,33 +240,26 @@ static inline void mxcmci_writew(struct mxcmci_host *host, u16 val, int reg) ...@@ -241,33 +240,26 @@ static inline void mxcmci_writew(struct mxcmci_host *host, u16 val, int reg)
static void mxcmci_set_clk_rate(struct mxcmci_host *host, unsigned int clk_ios); static void mxcmci_set_clk_rate(struct mxcmci_host *host, unsigned int clk_ios);
static inline void mxcmci_init_ocr(struct mxcmci_host *host) static void mxcmci_init_ocr(struct mxcmci_host *host)
{ {
host->vcc = regulator_get(mmc_dev(host->mmc), "vmmc"); host->vcc = devm_regulator_get(mmc_dev(host->mmc), "vmmc");
if (IS_ERR(host->vcc)) { if (IS_ERR(host->vcc)) {
host->vcc = NULL; if (host->pdata && host->pdata->ocr_avail)
host->mmc->ocr_avail = host->pdata->ocr_avail;
else
host->mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
} else { } else {
host->mmc->ocr_avail = mmc_regulator_get_ocrmask(host->vcc); host->mmc->ocr_avail = mmc_regulator_get_ocrmask(host->vcc);
if (host->pdata && host->pdata->ocr_avail) if (host->pdata && host->pdata->ocr_avail)
dev_warn(mmc_dev(host->mmc), dev_warn(mmc_dev(host->mmc),
"pdata->ocr_avail will not be used\n"); "pdata->ocr_avail will not be used\n");
} }
if (host->vcc == NULL) {
/* fall-back to platform data */
if (host->pdata && host->pdata->ocr_avail)
host->mmc->ocr_avail = host->pdata->ocr_avail;
else
host->mmc->ocr_avail = MMC_VDD_32_33 | MMC_VDD_33_34;
}
} }
static inline void mxcmci_set_power(struct mxcmci_host *host, static void mxcmci_set_power(struct mxcmci_host *host, unsigned char power_mode,
unsigned char power_mode, unsigned int vdd)
unsigned int vdd)
{ {
if (host->vcc) { if (!IS_ERR(host->vcc)) {
if (power_mode == MMC_POWER_UP) if (power_mode == MMC_POWER_UP)
mmc_regulator_set_ocr(host->mmc, host->vcc, vdd); mmc_regulator_set_ocr(host->mmc, host->vcc, vdd);
else if (power_mode == MMC_POWER_OFF) else if (power_mode == MMC_POWER_OFF)
...@@ -299,7 +291,6 @@ static void mxcmci_softreset(struct mxcmci_host *host) ...@@ -299,7 +291,6 @@ static void mxcmci_softreset(struct mxcmci_host *host)
mxcmci_writew(host, 0xff, MMC_REG_RES_TO); mxcmci_writew(host, 0xff, MMC_REG_RES_TO);
} }
static int mxcmci_setup_dma(struct mmc_host *mmc);
#if IS_ENABLED(CONFIG_PPC_MPC512x) #if IS_ENABLED(CONFIG_PPC_MPC512x)
static inline void buffer_swap32(u32 *buf, int len) static inline void buffer_swap32(u32 *buf, int len)
...@@ -868,8 +859,8 @@ static int mxcmci_setup_dma(struct mmc_host *mmc) ...@@ -868,8 +859,8 @@ static int mxcmci_setup_dma(struct mmc_host *mmc)
struct mxcmci_host *host = mmc_priv(mmc); struct mxcmci_host *host = mmc_priv(mmc);
struct dma_slave_config *config = &host->dma_slave_config; struct dma_slave_config *config = &host->dma_slave_config;
config->dst_addr = host->res->start + MMC_REG_BUFFER_ACCESS; config->dst_addr = host->phys_base + MMC_REG_BUFFER_ACCESS;
config->src_addr = host->res->start + MMC_REG_BUFFER_ACCESS; config->src_addr = host->phys_base + MMC_REG_BUFFER_ACCESS;
config->dst_addr_width = 4; config->dst_addr_width = 4;
config->src_addr_width = 4; config->src_addr_width = 4;
config->dst_maxburst = host->burstlen; config->dst_maxburst = host->burstlen;
...@@ -1040,8 +1031,8 @@ static const struct mmc_host_ops mxcmci_ops = { ...@@ -1040,8 +1031,8 @@ static const struct mmc_host_ops mxcmci_ops = {
static int mxcmci_probe(struct platform_device *pdev) static int mxcmci_probe(struct platform_device *pdev)
{ {
struct mmc_host *mmc; struct mmc_host *mmc;
struct mxcmci_host *host = NULL; struct mxcmci_host *host;
struct resource *iores, *r; struct resource *res;
int ret = 0, irq; int ret = 0, irq;
bool dat3_card_detect = false; bool dat3_card_detect = false;
dma_cap_mask_t mask; dma_cap_mask_t mask;
...@@ -1052,21 +1043,25 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1052,21 +1043,25 @@ static int mxcmci_probe(struct platform_device *pdev)
of_id = of_match_device(mxcmci_of_match, &pdev->dev); of_id = of_match_device(mxcmci_of_match, &pdev->dev);
iores = platform_get_resource(pdev, IORESOURCE_MEM, 0); res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
irq = platform_get_irq(pdev, 0); irq = platform_get_irq(pdev, 0);
if (!iores || irq < 0) if (irq < 0)
return -EINVAL; return -EINVAL;
r = request_mem_region(iores->start, resource_size(iores), pdev->name); mmc = mmc_alloc_host(sizeof(*host), &pdev->dev);
if (!r) if (!mmc)
return -EBUSY; return -ENOMEM;
mmc = mmc_alloc_host(sizeof(struct mxcmci_host), &pdev->dev); host = mmc_priv(mmc);
if (!mmc) {
ret = -ENOMEM; host->base = devm_ioremap_resource(&pdev->dev, res);
goto out_release_mem; if (IS_ERR(host->base)) {
ret = PTR_ERR(host->base);
goto out_free;
} }
host->phys_base = res->start;
ret = mmc_of_parse(mmc); ret = mmc_of_parse(mmc);
if (ret) if (ret)
goto out_free; goto out_free;
...@@ -1084,13 +1079,6 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1084,13 +1079,6 @@ static int mxcmci_probe(struct platform_device *pdev)
mmc->max_req_size = mmc->max_blk_size * mmc->max_blk_count; mmc->max_req_size = mmc->max_blk_size * mmc->max_blk_count;
mmc->max_seg_size = mmc->max_req_size; mmc->max_seg_size = mmc->max_req_size;
host = mmc_priv(mmc);
host->base = ioremap(r->start, resource_size(r));
if (!host->base) {
ret = -ENOMEM;
goto out_free;
}
if (of_id) { if (of_id) {
const struct platform_device_id *id_entry = of_id->data; const struct platform_device_id *id_entry = of_id->data;
host->devtype = id_entry->driver_data; host->devtype = id_entry->driver_data;
...@@ -1120,19 +1108,16 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1120,19 +1108,16 @@ static int mxcmci_probe(struct platform_device *pdev)
else else
host->default_irq_mask = 0; host->default_irq_mask = 0;
host->res = r;
host->irq = irq;
host->clk_ipg = devm_clk_get(&pdev->dev, "ipg"); host->clk_ipg = devm_clk_get(&pdev->dev, "ipg");
if (IS_ERR(host->clk_ipg)) { if (IS_ERR(host->clk_ipg)) {
ret = PTR_ERR(host->clk_ipg); ret = PTR_ERR(host->clk_ipg);
goto out_iounmap; goto out_free;
} }
host->clk_per = devm_clk_get(&pdev->dev, "per"); host->clk_per = devm_clk_get(&pdev->dev, "per");
if (IS_ERR(host->clk_per)) { if (IS_ERR(host->clk_per)) {
ret = PTR_ERR(host->clk_per); ret = PTR_ERR(host->clk_per);
goto out_iounmap; goto out_free;
} }
clk_prepare_enable(host->clk_per); clk_prepare_enable(host->clk_per);
...@@ -1159,9 +1144,9 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1159,9 +1144,9 @@ static int mxcmci_probe(struct platform_device *pdev)
if (!host->pdata) { if (!host->pdata) {
host->dma = dma_request_slave_channel(&pdev->dev, "rx-tx"); host->dma = dma_request_slave_channel(&pdev->dev, "rx-tx");
} else { } else {
r = platform_get_resource(pdev, IORESOURCE_DMA, 0); res = platform_get_resource(pdev, IORESOURCE_DMA, 0);
if (r) { if (res) {
host->dmareq = r->start; host->dmareq = res->start;
host->dma_data.peripheral_type = IMX_DMATYPE_SDHC; host->dma_data.peripheral_type = IMX_DMATYPE_SDHC;
host->dma_data.priority = DMA_PRIO_LOW; host->dma_data.priority = DMA_PRIO_LOW;
host->dma_data.dma_request = host->dmareq; host->dma_data.dma_request = host->dmareq;
...@@ -1178,7 +1163,8 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1178,7 +1163,8 @@ static int mxcmci_probe(struct platform_device *pdev)
INIT_WORK(&host->datawork, mxcmci_datawork); INIT_WORK(&host->datawork, mxcmci_datawork);
ret = request_irq(host->irq, mxcmci_irq, 0, DRIVER_NAME, host); ret = devm_request_irq(&pdev->dev, irq, mxcmci_irq, 0,
dev_name(&pdev->dev), host);
if (ret) if (ret)
goto out_free_dma; goto out_free_dma;
...@@ -1188,7 +1174,7 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1188,7 +1174,7 @@ static int mxcmci_probe(struct platform_device *pdev)
ret = host->pdata->init(&pdev->dev, mxcmci_detect_irq, ret = host->pdata->init(&pdev->dev, mxcmci_detect_irq,
host->mmc); host->mmc);
if (ret) if (ret)
goto out_free_irq; goto out_free_dma;
} }
init_timer(&host->watchdog); init_timer(&host->watchdog);
...@@ -1199,20 +1185,17 @@ static int mxcmci_probe(struct platform_device *pdev) ...@@ -1199,20 +1185,17 @@ static int mxcmci_probe(struct platform_device *pdev)
return 0; return 0;
out_free_irq:
free_irq(host->irq, host);
out_free_dma: out_free_dma:
if (host->dma) if (host->dma)
dma_release_channel(host->dma); dma_release_channel(host->dma);
out_clk_put: out_clk_put:
clk_disable_unprepare(host->clk_per); clk_disable_unprepare(host->clk_per);
clk_disable_unprepare(host->clk_ipg); clk_disable_unprepare(host->clk_ipg);
out_iounmap:
iounmap(host->base);
out_free: out_free:
mmc_free_host(mmc); mmc_free_host(mmc);
out_release_mem:
release_mem_region(iores->start, resource_size(iores));
return ret; return ret;
} }
...@@ -1223,23 +1206,15 @@ static int mxcmci_remove(struct platform_device *pdev) ...@@ -1223,23 +1206,15 @@ static int mxcmci_remove(struct platform_device *pdev)
mmc_remove_host(mmc); mmc_remove_host(mmc);
if (host->vcc)
regulator_put(host->vcc);
if (host->pdata && host->pdata->exit) if (host->pdata && host->pdata->exit)
host->pdata->exit(&pdev->dev, mmc); host->pdata->exit(&pdev->dev, mmc);
free_irq(host->irq, host);
iounmap(host->base);
if (host->dma) if (host->dma)
dma_release_channel(host->dma); dma_release_channel(host->dma);
clk_disable_unprepare(host->clk_per); clk_disable_unprepare(host->clk_per);
clk_disable_unprepare(host->clk_ipg); clk_disable_unprepare(host->clk_ipg);
release_mem_region(host->res->start, resource_size(host->res));
mmc_free_host(mmc); mmc_free_host(mmc);
return 0; return 0;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment