片上系统设计思想与源代码分析
上QQ阅读APP看本书,新人免费读10天
设备和账号都新为新人

4.6 NandFlash控制器的验证

本章所给出的Nandflash的控制器已经在FPGA上验证通过。

这里给出采用SystemC TLM模型写的NandFlash的Testbench。关于SystemC的基本语法和SystemC的TLM建模,请参见本书附录A、附录B、第20章。关于Nandflash的全部代码及其分析,见附录D和本书所附光盘,或者http://www.socstart.cn

下文假设bus->write(int data, int addr)为向地址addr写入数据data,bus->read(int& data,int addr)为从地址addr读取数据放入data。bus->write(int data, int addr)和bus->read(int& data,int addr)的具体实现见本书附录D。

4.6.1 读ID

NandFlash SystemC Testbench读ID的代码如下:

int stimulus::nfReadID()
{
    int res,temp;
    bus->write(READ_ID,NFCMD_ADR);
    bus->write(0,NFADDR_ADR);
    bus->write(0,NFENDADDR_ADR);
    bus->read(res,NFDATA_ADR);
    SC_REPORT_INFO("master","started");
    printf("Data Read:%x\n",res);
    bus->read(temp,NFDATA_ADR);
    printf("Data Read:%x\n",temp);
    res=temp+(res<<8);
    bus->read(temp,NFDATA_ADR);
    printf("Data Read:%x\n",temp);
    res=temp+(res<<8);
    bus->read(temp,NFDATA_ADR);
    printf("Data Read:%x\n",temp);
    res=temp+(res<<8);
    return res;
};

波形如图4-11所示。

图4-11 读ID波形图

4.6.2 块擦除

SystemC Testbench块擦除的代码如下:

void stimulus::nfBlockErase(int addr)
{
    int temp;
    bus->write(BERASE_FST,NFCMD_ADR);
    bus->write(addr>>11,NFADDR_ADR);
    bus->write(addr>>19,NFADDR_ADR);
    temp=0x1&(addr>>27);
    bus->write(temp,NFADDR_ADR);
    bus->write(0,NFENDADDR_ADR);
    bus->write(BERASE_SEC,NFCMD_ADR);
    bus->waitClockTicks(160000);//100ns+3ms
};

波形如图4-12所示。

图4-12 块擦除波形图

4.6.3 写操作

SystemC Testbench写操作的代码如下:

int stimulus::nfPageProgram( int * data,  int addr, int length)
{
    int temp;
    bus->write(PPRAM_FST,NFCMD_ADR);
    bus->write(addr,NFADDR_ADR);
    temp=(addr>>8)&0xf; bus->write(temp,NFADDR_ADR);
    bus->write(addr>>12,NFADDR_ADR);
    bus->write(addr>>20,NFADDR_ADR);
    temp=(addr>>28)&0x1;bus->write(temp,NFADDR_ADR);
    bus->write(0,NFENDADDR_ADR);
    bus->waitClockTicks(5);
    //start writing data
    for(int i=0;i<length;i++)
    {
        temp=data[i];
        bus->write(temp,NFDATA_ADR);
        bus->write((temp&0xff00)>>8,NFDATA_ADR);
        bus->write((temp&0xff0000)>>16,NFDATA_ADR);
        bus->write((temp&0xff000000)>>24,NFDATA_ADR);
    }
    bus->write(PPRAM_SEC,NFCMD_ADR);
    bus->waitClockTicks(36000);//100ns+700us
};

波形如图4-13所示。

图4-13 写操作波形图

写操作(二)

写操作(一)

4.6.4 读操作

SystemC Testbench读操作的代码如下:

void stimulus::nfRead( int addr,  int *desc_addr,int length)
{
    int temp;
    bus->write(READ_FST,NFCMD_ADR);
    bus->write(addr,NFADDR_ADR);
    temp=(addr>>8)&0xf; bus->write(temp,NFADDR_ADR);
    bus->write(addr>>12,NFADDR_ADR);
    bus->write(addr>>20,NFADDR_ADR);
    temp=(addr>>28)&0x1;bus->write(temp,NFADDR_ADR);
    bus->write(0,NFENDADDR_ADR);
    bus->write(READ_SEC,NFCMD_ADR);
    //start read data
    for(int i=0;i<length;i++)
    {
        desc_addr[i]=0;
        bus->read(temp,NFDATA_ADR);
        printf("NFRead:%x,",temp);
        desc_addr[i]=temp;
        bus->read(temp,NFDATA_ADR);
        printf("%x,",temp);
        desc_addr[i]=(desc_addr[i]<<8)+temp;
        bus->read(temp,NFDATA_ADR);
        printf("%x,",temp);
        desc_addr[i]=(desc_addr[i]<<8)+temp;
        bus->read(temp,NFDATA_ADR);
        desc_addr[i]=(desc_addr[i]<<8)+temp;
    }
    bus->waitClockTicks(10);
    };

printf("%x\n",temp);

波形如图4-14所示。

图4-14 读操作波形图

读操作(一)

图4-14 读操作波形图(续)

读操作(二)