root/drivers/mtd/nand/raw/oxnas_nand.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. oxnas_nand_read_byte
  2. oxnas_nand_read_buf
  3. oxnas_nand_write_buf
  4. oxnas_nand_cmd_ctrl
  5. oxnas_nand_probe
  6. oxnas_nand_remove

   1 // SPDX-License-Identifier: GPL-2.0-only
   2 /*
   3  * Oxford Semiconductor OXNAS NAND driver
   4 
   5  * Copyright (C) 2016 Neil Armstrong <narmstrong@baylibre.com>
   6  * Heavily based on plat_nand.c :
   7  * Author: Vitaly Wool <vitalywool@gmail.com>
   8  * Copyright (C) 2013 Ma Haijun <mahaijuns@gmail.com>
   9  * Copyright (C) 2012 John Crispin <blogic@openwrt.org>
  10  */
  11 
  12 #include <linux/err.h>
  13 #include <linux/io.h>
  14 #include <linux/module.h>
  15 #include <linux/platform_device.h>
  16 #include <linux/slab.h>
  17 #include <linux/clk.h>
  18 #include <linux/reset.h>
  19 #include <linux/mtd/mtd.h>
  20 #include <linux/mtd/rawnand.h>
  21 #include <linux/mtd/partitions.h>
  22 #include <linux/of.h>
  23 
  24 /* Nand commands */
  25 #define OXNAS_NAND_CMD_ALE              BIT(18)
  26 #define OXNAS_NAND_CMD_CLE              BIT(19)
  27 
  28 #define OXNAS_NAND_MAX_CHIPS    1
  29 
  30 struct oxnas_nand_ctrl {
  31         struct nand_controller base;
  32         void __iomem *io_base;
  33         struct clk *clk;
  34         struct nand_chip *chips[OXNAS_NAND_MAX_CHIPS];
  35 };
  36 
  37 static uint8_t oxnas_nand_read_byte(struct nand_chip *chip)
  38 {
  39         struct oxnas_nand_ctrl *oxnas = nand_get_controller_data(chip);
  40 
  41         return readb(oxnas->io_base);
  42 }
  43 
  44 static void oxnas_nand_read_buf(struct nand_chip *chip, u8 *buf, int len)
  45 {
  46         struct oxnas_nand_ctrl *oxnas = nand_get_controller_data(chip);
  47 
  48         ioread8_rep(oxnas->io_base, buf, len);
  49 }
  50 
  51 static void oxnas_nand_write_buf(struct nand_chip *chip, const u8 *buf,
  52                                  int len)
  53 {
  54         struct oxnas_nand_ctrl *oxnas = nand_get_controller_data(chip);
  55 
  56         iowrite8_rep(oxnas->io_base, buf, len);
  57 }
  58 
  59 /* Single CS command control */
  60 static void oxnas_nand_cmd_ctrl(struct nand_chip *chip, int cmd,
  61                                 unsigned int ctrl)
  62 {
  63         struct oxnas_nand_ctrl *oxnas = nand_get_controller_data(chip);
  64 
  65         if (ctrl & NAND_CLE)
  66                 writeb(cmd, oxnas->io_base + OXNAS_NAND_CMD_CLE);
  67         else if (ctrl & NAND_ALE)
  68                 writeb(cmd, oxnas->io_base + OXNAS_NAND_CMD_ALE);
  69 }
  70 
  71 /*
  72  * Probe for the NAND device.
  73  */
  74 static int oxnas_nand_probe(struct platform_device *pdev)
  75 {
  76         struct device_node *np = pdev->dev.of_node;
  77         struct device_node *nand_np;
  78         struct oxnas_nand_ctrl *oxnas;
  79         struct nand_chip *chip;
  80         struct mtd_info *mtd;
  81         struct resource *res;
  82         int nchips = 0;
  83         int count = 0;
  84         int err = 0;
  85 
  86         /* Allocate memory for the device structure (and zero it) */
  87         oxnas = devm_kzalloc(&pdev->dev, sizeof(*oxnas),
  88                              GFP_KERNEL);
  89         if (!oxnas)
  90                 return -ENOMEM;
  91 
  92         nand_controller_init(&oxnas->base);
  93 
  94         res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
  95         oxnas->io_base = devm_ioremap_resource(&pdev->dev, res);
  96         if (IS_ERR(oxnas->io_base))
  97                 return PTR_ERR(oxnas->io_base);
  98 
  99         oxnas->clk = devm_clk_get(&pdev->dev, NULL);
 100         if (IS_ERR(oxnas->clk))
 101                 oxnas->clk = NULL;
 102 
 103         /* Only a single chip node is supported */
 104         count = of_get_child_count(np);
 105         if (count > 1)
 106                 return -EINVAL;
 107 
 108         err = clk_prepare_enable(oxnas->clk);
 109         if (err)
 110                 return err;
 111 
 112         device_reset_optional(&pdev->dev);
 113 
 114         for_each_child_of_node(np, nand_np) {
 115                 chip = devm_kzalloc(&pdev->dev, sizeof(struct nand_chip),
 116                                     GFP_KERNEL);
 117                 if (!chip) {
 118                         err = -ENOMEM;
 119                         goto err_release_child;
 120                 }
 121 
 122                 chip->controller = &oxnas->base;
 123 
 124                 nand_set_flash_node(chip, nand_np);
 125                 nand_set_controller_data(chip, oxnas);
 126 
 127                 mtd = nand_to_mtd(chip);
 128                 mtd->dev.parent = &pdev->dev;
 129                 mtd->priv = chip;
 130 
 131                 chip->legacy.cmd_ctrl = oxnas_nand_cmd_ctrl;
 132                 chip->legacy.read_buf = oxnas_nand_read_buf;
 133                 chip->legacy.read_byte = oxnas_nand_read_byte;
 134                 chip->legacy.write_buf = oxnas_nand_write_buf;
 135                 chip->legacy.chip_delay = 30;
 136 
 137                 /* Scan to find existence of the device */
 138                 err = nand_scan(chip, 1);
 139                 if (err)
 140                         goto err_release_child;
 141 
 142                 err = mtd_device_register(mtd, NULL, 0);
 143                 if (err) {
 144                         nand_release(chip);
 145                         goto err_release_child;
 146                 }
 147 
 148                 oxnas->chips[nchips] = chip;
 149                 ++nchips;
 150         }
 151 
 152         /* Exit if no chips found */
 153         if (!nchips) {
 154                 err = -ENODEV;
 155                 goto err_clk_unprepare;
 156         }
 157 
 158         platform_set_drvdata(pdev, oxnas);
 159 
 160         return 0;
 161 
 162 err_release_child:
 163         of_node_put(nand_np);
 164 err_clk_unprepare:
 165         clk_disable_unprepare(oxnas->clk);
 166         return err;
 167 }
 168 
 169 static int oxnas_nand_remove(struct platform_device *pdev)
 170 {
 171         struct oxnas_nand_ctrl *oxnas = platform_get_drvdata(pdev);
 172 
 173         if (oxnas->chips[0])
 174                 nand_release(oxnas->chips[0]);
 175 
 176         clk_disable_unprepare(oxnas->clk);
 177 
 178         return 0;
 179 }
 180 
 181 static const struct of_device_id oxnas_nand_match[] = {
 182         { .compatible = "oxsemi,ox820-nand" },
 183         {},
 184 };
 185 MODULE_DEVICE_TABLE(of, oxnas_nand_match);
 186 
 187 static struct platform_driver oxnas_nand_driver = {
 188         .probe  = oxnas_nand_probe,
 189         .remove = oxnas_nand_remove,
 190         .driver = {
 191                 .name           = "oxnas_nand",
 192                 .of_match_table = oxnas_nand_match,
 193         },
 194 };
 195 
 196 module_platform_driver(oxnas_nand_driver);
 197 
 198 MODULE_LICENSE("GPL");
 199 MODULE_AUTHOR("Neil Armstrong <narmstrong@baylibre.com>");
 200 MODULE_DESCRIPTION("Oxnas NAND driver");
 201 MODULE_ALIAS("platform:oxnas_nand");

/* [<][>][^][v][top][bottom][index][help] */