这些小活动你都参加了吗?快来围观一下吧!>>
电子产品世界 » 论坛首页 » 嵌入式开发 » MCU » K9F2808U0A存储结构与访问

共1条 1/1 1 跳转至

K9F2808U0A存储结构与访问

专家
2009-03-13 12:47:33     打赏
 

 

K9F2808U0A的存储结构如图所示

点击开大图

                  1

K9F1208U0A 的数据是以bit 的方式保存在cell,这些cell 8 个为单位连成column也是该器件的位宽,这些column528个为组组成Page.32page形成block(如图1)。而528column又被分为1st half2nd half3rd 三部分,其中1st half256column2nd half256column3rd   16column
正因为如此K9F2808U0A的地址分为三级:

--Block Address -- Page Address  --Column Address
Nand flash 以页为单位读写数据,而以块为单位擦除数据。地址和命令只能在I/O[7:0]上传递,数据宽度是8 位。 

点击开大图
A[7:0]就是所谓的column address

A8不参与抵制译码

A[13:9],用来确定page地址

A[23:14]用来确定block地址

地址传送顺序是Column Address,Page Address,Block Address
由于地址只能在I/O[7:0]上传递,因此,必须采用移位的方式进行。 例如,对于128MbitNAND flash,地址范围是0~0xFF_FFFF,只要是这个范围内的数值表示的地址都是有效的。

操作 1 步是传递column address,就是A[7:0],不需移位即可传递到I/O[7:0]上,而halfpage pointer bit8 是由操作指令决定的,即指令决定在哪个halfpage 上进行读写。第2 步就是将NAND_ADDR 右移9 位(因为bit8不参与地址译码),将A[13:9]传到I/O[7:0] 3 步将A[23:14]放到I/O .因此,整个地址传递过程需要3 步才能完成,即3-step addressing。对于存储空间大于128Mbitnandflash则需要四步完成,第四步传动地址为A[XX:24].我的板子引脚链接如图2和图3所示.

                    图2

 

 

                      图3

根据这个可以定义访问地址如下:

#define Nand_RB        (0x0400)

#define Nand_CE        (0x4000)

#define Nand_CLE     (0x04)

#define Nand_ALE     (0x08)

#define Nand_IO_DAT    (*(volatile unsigned char *)0x02000000)     

#define Nand_IO_CMD       (*(volatile unsigned char *)(0x02000000|Nand_CLE)) #define Nand_IO_ADR          (*(volatile unsigned char *)(0x02000000|Nand_ALE))

下面是程序的源码:

复位:

void Flash_Reset()      

{

    int i;

    NAND_CMD();

    Nand_IO_CMD = 0xff; 

    for (i=0;i<0x3ff;i++);     

}

读ID

unsigned int Check_Flash_Id(void)

{

    int i;

    unsigned int id;

    NAND_CMD();

    Nand_IO_CMD = 0x90;

    NAND_INVALID();//这句不是必须的

    NAND_ADR();

    Nand_IO_ADR = 0;

    NAND_INVALID();

    NAND_DAT();

    for(i=0;i<10;i++);  

    id = Nand_IO_DAT<<8;//连续读出两个字节

    id += Nand_IO_DAT;

    NAND_INVALID();

    return id;

}

块擦除:

unsigned char Erase_Cluster(unsigned int block)

{

    unsigned int blockPage = (block<<5);

    int i;

 

    NAND_CMD();

    Nand_IO_CMD = 0x60;

    NAND_ADR();       

    Nand_IO_ADR = blockPage & 0xff; 

    Nand_IO_ADR = (blockPage>>8) & 0xff;

    for(i=0;i<2;i++);

    NAND_CMD();

    Nand_IO_CMD = 0xd0;   

    for(i=0;i<3;i++);   

    NAND_DAT();

    WAIT_RB();

    NAND_CMD();

    Nand_IO_CMD= 0x70;

    NAND_DAT();

    if (Nand_IO_DAT & 0x1)

    {

       NAND_INVALID();

       return 0;

    }

    else

    {

       NAND_INVALID();  

       return 1;

    }

}

页写int WritePage(unsigned int block,unsigned int page,unsigned char *buffer) 

{

    unsigned int blockPage = (block<<5) + page;

    int i;

    NAND_CMD();

    Nand_IO_CMD = 0x80;

    NAND_ADR();

    Nand_IO_ADR = 0;

    Nand_IO_ADR = blockPage & 0xff;

    Nand_IO_ADR = (blockPage>>8) & 0xff;

    NAND_DAT();

    for(i=0;i<528;i++)

    {

        Nand_IO_DAT=*buffer++;

    }       

    //WritePage(buffer);

    NAND_CMD();

    Nand_IO_CMD= 0x10;

    for(i=0;i<10;i++);

    WAIT_RB();      ////////////

    Nand_IO_CMD = 0x70; ///////////////////////////

    NAND_DAT();

    for(i=0;i<3;i++); 

    if((Nand_IO_DAT & 0x1)) 

    {

       NAND_INVALID();  

       return 0;

    }

    else

    {

       NAND_INVALID();

       return 1;     

    }

}

测试函数如下:

void Read_ID(void)

{

    unsigned short id;

    id = Check_Flash_Id();

    uart_printf("\nNandFLASH Chip's ID is 0x%4x\n",id);

}

 

void Erase_test(void)

{

    uart_printf("\nBegin to erase the last block...");

    if(Erase_Cluster(LASTBLOCK))

       uart_printf("\nOK! Compeleted.");

    else

        uart_printf("\nErase error!");

}

 

 

void Write_test(void)

{

    int i;

    unsigned char buffer[528];

    for(i=0;i<528;i++)

       buffer[i]=0xaa;

    uart_printf("\nBegin to Write the first Page of the last block...");

    if(WritePage(LASTBLOCK,0,buffer))

        uart_printf("\nOK! Compeleted.");

    else

        uart_printf("\nWrite error!");

}

 

void Read_test(void)

{

    int i,j=0;

    unsigned char buffer[528];

   

    uart_printf("\nBegin to Read the first Page of the last block...");

    ReadPage(LASTBLOCK,0,buffer);

    for(i=0;i<528;i++)

    {

       if(buffer[i]==0xaa)

           j++;

    }

    uart_printf("\n%4d Bytes verify match!",j);

}

注:由于读写以页为单位,所以选定页后一次可以读写528个字节,但是不建议对第三块进行读写




关键词: K9F2808U0A     存储     结构     访问     地址     un    

共1条 1/1 1 跳转至

回复

匿名不能发帖!请先 [ 登陆 注册 ]