qt210 nand驱动学习笔记

来源:互联网 发布:js 获取鼠标轨迹 编辑:程序博客网 时间:2024/05/17 02:52
#include <linux/module.h>#include <linux/types.h>#include <linux/init.h>#include <linux/kernel.h>#include <linux/string.h>#include <linux/ioport.h>#include <linux/platform_device.h>#include <linux/delay.h>#include <linux/err.h>#include <linux/cpufreq.h>#include <linux/mtd/mtd.h>#include <linux/mtd/nand.h>#include <linux/mtd/nand_ecc.h>#include <linux/mtd/partitions.h>#include <linux/mtd/map.h>#include <linux/errno.h>#include <asm/io.h>#include <linux/slab.h>#include <mach/hardware.h>#include <asm/sizes.h>#include "mtdcore.h"static unsigned long *clk_gate_ip1;static unsigned long *clk_gate_block;static unsigned long *mp0_3con;//建立分区 static struct mtd_partition s3c_nand_parts[] = {[0] = {        .name   = "bootloader",        .size   = 0x00080000,.offset= 0,},[1] = {        .name   = "params",        .offset = MTDPART_OFS_APPEND,        .size   = 0x00400000,},[2] = {        .name   = "kernel",        .offset = MTDPART_OFS_APPEND,        .size   = 0x03000000,},[3] = {        .name   = "root",        .offset = MTDPART_OFS_APPEND,        .size   = MTDPART_SIZ_FULL,}};struct s3c_nand_regs {unsigned long nfconf  ;unsigned long nfcont  ;unsigned long nfcmmd   ;unsigned long nfaddr  ;unsigned long nfdata  ;unsigned long nfeccd0 ;unsigned long nfeccd1 ;unsigned long nfeccd  ;unsigned long nfsblk  ;unsigned long nfeblk  ;unsigned long nfstat  ;unsigned long nfeccerr0;unsigned long nfeccerr1;unsigned long nfmecc0 ;unsigned long nfmecc1 ;unsigned long nfsecc  ;};static struct nand_chip *s3c_nand;static struct mtd_info *s3c_mtd;static struct s3c_nand_regs *s3c_nand_regs;static void qt210_select_chip(struct mtd_info *mtd, int chipnr){if(chipnr==-1){s3c_nand_regs->nfcont|=(1<<1);//取消片选 }else{s3c_nand_regs->nfcont&=~(1<<1);//选中芯片 }}static void qt210_cmd_ctrl(struct mtd_info *mtd, int dat, unsigned int ctrl){if (ctrl & NAND_CLE){/* 发命令: NFCMMD=dat */s3c_nand_regs->nfcmmd = dat;}else{/* 发地址: NFADDR=dat */s3c_nand_regs->nfaddr = dat;}}static int qt210_dev_ready(struct mtd_info *mtd){return (s3c_nand_regs->nfstat & (1<<0));}static int qt210_nand_init(void){s3c_nand=kzalloc(sizeof(struct nand_chip), GFP_KERNEL);s3c_nand_regs=ioremap(0xB0E00000, sizeof(struct s3c_nand_regs));s3c_nand->select_chip=qt210_select_chip;s3c_nand->cmd_ctrl=qt210_cmd_ctrl;s3c_nand->IO_ADDR_R=&s3c_nand_regs->nfdata;s3c_nand->IO_ADDR_W=&s3c_nand_regs->nfdata;s3c_nand->dev_ready=qt210_dev_ready;s3c_nand->ecc.mode=NAND_ECC_SOFT;mp0_3con         = ioremap(0xE0200320,4);clk_gate_ip1     = ioremap(0xE0100464,4);clk_gate_block = ioremap(0xE0100480,4);/*3.硬件相关*//*使能时钟*/*clk_gate_ip1     = 0xffffffff;*clk_gate_block = 0xffffffff;/* 设置相应GPIO管脚用于Nand */*mp0_3con = 0x22222222;#define TACLS 1#define TWRPH0 2#define TWRPH1 1s3c_nand_regs->nfconf=(TACLS<<12) | (TWRPH0<<8) | (TWRPH1<<4);/* NFCONT:  * BIT1-设为1, 取消片选  * BIT0-设为1, 使能NAND FLASH控制器 */s3c_nand_regs->nfcont |= (1<<1) | (1<<0);/* 4. 使用: nand_scan */s3c_mtd = kzalloc(sizeof(struct mtd_info), GFP_KERNEL);s3c_mtd->owner = THIS_MODULE;s3c_mtd->priv  = s3c_nand;nand_scan(s3c_mtd,1);  /* 识别NAND FLASH, 构造mtd_info *//* 5. add_mtd_partitions */add_mtd_partitions(s3c_mtd, s3c_nand_parts, 4);return 0;}static qt210_nand_exit(void){del_mtd_partitions(s3c_mtd);kfree(s3c_mtd);iounmap(s3c_nand_regs);kfree(s3c_nand);}module_init(qt210_nand_init);module_exit(qt210_nand_exit);MODULE_LICENSE("GPL");


编译nandflash遇到了很多问题比如:

WARNING: "nand_scan" [/mnt/hgfs/yuyu/uu/qt210_nand.ko] undefined!

解决办法:make menuconfig 把nand选上
arch/arm/mach-s5pv210/
#include "dev-nand.c"

然后make uImage

就可解决了。