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

📄 fat.c

📁 atmel at89c51snd1c mp3芯片方案源码
💻 C
📖 第 1 页 / 共 5 页
字号:
  return OK;
}


/*F**************************************************************************
* NAME: fat_fgetc
*----------------------------------------------------------------------------
* PARAMS:
*
* return:
*   byte read
*----------------------------------------------------------------------------
* PURPOSE:
*   Read one byte from file
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*   As this function is called very often it must be short and optimized
*   in execution time
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
Byte fat_fgetc (void)
{  
  if ((((Byte*)&fat_fclust_byte_count)[1] == 0x00) &&
      ((((Byte*)&fat_fclust_byte_count)[0] & fat_cluster_mask) == 0x00))
  {     
    /* extract if necessary the next cluster from the allocation list */
    if (fclusters[fat_fchain_index].number == fat_fchain_nb_clust)
    { /* new fragment */
      fat_fchain_index++;
      fat_fchain_nb_clust = 1;
      Hard_read_close();

      Hard_read_open(fat_ptr_data + ((Uint32)(fclusters[fat_fchain_index].cluster) * fat_cluster_size));
    }
    else
    { /* no new fragment */
      fat_fchain_nb_clust++;                /* one more cluster read */
    }
  }
  fat_fclust_byte_count++;                  /* one more byte read */
  return Hard_read_byte();
}




/*F**************************************************************************
* NAME: fat_feof
*----------------------------------------------------------------------------
* PARAMS:
*
* return:
*----------------------------------------------------------------------------
* PURPOSE:
*   Return the file end flag
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
bit fat_feof (void)
{
  if (fat_fchain_index >= fat_last_clust_index)
  {
    if (fat_open_mode == READ)
      return (fat_fclust_byte_count >= (Uint16)fat_cache.current.size.l);
    else
      return flag_end_disk_file;
  }
  else
  {
    return FALSE;
  }
}


/*F**************************************************************************
* NAME: fat_dseek
*----------------------------------------------------------------------------
* PARAMS:
*   offset: offset to current position in signed word value
*
* return:
*----------------------------------------------------------------------------
* PURPOSE:
*   Seek from the current position to a new offset computing relative 
*   poisition +/- scan size limited to a 16 bit offset
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*   We consider here that the seek size is minor to the cluster size !!!
*   if you want to do a more than a cluster seek, issue two successive 
*   dseek commands
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/ 
bit fat_dseek (Int16 offset)
{
Byte     nb_sect;                     /* number of sectors to seek */
Uint16   nb_byte;                     /* number of bytes to seek */
Uint16   target_cluster;              /* the cluster to reach */
Uint16   i;

  fat_dir_current_offs += offset;           /* Calculate the absolute byte pos */
  nb_sect = (Byte)((fat_dir_current_offs) / SECTOR_SIZE);
  fat_dir_current_sect = fat_dir_start_sect + nb_sect;
  nb_byte = (Uint16)((fat_dir_current_offs) % (SECTOR_SIZE * fat_cluster_size));
  fat_dclust_byte_count = nb_byte;
  nb_byte %= SECTOR_SIZE; 
  
  if (dir_is_root == FALSE)                 /* Sub-directory ? */
  {                                         /* Find the # cluster */
    target_cluster = (nb_sect / fat_cluster_size);
    fat_dchain_index = 0;
    fat_dchain_nb_clust = 0;
    for (i = 0; i <= target_cluster; i++)
    {
      if (dclusters[fat_dchain_index].number == fat_dchain_nb_clust)
      {
        fat_dchain_index++;                 /* next fragment */
        fat_dchain_nb_clust = 1;            /* reset the nb cluster in this new fragment */
      }
      else
      {
        fat_dchain_nb_clust++;              /* next contiguous cluster */
      }
    }
    /* update fat_dir_current_sect value */
    fat_dir_current_sect = (((Uint32)(dclusters[fat_dchain_index].cluster + fat_dchain_nb_clust - 1) * fat_cluster_size)
                           + fat_ptr_data + (nb_sect % fat_cluster_size));

    if (!fat_dclust_byte_count)
    {
      if ((target_cluster == 0) || (dclusters[fat_dchain_index].number == 1))  /* If seek is first directory byte, reset */
      {                                                           /* fat_dchain_nb_clust (see fat_dgetc())  */
        fat_dchain_nb_clust = 0;     
      } 
	}

  }

  Hard_read_close();

  if (Hard_read_open(fat_dir_current_sect) == OK)
  { /* seek in current sector */
    for (i = 0;  i < nb_byte; i += 2)
    {
      Hard_read_byte();                     /* dummy reads */
      Hard_read_byte();
    }


    return OK;
  }
  else
  {
    return KO;                              /* low level error */
  }
}


