当前位置:首页 > 单片机 > 单片机
[导读]我们先查看内核的启动信息,以搞清楚从哪个文件着手来分析:S3C24XX NAND Driver, (c) 2004 Simtec Electronicss3c2440-nand s3c2440-nand: Tacls=3, 30ns Twrph0=7 70ns, Twrph1=3 30nsNAND device: Manufacturer I

我们先查看内核的启动信息,以搞清楚从哪个文件着手来分析:


S3C24XX NAND Driver, (c) 2004 Simtec Electronics

s3c2440-nand s3c2440-nand: Tacls=3, 30ns Twrph0=7 70ns, Twrph1=3 30ns

NAND device: Manufacturer ID: 0xec, Chip ID: 0xda (Samsung NAND 256MiB 3,3V 8-bit)

Scanning device for bad blocks

Bad eraseblock 408 at 0x03300000

Bad eraseblock 441 at 0x03720000

Bad eraseblock 804 at 0x06480000

Bad eraseblock 1155 at 0x09060000

Bad eraseblock 1236 at 0x09a80000

Creating 4 MTD partitions on "NAND 256MiB 3,3V 8-bit":

0x00000000-0x00040000 : "bootloader"

0x00040000-0x00060000 : "params"

0x00060000-0x00260000 : "kernel"

0x00260000-0x10000000 : "root"


我们来搜索:S3C24XX NAND Driver

结果我们在driversmtdnands3c2410.c文件里发现了打印这句话的函数:

static struct platform_driver s3c2440_nand_driver = {

.probe = s3c2440_nand_probe,

.remove = s3c2410_nand_remove,

.suspend = s3c24xx_nand_suspend,

.resume = s3c24xx_nand_resume,

.driver = {

.name = "s3c2440-nand",

.owner = THIS_MODULE,

},

};

static int __init s3c2410_nand_init(void)

{

printk("S3C24XX NAND Driver, (c) 2004 Simtec Electronicsn");


platform_driver_register(&s3c2412_nand_driver);

platform_driver_register(&s3c2440_nand_driver);

return platform_driver_register(&s3c2410_nand_driver);

}

我们看到了,nandflash采用的是平台总线设备机制,当发现名字是s3c2440-nand的设备的时候,就会调用probe函数,那么我们就从probe函数入手了:

s3c24xx_nand_probe

s3c2410_nand_inithw(info, pdev);//初始化硬件

s3c2410_nand_init_chip(info, nmtd, sets);//初始化芯片,这里设置了chip的一些信息

nand_scan(&nmtd->mtd, (sets) ? sets->nr_chips : 1);//扫描芯片

nand_scan_ident(struct mtd_info *mtd, int maxchips)

nand_set_defaults(chip, busw);//设置默认函数

nand_get_flash_type(mtd, chip, busw, &nand_maf_id);//获取nandflash类型

chip->select_chip(mtd, 0);//选中芯片

chip->cmdfunc(mtd, NAND_CMD_READID, 0x00, -1);//发出读ID的命令,NAND_CMD_READID为90h

*maf_id = chip->read_byte(mtd);//读厂家ID

dev_id = chip->read_byte(mtd);//读设备ID

for (i = 0; nand_flash_ids[i].name != NULL; i++)//根据设备id在nand_flash_ids[i]数组中找到其类型

{

if (dev_id == nand_flash_ids[i].id)

{

type = &nand_flash_ids[i];

break;

}

}

nand_scan_tail(mtd);//这里设置了读写和擦除函数

mtd->erase = nand_erase;

mtd->read = nand_read;

mtd->write = nand_write;

s3c2410_nand_add_partition(info, nmtd, sets);//添加分区

add_mtd_partitions(&mtd->mtd, set->partitions, set->nr_partitions);

add_mtd_device(&mtd->mtd);

list_for_each(this, &mtd_notifiers)//详见注释1

{

struct mtd_notifier *not = list_entry(this, struct mtd_notifier, list);

not->add(mtd);

}

注释1:

list_for_each(this, &mtd_notifiers)

{

struct mtd_notifier *not = list_entry(this, struct mtd_notifier, list);

not->add(mtd);

}

首先我们要搞清楚这个宏:list_entry(this, struct mtd_notifier, list);它会返回一个指向mtd_notifier结构体的指针

这样我们就明白了,我们需要知道在哪里定义了mtd_notifier这个东西,这样才能知道它的成员add函数。我们发现:

void register_mtd_user (struct mtd_notifier *new)

{

..........................................................

list_add(&new->list, &mtd_notifiers);

...........................................................

}

那么是谁调用了register_mtd_use函数呢?我们发现:

driversmtdMtd_blkdevs.c和driversmtdMtdchar.c文件里面都调用了这个函数,这两个文件一个对应字符设备一个对应块设备,这也说明了nandflash既可以作为字符设备,也可以作为块设备。我们先进入字符设备看看吧:

很快我们发现了add函数的定义:

static void mtd_notify_add(struct mtd_info* mtd)

