حافظه nand flash

سلام من با آی سی حافظه SPI NAND Flash شرکت ALLIANCE دارم کار میکنم ولی هر کاری میکنم نمیتونم درست بنویسم و بخونم و دیتا ذخیره نمیشه این مدل AS5F38G04SND هشت گیگا بیت هست ادرس هم چک کردم ولی درست نشد لطفا راهنمایی کنید ممنون

سلام دوست عزیز
مشکل از خط 77 برنامت هست.

خارج از شوخی: دست کم برنامت رو میزاشتی تا ببینیم چیکار کردی!
یا سخت افزار رو میزاشتی ببینیم اون رو چیکار کردی!

دیتاشیتش رو نگاه انداختم چیز خاصی نداره تقریبا شبیه به فلش های سری w25qxx هست.
در چه حالتی باهاش ارتباط گرفتی؟
spi یا quadSpi ؟

اگر دیتاشیتش رو نگاه بندازی نحوه راه اندازش رو توضیح داده و چند نکته هم داره:
1- همیشه موقع خواندن و نوشتن حداقل به اندازه یک page انجام بده
2- همیشه موقع نوشتن اول کل اون صفحه (page) که میخوای روش بنویسی رو کامل پاک کن بعد بنویس
3- نکته: دیتاشیتش رو ببین تا متوجه بشی پاک کردن به چه شکلیه مثلا باید همش رو 0x00 بنویسی یا 0xFF یا اینکه یه دستور خاصی داره که خودش این کار رو میکنه (معولا یه دستور خاص داره)

اگر هر کدوم از 3 مورد بالارو رعایت نکنی نمیتونی محتویات درستی رو بنویسی و بخونی

3 پسندیده

عذر خواهی میکنم من از ارتباط spi استفاده میکنم و پایه wp و hold را به vcc متصل کردم.برنامه به این صورت هست:

void AS5F38G04SND::init(int FLASH_SS){
  pinMode(FLASH_SS, OUTPUT);
  digitalWrite(FLASH_SS, HIGH);
  _FLASH_SS = FLASH_SS;
  SPI.begin();
  SPI.setBitOrder(MSBFIRST);
  SPI.setDataMode(SPI_MODE3);
}

byte AS5F38G04SND::read(unsigned int page,byte pageAddress){
  
  digitalWrite(_FLASH_SS, LOW);
  SPI.transfer(READ_DATA);//03H
  SPI.transfer((page >> 8) & 0xFF);
  SPI.transfer((page >> 0) & 0xFF);
  SPI.transfer(0x00);
  SPI.transfer(pageAddress);
  byte val = SPI.transfer(0);
  digitalWrite(_FLASH_SS, HIGH);
  return val;
}

void AS5F38G04SND::write(unsigned int page,byte pageAddress, byte val){

  writeEnable();//06H
  digitalWrite(_FLASH_SS, LOW);
  SPI.transfer(PAGE_PROGRAM);//02H
  SPI.transfer((page >> 8) & 0xFF);
  SPI.transfer((page >> 0) & 0xFF);
  SPI.transfer(pageAddress);
  SPI.transfer(val);
  digitalWrite(_FLASH_SS, HIGH);
  writeDisable();//04H
}

void AS5F38G04SND::chipErase(unsigned int page) {
  writeEnable();
  digitalWrite(_FLASH_SS, LOW);
  SPI.transfer(CHIP_ERASE);
  SPI.transfer((page >> 16) & 0xFF);
  SPI.transfer((page >> 8) & 0xFF);
  SPI.transfer((page >> 0)  & 0xFF);
  digitalWrite(_FLASH_SS, HIGH);
  writeDisable();
}
-------------------------------------------------------------
AS5F38G04SND flash;
const int Cs1 = 10;

void setup(){
  Serial.begin(9600);
  delay(1000);
  Serial.println("Setup Run");

  AS5F38G04SND_init();
  
  AS5F38G04SND_test();
  
  Serial.println("Loop Run");
}

void loop() {}

