blob: 2c9bffb614c5b9808a34c9f80f77b01c3f44952c [file] [log] [blame]
Rafał Miłeckia54013702012-11-12 13:03:21 +01001/*
2 * BCM47XX NAND flash driver
3 *
4 * Copyright (C) 2012 Rafał Miłecki <zajec5@gmail.com>
5 *
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.
9 *
10 */
11
Rafał Miłeckibe0638d2013-02-07 11:56:04 +010012#include "bcm47xxnflash.h"
13
Rafał Miłeckia54013702012-11-12 13:03:21 +010014#include <linux/module.h>
15#include <linux/kernel.h>
16#include <linux/slab.h>
17#include <linux/platform_device.h>
18#include <linux/bcma/bcma.h>
19
Rafał Miłeckia54013702012-11-12 13:03:21 +010020MODULE_DESCRIPTION("NAND flash driver for BCMA bus");
21MODULE_LICENSE("GPL");
22MODULE_AUTHOR("Rafał Miłecki");
23
24static const char *probes[] = { "bcm47xxpart", NULL };
25
26static int bcm47xxnflash_probe(struct platform_device *pdev)
27{
28 struct bcma_nflash *nflash = dev_get_platdata(&pdev->dev);
29 struct bcm47xxnflash *b47n;
Boris BREZILLON17dd20b2015-12-10 08:59:52 +010030 struct mtd_info *mtd;
Rafał Miłeckia54013702012-11-12 13:03:21 +010031 int err = 0;
32
Sachin Kamat7e3019e2013-10-11 10:11:25 +053033 b47n = devm_kzalloc(&pdev->dev, sizeof(*b47n), GFP_KERNEL);
34 if (!b47n)
35 return -ENOMEM;
Rafał Miłeckia54013702012-11-12 13:03:21 +010036
37 b47n->nand_chip.priv = b47n;
Boris BREZILLON17dd20b2015-12-10 08:59:52 +010038 mtd = nand_to_mtd(&b47n->nand_chip);
39 mtd->dev.parent = &pdev->dev;
40 mtd->priv = &b47n->nand_chip; /* Required */
Rafał Miłeckia54013702012-11-12 13:03:21 +010041 b47n->cc = container_of(nflash, struct bcma_drv_cc, nflash);
42
Rafał Miłecki00940a22012-11-12 13:03:25 +010043 if (b47n->cc->core->bus->chipinfo.id == BCMA_CHIP_ID_BCM4706) {
44 err = bcm47xxnflash_ops_bcm4706_init(b47n);
Rafał Miłeckia54013702012-11-12 13:03:21 +010045 } else {
46 pr_err("Device not supported\n");
47 err = -ENOTSUPP;
48 }
49 if (err) {
50 pr_err("Initialization failed: %d\n", err);
Sachin Kamat7e3019e2013-10-11 10:11:25 +053051 return err;
Rafał Miłeckia54013702012-11-12 13:03:21 +010052 }
53
Brian Norris665d2c22015-12-08 17:04:59 -080054 platform_set_drvdata(pdev, b47n);
55
Boris BREZILLON17dd20b2015-12-10 08:59:52 +010056 err = mtd_device_parse_register(mtd, probes, NULL, NULL, 0);
Rafał Miłeckia54013702012-11-12 13:03:21 +010057 if (err) {
58 pr_err("Failed to register MTD device: %d\n", err);
Sachin Kamat7e3019e2013-10-11 10:11:25 +053059 return err;
Rafał Miłeckia54013702012-11-12 13:03:21 +010060 }
61
62 return 0;
Rafał Miłeckia54013702012-11-12 13:03:21 +010063}
64
Greg Kroah-Hartmand8929942012-12-21 13:19:05 -080065static int bcm47xxnflash_remove(struct platform_device *pdev)
Rafał Miłeckia54013702012-11-12 13:03:21 +010066{
Brian Norris665d2c22015-12-08 17:04:59 -080067 struct bcm47xxnflash *nflash = platform_get_drvdata(pdev);
Rafał Miłeckia54013702012-11-12 13:03:21 +010068
Boris BREZILLON17dd20b2015-12-10 08:59:52 +010069 nand_release(nand_to_mtd(&nflash->nand_chip));
Rafał Miłeckia54013702012-11-12 13:03:21 +010070
71 return 0;
72}
73
74static struct platform_driver bcm47xxnflash_driver = {
Hauke Mehrtensa7bf6542013-01-28 11:25:48 +010075 .probe = bcm47xxnflash_probe,
Greg Kroah-Hartmand8929942012-12-21 13:19:05 -080076 .remove = bcm47xxnflash_remove,
Rafał Miłeckia54013702012-11-12 13:03:21 +010077 .driver = {
78 .name = "bcma_nflash",
Rafał Miłeckia54013702012-11-12 13:03:21 +010079 },
80};
81
Sachin Kamat994bbd02013-10-11 10:11:24 +053082module_platform_driver(bcm47xxnflash_driver);