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

📄 nf.c

📁 开发工具:keil7 主要IC:at89c51sdnd1(atmel) 说明:mp3播放器详细设计方案
💻 C
📖 第 1 页 / 共 4 页
字号:
/*F**************************************************************************
* NAME: nf_write_byte
*----------------------------------------------------------------------------
* PARAMS:
*   b: data to write
*
* RETURN:
*   write status: OK: write done
*                 KO: write not done
*
*----------------------------------------------------------------------------
* PURPOSE:
*   Low level memory write function
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
bit nf_write_byte (Byte b)
{
char pdata *ptr = gl_buffer;

  if (nf_busy)
  {
    nf_busy = FALSE;
    if (!gl_cpt_page) /* if we are at the beginning of a new page */
    {
      /* if there is a block change */
      if ( !(gl_ptr_mem & 0x1F) )                            
      { 
        /* If previous block have to de deleted */
        if (block_used)       
        {
          nf_block_erase((Uint32)(block_to_be_deleted) << 5);
        }
        /* increase the main buffer index */
        gl_buf_idx++;
        /* if zone change */
        if (gl_buf_idx >= block_max)
        {
          nf_write_open(gl_ptr_mem);
        }
        else
        {
          /* if the block in the buffer is already assign, then invert it with a spare block */
          if ( !(buf[gl_buf_idx].w & 0x8000))                 
          {                                                 
            if ((buf_free[gl_buf_free_idx] & 0x7FFF) == lut_block[nf_zone])
            {
              gl_buf_free_idx++;
              if (gl_buf_free_idx >= spare_block)
              {
                gl_buf_free_idx = 0;
              }      
            }        
            /* invert the block and assign the next block to be deleted */
            block_to_be_deleted = buf[gl_buf_idx].w;
            buf[gl_buf_idx].w = buf_free[gl_buf_free_idx] & 0x7FFF;
            buf_free[gl_buf_free_idx] = block_to_be_deleted | 0x8000;
            /* block have to be deleted */
            block_used = TRUE;
            /* increase the spare buffer index */
            if ((gl_buf_free_idx++) >= spare_block )
            {
              gl_buf_free_idx = 0;
            }
    
          }
          else /* The block is not assigned. Nothing to do */
          {
            buf[gl_buf_idx].w &= 0x7FFF;
            block_used = FALSE;
          }
          /* update the max index buffer */
          if (gl_buf_idx > gl_buf_idx_max)
            gl_buf_idx_max = gl_buf_idx;
    
          /* Update current physical sector */
          current_physical_sector_addr = (Uint32)(buf[gl_buf_idx].w) << 5;
          /* increase the logical block */
          logical_block++;
          /* calculate the redundant block address */
          nf_calc_logical_block();
        }
      }
      else  /* if there is no block change, we just need to continue write operation */
      {     /* on the next physical sector                                           */
        current_physical_sector_addr++;
      }
    }
  
  }



  Nf_CS_ON();

  /* Save data in gl_buffer */  
  gl_buffer[(gl_cpt_page & 0xFF)] = b;
  /* Increase internal page counter */
  gl_cpt_page++;                          
  if (gl_cpt_page == 256)                 /* First 256 bytes */
  {
    /* Open in write mode in A Area */
    Nf_wait_busy();
    Nf_send_command (NF_READ_A_AREA_CMD);
    Nf_send_command (NF_SEQUENTIAL_DATA_INPUT_CMD); /* Sequential data input Type Command */
    Nf_send_address ( 0x00 );                                       /* 1st address cycle*/
    Nf_send_address ( ((Byte*)&current_physical_sector_addr)[3] );  /* 2nd address cycle*/
    Nf_send_address ( ((Byte*)&current_physical_sector_addr)[2] );  /* 3rd address cycle*/
    if (NF_4_CYCLE_ADDRESS)                                       /* Size of card >= 64Mbytes ?*/
      Nf_send_address ( ((Byte*)&current_physical_sector_addr)[1] );/* 4th address cycle*/
    /* Copy the buffer */
    nf_download_buffer();
    Nf_send_command(NF_PAGE_PROGRAM_CMD);
    nf_busy = TRUE;    

  }
  else
    if (gl_cpt_page == NF_DATA_SIZE)        /* check if end of data page      */
    {
      /* Open in write mode in B Area */
      Nf_wait_busy();
      Nf_send_command (NF_READ_B_AREA_CMD);
      Nf_send_command (NF_SEQUENTIAL_DATA_INPUT_CMD); /* Sequential data input Type Command */
      Nf_send_address ( 0x00 );                                       /* 1st address cycle*/
      Nf_send_address ( ((Byte*)&current_physical_sector_addr)[3] );  /* 2nd address cycle*/
      Nf_send_address ( ((Byte*)&current_physical_sector_addr)[2] );  /* 3rd address cycle*/
      if (NF_4_CYCLE_ADDRESS)                                       /* Size of card >= 64Mbytes ?*/
        Nf_send_address ( ((Byte*)&current_physical_sector_addr)[1] );/* 4th address cycle*/
      /* Copy the buffer */
      nf_download_buffer();
      /* Update spare data */
      nf_update_spare_data();
      Nf_send_command(NF_PAGE_PROGRAM_CMD);
      nf_busy = TRUE;
      gl_ptr_mem++;
      gl_cpt_page = 0;      
    }

  return OK;

}


