#include #include #include #include #include #include #include /*spinand rom print level*/ #define DEBUG_LEVEL 4 #define INFO_LEVEL 3 #define WARN_LEVEL 2 #define ERROR_LEVEL 1 /* struct FlashChipInfo takes total 60 bytes size */ #define NAND_CHIPID_LENGTH (8) /* nand flash chipid length */ /* * struct FlashChipInfo takes total 60 bytes size * read mode: * 0x0:1xIO(0x03), cpu trans; 0x10:1xIO(0x03), dma trans; * 0x1:2xIO-quad(0xbb), cpu trans; 0x11:2xIO-quad(0xbb), dma trans; * 0x2:2xIO-dual(0x3b), cpu trans; 0x12:2xIO-dual(0x3b), dma trans; * 0x4:4xIO-quad(0x6b), cpu trans; 0x14:4xIO-quad(0x6b), dma trans; * 0x8:4xIO-dual(0xeb), cpu trans; 0x18:4xIO-dual(0xeb), dma trans. * write mode: * 0x0:1xIO(0x02), cpu trans; 0x10:1xIO(0x02), dma trans; * 0x4:4xIO-quad(0x32), cpu trans; 0x14:4xIO-quad(0x32), dma trans; */ struct FlashChipInfo { uint8_t ChipID[NAND_CHIPID_LENGTH]; /* nand flash id */ uint8_t ChipCnt; /* the count of chip connecting in flash*/ uint8_t DieCntPerChip; /* the die count in a chip */ uint8_t PlaneCntPerDie; /* the plane count in a die */ uint8_t SectorNumPerPage; /* page size, based on sector */ uint8_t SpareBytesPerSector; /* spare bytes per sector */ uint8_t Frequence; /* spi clk, may be based on xMHz */ uint16_t PageNumPerPhyBlk; /* the page number of physic block */ uint16_t TotalBlkNumPerDie; /* total number of the physic block in a die */ uint16_t DefaultLBlkNumPer1024Blk; /* Logical number per 1024 physical block */ uint16_t userMetaOffset; /*user meta data offset, add for spinand*/ uint8_t userMetaShift; /*user meta data shift, add for spinand*/ uint8_t userMetaSize; /*user meta data size, add for spinand*/ uint8_t ECCBits; uint8_t eccStatusMask; /*ecc status mask, add for spinand*/ uint8_t eccStatusErrVal; /*ecc status err value, add for spinand*/ uint8_t readAddressBits; /*read address bit, 16bit or 24bit address, add for spinand*/ uint8_t readMode; uint8_t writeMode; uint8_t Version; /* flash chipinfo version */ uint8_t FlashMark[16]; /* the name of spinand */ uint8_t delayChain; /* the delaychain of spinand, value from 0 to 63(spi0) or 31(spi1, spi2, spi3) */ uint8_t Reserved1[12]; /* reserved */ } __attribute__ ((packed)); //10Byte struct NandIdTblHeader { uint8_t num; uint32_t magic; uint32_t checksum; uint8_t Reserved; } __attribute__ ((packed)); struct nand_info { /* spi controller address */ uint32_t base; uint8_t bus_width; uint8_t delay_chain; uint8_t spi_mode; uint8_t data; uint32_t dma_base; int (*printf)(const char *fmt, ...); //1:err;2:warn;3:info;4:debug. uint8_t loglevel; //act as a patch for spinand rom. uint8_t (*phy_readpage)(void *sni, uint32_t colAddr, void *buf, uint32_t len, int addrBits, int mode); uint8_t (*phy_writepage)(void *sni, uint32_t rowAddr, const void *buf, uint32_t len, const void *uData, int uDataSize, int mode); void (*prepare_hook)(void *sni); void (*panic)(const char *fmt, void *sni); void (*checkrb_sem)(void *sni); void (*phy_special_init)(void *sni); void (*phy_special_ecc_err)(void *sni, const uint32_t errBits); } __attribute__ ((packed)); struct spinand_info { struct nand_info *spi; //protect is a lock for write/erase some sectors; protect=0: lock; protect=1: unlock. uint32_t protect; void *id_tbl; //bass data for spinand code rom. void *bss; } __attribute__ ((packed)); #ifndef CONFIG_SPINAND_LIB struct PhysicOpParameter { //Bank number uint8_t BankNum; //page number in physic block,the page is based on multi-plane if support uint16_t PageNum; //physic block number in bank,the physic block is based on multi-plane if support uint16_t PhyBlkNumInBank; //page sector bitmap uint32_t SectorBitmapInPage; //pointer to main data buffer void *MainDataPtr; //pointer to spare data buffer void *SpareDataPtr; } __attribute__ ((packed)); struct spinand_extra_api { uint32_t (*phy_read)(struct spinand_info *sni, struct PhysicOpParameter *OpPar); uint32_t (*phy_write)(struct spinand_info *sni, struct PhysicOpParameter *OpPar); uint32_t (*phy_erase)(struct spinand_info *sni, struct PhysicOpParameter *OpPar); int (*null)(struct spinand_info *sni); } __attribute__ ((packed)); struct spinand_operation_api { int (*init)(struct spinand_info *sni); uint32_t (*read_chipid)(struct spinand_info *sni); int (*read)(struct spinand_info *sni, uint32_t addr, void *buf, uint32_t len); int (*write)(struct spinand_info *sni, uint32_t addr, const void *buf, uint32_t len); int (*erase)(struct spinand_info *sni, uint32_t addr, uint32_t len); int (*flush)(struct spinand_info *sni); int (*flash_protect) (struct spinand_info *sni, uint32_t len); int (*spinand_pdl_init) (struct spinand_info *sni); uint8_t (*spinand_get_feature) (struct spinand_info *sni, uint8_t feature); uint8_t (*spinand_set_feature) (struct spinand_info *sni, uint8_t feature, uint8_t setting); uint8_t (*spinand_get_version) (struct spinand_info *sni, char *version); const struct spinand_extra_api *extra_api; } __attribute__ ((packed)); //spinand code rom api address #define SPINAND_API_ADDR 0x00007000 #define p_spinand_api ((struct spinand_operation_api *)SPINAND_API_ADDR) #else int spinand_pdl_init(struct spinand_info *sni); int spinand_init(struct spinand_info *sni); u32_t spinand_read_chipid(struct spinand_info *sni); int spinand_read(struct spinand_info *sni, u32_t addr, void *buf, u32_t len); int spinand_write(struct spinand_info *sni, u32_t addr, const void *buf, u32_t len); int spinand_erase(struct spinand_info *sni, u32_t addr, u32_t len); int spinand_flush(struct spinand_info *sni, bool efficient); int spinand_flash_protect(struct spinand_info *sni, u32_t len); uint8_t spinand_get_feature(struct spinand_info *sni, u8_t feature); void spinand_set_feature(struct spinand_info *sni, u8_t feature, u8_t setting); uint8_t *spinand_get_version(void); #ifdef CONFIG_SPINAND_TEST_FRAMEWORKS int spinand_get_delaychain(struct spinand_info *sni); int spinand_get_chipid(struct spinand_info *sni, u32_t *chipid); int get_storage_params(struct spinand_info *sni, u8_t *id, struct FlashChipInfo **ChipInfo); #endif #endif struct spinand_acts_config { struct acts_spi_controller *spi; uint32_t spiclk_reg; const char *dma_dev_name; uint8_t txdma_id; uint8_t txdma_chan; uint8_t rxdma_id; uint8_t rxdma_chan; uint8_t clock_id; uint8_t reset_id; uint8_t flag_use_dma:1; uint8_t delay_chain:7; }; #define DEV_CFG(dev) \ ((const struct spinand_acts_config *const)(dev)->config) #define DEV_DATA(dev) \ ((struct spinand_info *)(dev)->data)