{

if (!mtd)

return;

class_device_create(mtd_class, NULL, MKDEV(MTD_CHAR_MAJOR, mtd->index*2),NULL, "mtd%d", mtd->index);//创建设备节点

class_device_create(mtd_class, NULL,MKDEV(MTD_CHAR_MAJOR, mtd->index*2+1),NULL, "mtd%dro", mtd->index);//创建只读设备节点

}

我们有必要分析一下这个文件:

register_chrdev(MTD_CHAR_MAJOR, "mtd", &mtd_fops);//注册字符设备

class_create(THIS_MODULE, "mtd");//创建类,但是并没有在类下创建设备节点哦,这个节点要在适当的时候才来创建

mtd_notify_add(struct mtd_info* mtd);


我们再来看一下块设备驱动的吧:

很快我们就发下了add函数的定义:

static void blktrans_notify_add(struct mtd_info *mtd)

{

struct list_head *this;

if (mtd->type == MTD_ABSENT)

return;

list_for_each(this, &blktrans_majors) {

struct mtd_blktrans_ops *tr = list_entry(this, struct mtd_blktrans_ops, list);

tr->add_mtd(tr, mtd);

}

}

不过我们好像还得继续向上搜寻,我们要看一看是谁设置了blktrans_majors:

int register_mtd_blktrans(struct mtd_blktrans_ops *tr)

{

..........................................................

list_add(&tr->list, &blktrans_majors);

..........................................................

}

那么我们还要看看register_mtd_blktrans这个函数在哪里调用:

我们在driversmtdMtdblock.c文件里面发现了调用:

很快我们找到了add函数的定义:
mtdblock_add_mtd(struct mtd_blktrans_ops *tr, struct mtd_info *mtd)

add_mtd_blktrans_dev(dev);

alloc_disk(1 << tr->part_bits);//申请磁盘,一下就可以看出和我们上节课编写的驱动程序挂钩了哦!

gd->queue = tr->blkcore_priv->rq;//设置队列

add_disk;//注册磁盘

针对上面的分析,我们在这里整理一下,首先来说一说将nandflash当作块设备来用的时候,其工作流程:

我们其实是分成了几个层次的,一个是块设备,我们在之前已经知道了,应用程序对块设备的读写请求被放放入队列里面,也就是说块设备对请求作了优化。而我们从s3c2410_nand_add_partition函数分析出来,mtdblock_add_mtd里面注册了这个队列,那么请求就可以放在这个队列里面,并且这个函数里面还分配的磁盘并且注册了磁盘。下面还差

本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除。
换一批
延伸阅读

关于使用烧录器烧录Nand Flash,一直都是很多用户头疼的难点,他们强调已经使用了正确的坏块管理方案,也制定了规范的操作流程,但是烧录的良品率还是无法提高,只能每天眼睁睁看着一盘盘&ldqu

关键字: nandflash 烧录器

5月26日消息,据国外媒体报道,集邦咨询半导体研究中心(DRAMeXchange)在周一发布的一份报告中称,今年第一季度,三星在全球NAND Flash市场上的份额为33.3%,与前一季度相比,环比略

关键字: nandflash 三星 芯片

华为作为美光最大的客户之一,美国将华为列入实体名单一事对美光产生了非常严重的影响,美光业绩已经逐渐露出下滑趋势,上周五美光股价大跌近7%,南亚科、华邦电、威刚等存储器企业也纷纷走低。 近期DRAM及N

关键字: DRAM nandflash 美光 芯片

6月24日消息 日前全球第二大闪存供应商东芝位于日本三重县的闪存工厂因地震遭遇断电事故,虽然停电过程非常短,13分钟之后就恢复供电了,但是工厂却一直停产,直到21日上午才恢复,至少停工了5天时间。 根

关键字: nandflash 东芝 台积电 芯片 闪存

Nandflash芯片以其高性价比,大存储容量在电子产品中广泛应用。但是,在此量大质优的应用领域,很多客户却痛苦于批量质量问题:专用工具无法满足量产,量产工具却可能出现极大的不良品率,那么究竟要如何解决呢?

关键字: nandflash 芯片 烧录技巧

一、 首先先来看看核心板的原理图我们发现数据线才有8条,而并没有地址信号,所以该8条线一定是可以传数据,也可以传地址。而地址线肯定又不够,那么,地址肯定又是多次发出的。从datasheet可以看到它要发出5个周期的

关键字: nandflash ok6410 硬件

它包含7个文件:head.Sinit.cmain.cMakefilenand.cnand.lds我们之前的程序都是在nandflash的前4k放代码,上电后自动拷贝到SRAM中,之后将SRAM中的代码拷贝到SDRAM中。...

关键字: nandflash 裸机程序

注:此文为部分摘录,并且在原文基础上有改动link这几天一直在摸索s3c2410的启动过程,几天的困惑终于在昨天晚上基本解决.下面详细分析一下它的最前面的启动过程.1.在板子上电的一开始,首先自动判断是否是autoboo...

关键字: nandflash s3c2410 启动过程
关闭
关闭