⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 df.c

📁 ATMEL 90usb128 USB source,include USB protocol stack.
💻 C
📖 第 1 页 / 共 4 页
字号:
//!   The memory check failed -> KO
//!/
bit df_mem_check (void)
{
   //# DF memory check.
   for(df_select=0; df_select<DF_NB_MEM; df_select++)
   {
      df_chipselect_current();
      Spi_write_data(DF_RD_STATUS); /* Send the read status register cmd
                                       + 1st step to clear the SPIF bit */
      Spi_write_dummy();            /* dummy write that:
                                    (.) finalize the clear of the SPIF bit (access to SPDR)
                                    (.) get status register
                                    (.) does the 1st step to clear the SPIF bit  */
      /* Following Spi_read_data() finalize the clear of SPIF by accessing SPDR. */
      // Check the DF density.
      if ((Spi_read_data() & DF_MSK_DENSITY) != DF_DENSITY)
      {   // Unexpected value.
        Df_desel_all();
        return (KO);
      }
      Df_desel_all();
   }

   return OK;
}



//!
//! @brief This function waits until the DataFlash is not busy.
//!
//! @warning Code:?? bytes (function code length)
//!
//! @param  None
//!
//! @return None
//!/
static void df_wait_busy (void)
{
  // Read the status register until the DataFlash is not busy.
  df_chipselect_current();
  Spi_write_data(DF_RD_STATUS); /* Send the read status register cmd
                                   + 1st step to clear the SPIF bit */
  Spi_write_dummy();            /* dummy write that:
                                    (.) finalize the clear of the SPIF bit (access to SPDR)
                                    (.) get status register
                                    (.) does the 1st step to clear the SPIF bit */
  // Following Spi_read_data() finalize the clear of SPIF by accessing SPDR
  while ((Spi_read_data() & DF_MSK_BIT_BUSY) == DF_MEM_BUSY)
  {
    Spi_write_dummy();           /* dummy write to get new status
                                   + 1st step to clear the SPIF bit */
  }
  Df_desel_all();                /* unselect memory to leave STATUS request mode */
  Spi_ack_write();               /* Final step to clear the SPIF bit. */
}



//!
//! @brief This function opens a DF memory in read mode at a given sector address.
//!
//! NOTE: Address may not be synchronized on the beginning of a page (depending on the DF page size).
//!
//! @warning Code:?? bytes (function code length)
//!
//! @param  pos   Logical sector address
//!
//! @return bit
//!   The open succeeded      -> OK
//!/
bit df_read_open (Uint32 pos)
{
  // Set the global memory ptr at a Byte address.
  gl_ptr_mem = df_translate_addr(pos);

  // Select the DF that memory "pos" points to (the "df_select" variable will be updated)
  df_chipselect_memzone(LSB0(pos));

  // If the DF memory is busy, wait until it's not.
  if (is_df_busy(df_select))
  {
    df_release_busy(df_select);
    df_wait_busy();                              /* wait end of programming */
  }

  // Physically assert the selected dataflash
  df_chipselect_current();

  //#
  //# Initiate a page read at a given sector address.
  //#
  // Send read main command, + first step to clear the SPIF bit
  Spi_write_data(DF_RD_MAIN);
  // Final step to clear the SPIF bit will be done on the next write

  // Send the three address Bytes made of:
  //  (.) the page-address(first xbits),
  //  (.) the Byte-address within the page(last ybits).
  // (x and y depending on the DF type).
  // NOTE: the bits of gl_ptr_mem above the 24bits are not useful for the local
  // DF addressing. They are used for DF discrimination when there are several
  // DFs.
  Spi_write_data((MSB1(gl_ptr_mem) << DF_SHFT_B1) | (MSB2(gl_ptr_mem) >> DF_SHFT_B2));
  Spi_write_data(((MSB2(gl_ptr_mem) & ~DF_PAGE_MASK) << DF_SHFT_B1) | (MSB2(gl_ptr_mem) & DF_PAGE_MASK));
  Spi_write_data(MSB3(gl_ptr_mem));
  // Final step to clear the SPIF bit will be done on the next write

  // 4 dummy writes for reading delay
  Spi_write_data(0xFF);
  Spi_write_data(0xFF);
  Spi_write_data(0xFF);
  Spi_write_data(0xFF); /* Tx 0xFF, first step to clear the SPIF bit */
  Spi_ack_write();      /* Final step to clear the SPIF bit. */

  return OK;
}


//!
//! @brief This function unselects the current DF memory.
//!
//! @warning Code:?? bytes (function code length)
//!
//! @param  None
//!
//! @return None
//!/
void df_read_close (void)
{
  Df_desel_all();   /* Unselect memory */
}