void AS5F38G04SND_init(){
  pinMode(Cs1, OUTPUT);
  digitalWrite(Cs1, HIGH);
}

void AS5F38G04SND_test() {
  
  flash.init(Cs1);
  uint32_t j = 0,y = 0;//page
  uint32_t i[] = {20,21};//pageaddress
  uint32_t val1 = 32,val2 = 35;//value

  flash.chipErase(0);
  flash.write(j,i[0],val1);
  Serial.print(j);
  Serial.print(",");
  Serial.print(i[0]);
  Serial.print(": ");
  Serial.println(flash.read(j,i[0]));
  
  flash.write(y,i[1],val2);
  Serial.print(y);
  Serial.print(",");
  Serial.print(i[1]);
  Serial.print(": ");
  Serial.println(flash.read(y,i[1]));
  Serial.println(flash.read(j,i[0]));
  Serial.println(flash.read(y,i[1]));

سلام وقت بخیر بنده همین مواردی که فرمودین اعمال کردم ولی باز هم نتیجه نداشت(طبق کدی که در پاسخ قبلی ارسال کردم) و خیلی هم روش کار کردم به نظرتون مشکل از کجا میتونه باشه؟

سلام دوست عزیز
توی بررسی کد بقیه وقتی به همه برنامه دسترسی ندارم زیاد کارم خوب نیست.
از طرفی هم زمان ندارم که ازت بخوام کل برنامه رو آپلود کنی و بررسیش کنم.
با این حال:
در تابع زیر:

چرا دستور :

  writeEnable();//06H

قبل از :

  digitalWrite(_FLASH_SS, LOW);

اومده؟

اگر دستور

 digitalWrite(_FLASH_SS, LOW);

کارش تنظیم پین CS هست باید قبل از برقراری ارتباط تنظیم لازم روش انجام بشه.


به ترتیب زیر یکبار عمل کن:
اول پین CS رو تنظیم کن (زمین کن یا low کن) بعد مقادیر زیر رو به ترتیب بفرست:

06H
9FH

بعدم مورد زیر رو تست کن:

06H
9FH
00H

ببین چه جوابی میگیری. جواب رو بزار تا ببینم

نکته: اگر از STM32 داری استفاده میکنی بهتره از قابلیت DMA بدون اینتراپت استفاده کنی و بصورت دستی delay حدود 5 ثانیه بزار و کلش رو داخل while(1) اصلی تابع main() قرار بدی.
رشته ای که میخوای برای ارسال دستور و رشته ای که میخوای برای دریافت پاسخ در دستور DMA بخش SPI استفاده کنی رو خارج از تابع main() تعریف کن تا global باشه و در زمان دیباگ کردن بهش دسترسی کامل داشته باشی
بعد در محیط دیباگ ببین دقیقا چی داره میفرسته و چی پاسخ میگیری

1 پسندیده

وقت شما بخیر مهندس.من با خواندن Device ID مشکلی ندارم راحت 2D دریافت میکنم مشکل از خواندن و نوشتن صفحه هست که مثلا اگر دو بار مینویسم (مثل کدی که فرستادم) تو page 0 و pageAddress 10 page 0 /pageAddress 11 وقتی رشته اولی دوباره میخونم رشته جدید (دومی) رو میخونه و قبلی حذف میکنه.در ضمن وقتی تابع write کامنت میکنم حافظه رو از برق میکشم حافظه رو میخونم پاک میشه و عدد 255 میده که نشون میده رشته داخل حافظه با قطع برق نمیمونه!

این رو تست کردی؟
چرا دستور :

  writeEnable();//06H

قبل از :

  digitalWrite(_FLASH_SS, LOW);

اومده؟


دستور

writeEnable();

رو بزار بعد از

  digitalWrite(_FLASH_SS, LOW);

و دستور

writeDisable();

رو بزار قبل از

digitalWrite(_FLASH_SS, HIGH);
1 پسندیده

بله تاثیری نداشت من قبلا جا به جا کرده بودم که شاید فرجی بشه!