/*F**************************************************************************
* NAME: fat_dgetc
*----------------------------------------------------------------------------
* PARAMS:
*
* return:
*----------------------------------------------------------------------------
* PURPOSE:
*   Return the directory data byte at the current position
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/ 
Byte fat_dgetc (void)
{
  /* check if we are at the end of a cluster */
  if ((((Byte*)&fat_dclust_byte_count)[1] == 0x00) &&
      ((((Byte*)&fat_dclust_byte_count)[0] & fat_cluster_mask) == 0x00))
  {
    /* extract if necessary the next cluster from the allocation list */
    if (dclusters[fat_dchain_index].number == fat_dchain_nb_clust)
    { /* new fragment */
      fat_dchain_index++;
      fat_dchain_nb_clust = 1;
      Hard_read_close();
      Hard_read_open(fat_ptr_data + ((Uint32)(dclusters[fat_dchain_index].cluster) * fat_cluster_size));
      fat_dir_current_sect = fat_ptr_data + ((Uint32)(dclusters[fat_dchain_index].cluster) * fat_cluster_size);
    }
    else
    { /* no new fragment */
      fat_dir_current_sect = fat_ptr_data + ((Uint32)(dclusters[fat_dchain_index].cluster + fat_dchain_nb_clust) * fat_cluster_size);
      fat_dchain_nb_clust++;                /* one more cluster read */
    }
  }
  fat_dclust_byte_count++;                  /* one more byte read */
  return Hard_read_byte();
}