//!
//! @brief This function is optimized and writes nb-sector * 512 Bytes from
//! DataFlash memory to USB controller
//!
//!         DATA FLOW is: DF => USB
//!
//!
//! NOTE:
//!   - First call must be preceded by a call to the df_read_open() function,
//!   - The USB EPIN must have been previously selected,
//!   - USB ping-pong buffers are free,
//!   - As 512 is always a sub-multiple of page size, there is no need to check
//!     page end for each Bytes,
//!   - Interrupts are disabled during transfer to avoid timer interrupt,
//!   - nb_sector always >= 1, cannot be zero.
//!
//! @warning code:?? bytes (function code length)
//!
//! @param nb_sector    number of contiguous sectors to read [IN]
//!
//! @return bit
//!   The read succeeded   -> OK
//!/
bit df_read_sector (Uint16 nb_sector)
{
   U8 i;
   do
   {
      for (i = 8; i != 0; i--)
      {
         Disable_interrupt();    // Global disable.

         // Principle: send any Byte to get a Byte.
         // Spi_write_dummy(): send any Byte + 1st step to clear the SPIF bit.
         // Spi_read_data(): get the Byte + final step to clear the SPIF bit.
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());
         Spi_write_dummy(); Usb_write_byte(Spi_read_data());

         //# Send the USB FIFO IN content to the USB Host.
         Usb_send_in();       // Send the FIFO IN content to the USB Host.

         Enable_interrupt();     // Global interrupt re-enable.

         // Wait until the tx is done so that we may write to the FIFO IN again.
         while(Is_usb_write_enabled()==FALSE);
      }
      gl_ptr_mem += 512;      // increment global address pointer
      nb_sector--;            // 1 more sector read
      #if (DF_NB_MEM == 1)    // end of page ?
         #if (DF_PAGE_SIZE == 512)
            Df_desel_all();
            if (nb_sector != 0)
              df_read_open(gl_ptr_mem>>9);
         #else
            if ((MSB2(gl_ptr_mem) & DF_PAGE_MASK) == 0x00)
            {
               Df_desel_all();
               if (nb_sector != 0)
                 df_read_open(gl_ptr_mem>>9);
            }
         #endif
      #endif
   }
   while (nb_sector != 0);

  return OK;   // Read done.
}


//!
//! @brief This function opens a DF memory in write mode at a given sector
//! address.
//!
//! NOTE: If page buffer > 512 bytes, page content is first loaded in buffer to
//! be partially updated by write_byte or write64 functions.
//!
//! @warning Code:?? bytes (function code length)
//!
//! @param  pos   Sector address
//!
//! @return bit
//!   The open succeeded      -> OK
//!/
bit df_write_open (Uint32 pos)
{
  // Set the global memory ptr at a Byte address.
  gl_ptr_mem = df_translate_addr(pos);

  // Select the DF that memory "pos" points to
  df_chipselect_memzone(LSB0(pos));

  // If the DF memory is busy, wait until it's not.
  if (is_df_busy(df_select))
  {
    df_release_busy(df_select);
    df_wait_busy();                              /* wait end of programming */
  }

#if DF_PAGE_SIZE > 512
  // Physically assert the selected dataflash
  df_chipselect_current();

  //#
  //# Transfer the current page content in buffer1.
  //#
  // Send Main Mem page to Buffer1 command, + first step to clear the SPIF bit
  Spi_write_data(DF_TF_BUF_1);
  // Final step to clear the SPIF bit will be done on the next write

  // Send the three address Bytes made of:
  //  (.) the page-address(first xbits),
  //  (.) remaining don't care bits(last ybits).
  // (x and y depending on the DF type).
  // NOTE: the bits of gl_ptr_mem above the 24bits are not useful for the local
  // DF addressing. They are used for DF discrimination when there are several
  // DFs.
  Spi_write_data((MSB1(gl_ptr_mem) << DF_SHFT_B1) | (MSB2(gl_ptr_mem) >> DF_SHFT_B2));
  Spi_write_data(MSB2(gl_ptr_mem) << DF_SHFT_B1);
  Spi_write_dummy();       // Remaining don't care bits.
  Spi_ack_write();         // Final step to clear the SPIF bit.

  Df_desel_all();          // Unselect memory to validate the command

  df_wait_busy();               // Wait end of page transfer
#endif

  // Physically assert the selected dataflash
  df_chipselect_current();

  //#
  //# Initiate a page write at a given sector address.
  //#
  // Send Main Memory Page Program Through Buffer1 command,
  // + first step to clear the SPIF bit
  Spi_write_data(DF_PG_BUF_1);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -