fmc控制nand flash無法讀寫?

2019-07-21 01:50发布

我是使用stm32f427透過fmc控制MT29F1G08ABAEAWP
目前可以讀到ID與ParameterID
但是我想要做讀寫的測試
要對某個page做抹寫再寫入再讀出
來判斷是否有問題

但是
無論我寫任何值
總是讀出0的值
不知道大俠是否有經驗

讀function
HAL_StatusTypeDef HAL_NAND_Read_Page(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, unsigned char *pBuffer, unsigned int NumPageToRead)
{
  unsigned int index  = 0;
  unsigned int deviceaddress = 0, size = 0, numpagesread = 0, addressstatus = NAND_VALID_ADDRESS;                                                                                                                   
  NAND_AddressTypeDef nandaddress;
  unsigned int addressoffset = 0;                                                                                                                                                                                   

  /* Process Locked */
  __HAL_LOCK(hnand);

  /* Check the NAND controller state */
  if(hnand->State == HAL_NAND_STATE_BUSY)                                                                                                                                                                           
  {                           
     return HAL_BUSY;
  }  

  /* Identify the device address */
  if(hnand->Init.NandBank == FMC_NAND_BANK2)                                                                                                                                                                        
  {    
    deviceaddress = NAND_DEVICE1;
  }    
  else
  {    
    deviceaddress = NAND_DEVICE2;
  }    

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_BUSY;                                                                                                                                                                               

  /* Save the content of pAddress as it will be modified */
  nandaddress.Block     = pAddress->Block;
  nandaddress.Page      = pAddress->age;
  nandaddress.Zone      = pAddress->Zone;
/* Page(s) read loop */
  while((NumPageToRead != 0) && (addressstatus == NAND_VALID_ADDRESS))
  {
    /* update the buffer size */
    size = hnand->Info.PageSize + ((hnand->Info.PageSize) * numpagesread);

    /* Get the address offset */
    addressoffset = ARRAY_ADDRESS(&nandaddress, hnand);

    /* Send read page command sequence */
    *(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;

    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x00;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x00;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x09;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x11;

 *(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA))  = NAND_CMD_AREA_TRUE1;

#if 1
    /* Read status until NAND is ready */
    unsigned int i = 0;
    printk("!!!!!!!!!!!!!!!! ");
    while(HAL_NAND_Read_Status(hnand) != NAND_READY)
    {
    //  if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
      if(i>NAND_WRITE_TIMEOUT)
      {
        return HAL_TIMEOUT;
      }
      i++;
    }
    printk("!!!!!!!!!!!!!!!! ");
#endif
    *(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = 0x00;

    //unsigned char data = 0;
    /* Get Data into Buffer */
    for(index = size; index != 0; index--)
    {
      *pBuffer++ = *(unsigned char *)deviceaddress;
      //pBuffer[index] = *(unsigned char *)deviceaddress;
      //data = *(unsigned char *)deviceaddress;
    //printk("!!!data = 0x%x ",data);
    }

 numpagesread++;

    /* Decrement pages to read */
    NumPageToRead--;

    /* Increment the NAND address */
    addressstatus = HAL_NAND_Address_Inc(hnand, &nandaddress);
  }

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_READY;

  /* Process unlocked */
  __HAL_UNLOCK(hnand);

  return HAL_OK;

}

寫function
HAL_StatusTypeDef HAL_NAND_Write_Page(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, unsigned char *pBuffer, unsigned int NumPageToWrite)
{
  unsigned int index   = 0;
  unsigned int tickstart = 0;
  unsigned int deviceaddress = 0 , size = 0, numpageswritten = 0, addressstatus = NAND_VALID_ADDRESS;
  NAND_AddressTypeDef nandaddress;
  unsigned int addressoffset = 0;

  /* Process Locked */
  __HAL_LOCK(hnand);

  /* Check the NAND controller state */
  if(hnand->State == HAL_NAND_STATE_BUSY)
  {
     return HAL_BUSY;
  }

  /* Identify the device address */
  if(hnand->Init.NandBank == FMC_NAND_BANK2)
  {
    deviceaddress = NAND_DEVICE1;
  }
  else
  {
    deviceaddress = NAND_DEVICE2;
  }

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_BUSY;

  /* Save the content of pAddress as it will be modified */
  nandaddress.Block     = pAddress->Block;
  nandaddress.Page      = pAddress->age;
  nandaddress.Zone      = pAddress->Zone;
/* Page(s) write loop */
  while((NumPageToWrite != 0) && (addressstatus == NAND_VALID_ADDRESS))
  {
    /* update the buffer size */
    size = hnand->Info.PageSize + ((hnand->Info.PageSize) * numpageswritten);

    /* Get the address offset */
    addressoffset = ARRAY_ADDRESS(&nandaddress, hnand);
    printk("addressoffset = 0x%x ",addressoffset);

    /* Send write page command sequence */
    //*(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
    *(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;

*(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;

    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x00;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x00;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x09;
    *(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x11;
    //*(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA+2)) = ADDR_1ST_CYCLE(addressoffset);
    //*(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA+3)) = ADDR_2ND_CYCLE(addressoffset);
    //*(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(addressoffset);

    /* for 512 and 1 GB devices, 4th cycle is required */
    if(hnand->Info.BlockNbr >= 1024)
    {
      //*(unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = ADDR_4TH_CYCLE(addressoffset);
    }

    /* Write data to memory */
    for(index = size; index != 0; index--)
    {
      *(unsigned char *)deviceaddress = *(unsigned char *)pBuffer++;
     //*(unsigned char *)deviceaddress = 0x25;
    }

    *(unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE_TRUE1;

    /* Get tick */
    //tickstart = HAL_GetTick();

#if 1
    /* Read status until NAND is ready */
    printk("@@@@@@@@@@@@@@@ ");
    unsigned int i = 0;
    while(HAL_NAND_Read_Status(hnand) != NAND_READY)
    {
    //  if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
      if(i>NAND_WRITE_TIMEOUT)
      {
        return HAL_TIMEOUT;
      }
      i++;
    }
    printk("@@@@@@@@@@@@@@@ ");

#endif
/* Increment written pages number */
    numpageswritten++;

    /* Decrement pages to write */
    NumPageToWrite--;

 /* Increment the NAND address */
    addressstatus = HAL_NAND_Address_Inc(hnand, &nandaddress);
  }

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_READY;

  /* Process unlocked */
  __HAL_UNLOCK(hnand);

  return HAL_OK;
}

erase function
HAL_StatusTypeDef HAL_NAND_Erase_Block(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, short block)
{
  unsigned int deviceaddress = 0;
  unsigned int tickstart = 0;

  /* Process Locked */
  __HAL_LOCK(hnand);

  /* Check the NAND controller state */
  if(hnand->State == HAL_NAND_STATE_BUSY)
  {
     return HAL_BUSY;
  }

  /* Identify the device address */
  if(hnand->Init.NandBank == FMC_NAND_BANK2)
  {
    deviceaddress = NAND_DEVICE1;
  }
  else
  {
    deviceaddress = NAND_DEVICE2;
  }

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_BUSY;

  unsigned char block1 = ((block&0x3)<<6);
  unsigned char block2 = (block>>2);
  printk("block1 = 0x%x, block2 = 0x%x ", block1, block2);
  /* Send Erase block command sequence */
  *( unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_ERASE0;

//  *( unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x09;
//  *( unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = 0x11;
  *( unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = block1;
  *( unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = block2;

if(hnand->Info.BlockNbr >= 1024)
  {
    //*( unsigned char *)((unsigned int)(deviceaddress | ADDR_AREA)) = ADDR_4TH_CYCLE(ARRAY_ADDRESS(pAddress, hnand));
  }

  *( unsigned char *)((unsigned int)(deviceaddress | CMD_AREA)) = NAND_CMD_ERASE1;

  /* Update the NAND controller state */
  hnand->State = HAL_NAND_STATE_READY;

  /* Get tick */
  //tickstart = HAL_GetTick();
  unsigned int i = 0;

  /* Read status until NAND is ready */
  printk("############## ");
  while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  {
    //if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
    if(i>NAND_WRITE_TIMEOUT)
    {
      /* Process unlocked */
      __HAL_UNLOCK(hnand);

      return HAL_TIMEOUT;
    }
    i++;
  }

  printk("############## ");
  /* Process unlocked */
  __HAL_UNLOCK(hnand);

  return HAL_OK;

}





友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。