/*F**************************************************************************
* NAME: fat_fseek
*----------------------------------------------------------------------------
* PARAMS:
*   offset: relative signed seek offset in file
*
* return:
*   seek status:  - OK: seek done
*                 - KO: out of file seek
*----------------------------------------------------------------------------
* PURPOSE:
*   Change file pointer of an openned file
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*   In read mode, seek is done with byte boundary
*   In write mode, seek is done with sector boundary
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
bit fat_fseek (Int32 offset)
{
Uint32  file_pos;                           /* current position in file */
Uint16  cluster_offset;                     /* cluster offset in file */
Byte    sector_offset;                      /* sector offset in cluster */
#define i               sector_offset       /* local variable overlay */
#define byte_offset     cluster_offset      /* local variable overlay */

  /* init file pos with the current cluster in the index */
  if (fat_fchain_nb_clust != 0)
    file_pos = fat_fchain_nb_clust - 1;
  else
    file_pos = 0;
  /* Add the previous cluster number */
  for (i = 0; i != fat_fchain_index; i++)
  {
    file_pos += fclusters[i].number;
  }
  /* convert absolute cluster value in byte position */
  file_pos *= SECTOR_SIZE * fat_cluster_size; 

  if ((fat_fchain_nb_clust != 0) && ( fat_fclust_byte_count % (fat_cluster_size * SECTOR_SIZE) == 0))
  {
    file_pos += (fat_cluster_size * SECTOR_SIZE);
  }
  else
  {
    ((Byte*)&fat_fclust_byte_count)[0] &= fat_cluster_mask;
    file_pos += fat_fclust_byte_count;        /* offset in cluster */
  }

  /* Check range value */
  if (((file_pos + offset) < 0) ||
      ((file_pos + offset) > fat_cache.current.size.l))
  {
    return KO;                              /* out of file limits */
  }

  file_pos += offset;    /* new position */

  /* Calculate byte position in cluster */
  ((Byte*)&fat_fclust_byte_count)[1] = ((Byte*)&file_pos)[3];
  ((Byte*)&fat_fclust_byte_count)[0] = ((Byte*)&file_pos)[2];

  /* Calculate the absolute cluster position */
  cluster_offset = file_pos / (SECTOR_SIZE * fat_cluster_size);
  fat_fchain_index = 0;                     /* reset fragment number */

  /* Determinate the index for the chain cluster */
  while (cluster_offset >= fclusters[fat_fchain_index].number)
  {
    cluster_offset -= fclusters[fat_fchain_index].number;
    fat_fchain_index++;                     /* ome more fragment */
  }

  /* Determinate the cluster offset value for the selected index */
  fat_fchain_nb_clust = cluster_offset;

  /* Determinate the sector offset value in the selected cluster */
  sector_offset = (fat_fclust_byte_count  & ((fat_cluster_size * SECTOR_SIZE) - 1)) / SECTOR_SIZE;

  /* seek into sector */
  byte_offset = file_pos % SECTOR_SIZE;

  /* re-open file in read or write mode */
  if (fat_open_mode == READ)
  {
    Hard_read_close();                      /* close  reading */
    Hard_read_open(((Uint32)(fclusters[fat_fchain_index].cluster + fat_fchain_nb_clust) * fat_cluster_size)
                   + sector_offset + fat_ptr_data);
  
    if ((fat_fchain_nb_clust != 0) || (sector_offset != 0) || (byte_offset != 0))
    { /* if no offset, nb_clust incremented in fgetc() function */
      fat_fchain_nb_clust++;                /* one-based variable */
    }
    while (byte_offset != 0)
    {
      Hard_read_byte();                     /* dummy read */
      byte_offset--;
    }
  }

  return OK;
}



/*F**************************************************************************
* NAME: fat_fseek_abs
*----------------------------------------------------------------------------
* PARAMS:
*   offset: absolute seek offset in file
*
* return:
*----------------------------------------------------------------------------
* PURPOSE:
*   Move ahead file read pointer of an openned file
*----------------------------------------------------------------------------
* EXAMPLE:
*----------------------------------------------------------------------------
* NOTE:
*----------------------------------------------------------------------------
* REQUIREMENTS:
*****************************************************************************/
void fat_fseek_abs (Uint32 offset)
{
Byte    sector_offset;                      /* sector offset in cluster */
Uint16  cluster_offset;                     /* cluster offset in file */
#define i               sector_offset       /* local variable overlay */
#define byte_offset     cluster_offset      /* local variable overlay */

  /* Calculate byte position in cluster */
  ((Byte*)&fat_fclust_byte_count)[1] = ((Byte*)&offset)[3];
  ((Byte*)&fat_fclust_byte_count)[0] = (((Byte*)&offset)[2] & fat_cluster_mask);

  /* Calculate the absolute cluster position */
  cluster_offset = offset / (SECTOR_SIZE * fat_cluster_size);
  fat_fchain_index = 0;                     /* reset fragment number */

  /* Determinate the index for the chain cluster */
  while (cluster_offset > fclusters[fat_fchain_index].number)
  {
    cluster_offset -= fclusters[fat_fchain_index].number;
    fat_fchain_index++;                     /* ome more fragment */
  }
  /* Determinate the cluster offset value for the selected index */
  fat_fchain_nb_clust = cluster_offset;
  /* Determinate the sector offset value in the selected cluster */
  sector_offset = fat_fclust_byte_count / (SECTOR_SIZE);

  /* re-open file in read or write mode */
  if (fat_open_mode == READ)
  {
    Hard_read_close();                      /* close  reading */
    Hard_read_open(((Uint32)(fclusters[fat_fchain_index].clu

⌨️ 快捷键说明

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