微波EDA网,见证研发工程师的成长!
首页 > 硬件设计 > 嵌入式设计 > NANDFlashd的读写(基于s3c2440)

NANDFlashd的读写(基于s3c2440)

时间:11-20 来源:互联网 点击:

  1. tf("/r/nError:DetectNandBusytimeout!!!/r/n");
  2. rNFSTAT|=(1<2);//清忙标志
  3. return-1;//错误返回-1
  4. }
  5. }
  6. rNFSTAT|=(1<2);//清忙标志
  7. return1;
  8. }
  9. voidnand_reset(void)//NAND复位
  10. {
  11. rNFCMD=NAND_CMD_RES;
  12. detect_nand_busy();//检测忙
  13. }
  14. voidcontrol_start(void)//芯片开启
  15. {
  16. select_nand();
  17. controller_enable();
  18. rNFSTAT|=(1<2);//清忙标志
  19. nand_reset();
  20. }
  21. voidcontrol_end(void)//芯片关闭
  22. {
  23. dis_select_nand();
  24. controller_disable();
  25. }
  26. voidecc_main_init(void)//初始化ECC值
  27. {
  28. rNFCONT|=1<4;//initEcc
  29. }
  30. voidecc_main_start(void)//开锁mainECC
  31. {
  32. rNFCONT&=~(1<5);//unlock
  33. }
  34. voidecc_main_end(void)//锁定mainECC
  35. {
  36. rNFCONT|=1<5;//lock
  37. }
  38. voidecc_spare_start(void)//开锁spareECC
  39. {
  40. rNFCONT&=~(1<6);//unlock
  41. }
  42. voidecc_spare_end(void)//锁定spareECC
  43. {
  44. rNFCONT|=1<6;//lock
  45. }
  46. void__irqnandINT(void)//NAND中断函数
  47. {
  48. //此处写处理代码
  49. #ifdefNAND_DEBUG
  50. Uart_Printf("/r/nNandError...Ininterruptnow!!!");//只有错误才会进入中断
  51. #endif
  52. rSRCPND|=0x1
  53. rINTPND|=0x1
  54. }
  55. voidnand_read_id(void)//读取芯片ID信息
  56. {
  57. control_start();//开控制
  58. rNFCMD=NAND_CMD_READ_ID;
  59. rNFADDR=0;
  60. //读芯片ID
  61. nand_id.IDm=(U8)rNFDATA8;
  62. nand_id.IDd=(U8)rNFDATA8;
  63. nand_id.ID3rd=(U8)rNFDATA8;
  64. nand_id.ID4th=(U8)rNFDATA8;
  65. nand_id.ID5th=(U8)rNFDATA8;
  66. //打印ID信息
  67. #ifdefNAND_DEBUG
  68. Uart_Printf("/r/nReadNANDFlashID:");
  69. Uart_Printf("/r/nNANDMarkcode:0x%x",nand_id.IDm);
  70. Uart_Printf("/r/nNANDDevicecode:0x%x",nand_id.IDd);
  71. Uart_Printf("/r/nNAND3rdIDcode:0x%x",nand_id.ID3rd);
  72. Uart_Printf("/r/nNAND4thIDcode:0x%x",nand_id.ID4th);
  73. Uart_Printf("/r/nNAND5thIDcode:0x%x",nand_id.ID5th);
  74. #endif
  75. control_end();//关控制
  76. }
  77. //擦出时只要给定块所在页的地址,就能擦除整个块
  78. intnand_block_erase(U32num)//num要删除的块号
  79. {
  80. num=num*64;//每块的第一页
  81. control_start();//开控制
  82. nand_reset();//复位
  83. rNFCMD=NAND_CMD_BLOCK_ERASE_1st;
  84. rNFADDR=num&0xff;
  85. rNFADDR=(num>>8)&0xff;
  86. rNFADDR=(num>>16)&0xff;
  87. rNFCMD=NAND_CMD_BLOCK_ERASE_2st;
  88. detect_nand_busy();
  89. rNFCMD=NAND_CMD_READ_STATUS;//读状态
  90. if(rNFDATA8&1)//最低位可以判断擦除和写是否成功
  91. {
  92. #ifdefNAND_DEBUG
  93. Uart_Printf("/r/nError:nanderaseerror...block=0x%x",num/64);
  94. #endif
  95. control_end();//关控制
  96. nand_mask_bad_block(num/64);//登记为坏块
  97. return-1;//删除错误返回0
  98. }
  99. control_end();//关控制
  100. #ifdefNAND_DEBUG
  101. Uart_Printf("/r/nNANDblock%derasecompleted.",num/64);
  102. #endif
  103. return1;//擦除成功
  104. }
  105. intnand_page_write(U32addr,U8*buffer,U32size)//addr要写的起始页地址,buffer要写的缓存,size要写的字节大小最大为4G
  106. {
  107. U32i,n,p,temp,ecc;
  108. U8*bu;
  109. bu=buffer;
  110. temp=0;
  111. n=size/2048+(((size%2048)==0)?0:1);//计算出要写的页数,小于一页的部分当作一页
  112. for(i=0;i
  113. {
  114. control_start();//开控制
  115. nand_reset();//复位
  116. #ifdefUSE_ECC
  117. ecc_main_init();
  118. ecc_main_start();//可以产生main区ECC
  119. #endif
  120. rNFCMD=NAND_CMD_WRITE_PAGE_1st;
  121. rNFADDR=0;//从每页的0地址开始
  122. rNFADDR=0;//从每页的0地址开始
  123. rNFADDR=(addr)&0xff;
  124. rNFADDR=(addr>>8)&0xff;
  125. rNFADDR=(addr>>16)&0xff;
  126. for(p=0;p<2048;p++)//写入一页
  127. {
  128. temp=temp+1;
  129. if(temp>size)
  130. {
  131. rNFDATA8=0xff;//多余的填写0xff
  132. }
  133. else
  134. {
  135. rNFDATA8=*(bu+p);
  136. }
  137. }
  138. //delay_lhg(100,100);//
  139. #ifdefUSE_ECC
  140. ecc_main_end();//锁定main区ecc
  141. ecc=rNFMECC0;
  142. ecc_spare_start();//解锁spare区ECC
  143. //mainECC值写入备用区的头0~4个地址内
  144. rNFDATA8=ecc&0xff;
  145. rNFDATA8=(ecc>>8)&0xff;
  146. rNFDATA8=(ecc>>16)&0xff;
  147. rNFDATA8=(ecc>>24)&0xff;
  148. ecc_spare_end();//锁定spare区ECC
  149. //delay_lhg(100,100);//
  150. ecc=rNFSECC;//spareECC值写入备用区的5~6两个地址内
  151. rNFDATA8=ecc&0xff;
  152. rNFDATA8=(ecc>>8)&0xff;
  153. #endif
  154. bu=bu+2048;//页增量
  155. addr++;
  156. rNFCMD=NAND_CMD_WRITE_PAGE_2st;
  157. detect_nand_busy();//检测忙
  158. rNFCMD=NAND_CMD_READ_STATUS;//读状态
  159. if(rNFDATA8&1)
  160. {
  161. #ifdefNAND_DEBUG
  162. Uart_Printf("/r/nnandwritepageerror:pageaddr=0x%d",addr-1);//写入失败,以后改进
  163. #endif
  164. control_end();//关控制
  165. nand_mask_bad_block((addr-1)/64);//登记为坏块
  166. return-1;//写入错误返回-1
  167. }
  168. control_end();//关控制
  169. }
  170. return1;//成功返回1
  171. }
  172. intnand_page_read(U32addr,U8*buffer,U32size)//addr开始页地址,从每页00地址开始读,size为需要读的字节数
  173. {
  174. U32i,n,p,temp,ecc;
  175. U8*bu,no;
  176. bu=buffer;
  177. temp=0;
  178. n=size/2048+(((size%2048)==0)?0:1);//计算出要读的页数,小于一页的部分当

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top