/*F**************************************************************************
* NAME: nf_write_sector
*----------------------------------------------------------------------------
* PARAMS:
*   global: gl_ptr_mem
*
* return:
*   write status: OK: write done
*                 KO: write not done
*----------------------------------------------------------------------------
* PURPOSE: 
*   This function is an optimized function that writes nb-sector * 512 bytes
*   from USB controller to NF card
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*   nb_sector always >= 1, can not be zero
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
bit nf_write_sector (Uint16 nb_sector)
{
Byte j;

  do
  {   
    if (nf_busy)
    {
      nf_busy = FALSE;
      /* if there is a block change */
      if ( !(gl_ptr_mem & 0x1F) )                            
      { 
        /* If previous block have to de deleted */
        if (block_used)       
        {
          nf_block_erase((Uint32)(block_to_be_deleted) << 5);
        }
        /* increase the main buffer index */
        gl_buf_idx++;
        /* if zone change */
        if (gl_buf_idx >= block_max)
        {
          nf_write_open(gl_ptr_mem);
        }
        else
        {
          /* if the block in the buffer is already assign, then invert it with a spare block */
          if ( !(buf[gl_buf_idx].w & 0x8000))                 
          {                                                 
            if ((buf_free[gl_buf_free_idx] & 0x7FFF) == lut_block[nf_zone])
            {
              gl_buf_free_idx++;
              if (gl_buf_free_idx >= spare_block)
              {
                gl_buf_free_idx = 0;
              }      
            }        
            /* invert the block and assign the next block to be deleted */
            block_to_be_deleted = buf[gl_buf_idx].w;
            buf[gl_buf_idx].w = buf_free[gl_buf_free_idx] & 0x7FFF;
            buf_free[gl_buf_free_idx] = block_to_be_deleted | 0x8000;
            /* block have to be deleted */
            block_used = TRUE;
            /* increase the spare buffer index */
            if ((gl_buf_free_idx++) >= spare_block )
            {
              gl_buf_free_idx = 0;
            }
          }
          else /* The block is not assigned. Nothing to do */
          {
            buf[gl_buf_idx].w &= 0x7FFF;
            block_used = FALSE;
          }
          /* update the max index buffer */
          if (gl_buf_idx > gl_buf_idx_max)
            gl_buf_idx_max = gl_buf_idx;
    
          /* Update current physical sector */
          current_physical_sector_addr = (Uint32)(buf[gl_buf_idx].w) << 5;
          /* increase the logical block */
          logical_block++;
          /* calculate the redundant block address */
          nf_calc_logical_block();
        }
      }
      else  /* if there is no block change, we just need to continue write operation */
      {     /* on the next physical sector                                           */
        current_physical_sector_addr++;
      }
    }
  
    Nf_CS_ON();
  
    /* Open media in write operation */
    Nf_wait_busy();
    Nf_send_command (NF_READ_A_AREA_CMD);
    Nf_send_command (NF_SEQUENTIAL_DATA_INPUT_CMD);                 /* Sequential data input Type Command */
    Nf_send_address ( 0x00 );                                       /* 1st address cycle*/
    Nf_send_address ( ((Byte*)&current_physical_sector_addr)[3] );  /* 2nd address cycle*/
    Nf_send_address ( ((Byte*)&current_physical_sector_addr)[2] );  /* 3rd address cycle*/
    if (NF_4_CYCLE_ADDRESS)                                                      /* Size of card >= 64Mbytes ?*/
      Nf_send_address ( ((Byte*)&current_physical_sector_addr)[1] );/* 4th address cycle*/
  
    for (j = 8; j != 0; j--)
    {
      while (!Usb_rx_complete());             /* wait end of reception */
      Nf_wr_byte(Usb_read_byte());            /* write 64 bytes to card */
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Nf_wr_byte(Usb_read_byte());
      Usb_clear_RXOUT_PP();                      /* usb read acknowledgement */
    }
  
    /* Update spare data */
    nf_update_spare_data();
  
    Nf_send_command (NF_PAGE_PROGRAM_CMD);
    /* increase gl_ptr_mem : next page */
    gl_ptr_mem++;              
    /* set flag busy */
    nf_busy = TRUE;
  
  
    Nf_wait_busy();
    nb_sector--;
  }
  while (  nb_sector != 0 );
  return OK;
}



/*F**************************************************************************
* NAME: nf_format
*----------------------------------------------------------------------------
* PARAMS:
*
* return:
*   Address of the format parameter structure in code
*----------------------------------------------------------------------------
* PURPOSE: 
*   This function is called by the fat_format function and returns a pointer
*   to a table containing the format parameters after erasing the NF.
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
s_format code * nf_format (void)
{

code  s_format  nf_tab_format[]=
  {
   /* nb_cylinder, nb_head,  nb_sector, nb_hidden, nb_sector_per_cluster */
    { (Uint16)500, (Byte)4,  (Byte)16,  (Byte)57,  (Byte)32 }, /* 16MB */
    { (Uint16)500, (Byte)8,  (Byte)16,  (Byte)51,  (Byte)32 }, /* 32MB */
    { (Uint16)500, (Byte)8,  (Byte)32,  (Byte)39,  (Byte)32 }, /* 64MB */
    { (Uint16)500, (Byte)16, (Byte)32,  (Byte)63,  (Byte)32 }, /* 128MB */
  };

  /* Erase all block */
  nf_erase_all_block();

  /* -- NF Type Selection -- */
  return &nf_tab_format[NF_TYPE];
}

⌨️ 快捷键说明

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