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

📄 fat16.c

📁 实现 32M的MP3+U盘的循环播放功能的原程序
💻 C
字号:
/*
* Copyright (c) 2004,北京博创兴业科技有限公司
* All rights reserved.
* 
* 文件名称:fat16.c
* 文件标识:fat16
* 摘    要:fat操作的函数实现
* 
* 当前版本:2.0
* 作    者:Kent
* 完成日期:2004年5月20日
*
* 取代版本:1.1 
* 原作者  :Frank
* 完成日期:2003年8月10日
*/
#include "Fat16.h"
#include "Flash.h"
#include "uart.h"
#include "string.h"

//数据结构与全局变量定义
extern unsigned char Page_Buf[];
extern unsigned char SONG[];

long int Current_Cluster, DataRead = 0, DataRemain = 0, Sector_Offset = 0x21d;


unsigned int TotalCluster, BootSector, RsdSector, SectorofFatSize, TotalCapacity, RootEntry, SecPerClus, TotalSector, BytesPerSec, FirstDataSec;
unsigned char FAT_TYPE; 

void Init_FAT_Info(void)
{
	//int i;

	///////////////////////////////////////////////////
	//得到引导扇区所在扇区号,如果介质是不带分区的,则0扇区就是BootSector了。
	ReadPage(Begin_Cluster, 0, Page_Buf);

	if (!(Page_Buf[0] == 0xeb && Page_Buf[2] == 0x90))
	{	//通过判断EB ?? 90来看是否已经是BPB了
		//带分区的介质
		BootSector = Page_Buf[454] + Page_Buf[455] * 256 + Page_Buf[456] * (256 * 256) + Page_Buf[457] * (256 * 256 * 256);
	}
	else 
	{
		BootSector = 0;
	}
	///////////////////////////////////////////////////

	////////////////////////////////////////////////
	//得到保留扇区数,总扇区数,总扇区数/每簇扇区数得到簇数,是FAT类型的依据
	ReadPage(Begin_Cluster, BootSector, Page_Buf);
	RsdSector = Page_Buf[14] + Page_Buf[15] * 256;
	SecPerClus = Page_Buf[13];

	BytesPerSec = Page_Buf[12] * 256 + Page_Buf[11];

	TotalSector = (Page_Buf[20] * 256 + Page_Buf[19]);
	TotalCapacity = TotalSector * BytesPerSec;
	TotalCluster = TotalSector / SecPerClus;//FAT16的簇总数=扇区总数/每簇扇区数

	SectorofFatSize = ((Page_Buf[22] + Page_Buf[23] * 256));
	RootEntry = (Page_Buf[18] * 256 + Page_Buf[17]);
 
	FirstDataSec = BootSector + RsdSector + (SectorofFatSize * 2) + ((RootEntry * 32 + (BytesPerSec-1)) / BytesPerSec);

	if (TotalCluster > 65525)
	{  //FAT32的扇区总数和FAT表项长度
		FAT_TYPE = FAT32;

		if (TotalSector == 0) 
		{
			TotalSector = (Page_Buf[32] + Page_Buf[33] * 256 + Page_Buf[34] * 256 * 256 + Page_Buf[35] * 256 * 256 * 256);
		}
		TotalCapacity = TotalSector * BytesPerSec;
		TotalCluster = TotalSector / SecPerClus;

		SectorofFatSize = (Page_Buf[36] + Page_Buf[37] * 256 + Page_Buf[38] * 256 * 256 + Page_Buf[39] * 256 * 256 * 256);
		if (SectorofFatSize > (TotalCluster * 16 / 512))
		{
			SectorofFatSize = ((Page_Buf[22] + Page_Buf[23] * 256));
		}
		RootEntry = (Page_Buf[44] * 256 + Page_Buf[43]);
		FirstDataSec = BootSector+RsdSector + (SectorofFatSize * 2) + ((RootEntry * 32 + (BytesPerSec-1)) / BytesPerSec);
		
	}
	else if ((TotalCluster > 0) && (TotalCluster < 4085)) 
	{//FAT12
		FAT_TYPE = FAT12;
	}
	else
	{	//FAT16
		FAT_TYPE = FAT16;
	}
	printuf("\nFAT : %x", SectorofFatSize >> 8);
	printuf("%x\n", SectorofFatSize & 0xff);
	printuf("\nDATA : %x", FirstDataSec >> 8);
	printuf("%x\n", FirstDataSec & 0xff);
}

unsigned char GetMP3List(void)
{
	unsigned char i = 0, j = 0, l = 0;
	int k = 0;
	unsigned char MP3[3] = {'M', 'P', '3'};
	Init_FAT_Info();

	k = BootSector + RsdSector + 2 * SectorofFatSize;
	printuf("BootSector : %x", BootSector);
	printuf("RsdSector : %x", RsdSector);
	printuf("SectorofFatSize : %x", SectorofFatSize);

	printuf("RootDIR : %x", (k & 0xff00) >> 8);
	printuf("%x\n", k);

	ReadPage(0 + k / 32, k % 32, Page_Buf);
 
	while (Page_Buf[0] != 0)
	{//遍历整个目录
		for (j=0; j<16; j++)
		{
			if (!Page_Buf[j * 32]) break;
			if (Page_Buf[j * 32] == 0xE5) continue;

			if (!memcmp(MP3, &Page_Buf[j * 32 + 8], 3))
			{	//file find
					for (i=0; i<11; i++) 
					{
						SONG[l * 11 + i] = Page_Buf[j * 32 + i];
					}
					l++;
			}
		}
		k++;
		ReadPage(0 + k / 32, k % 32, Page_Buf);
	}
	return (l);
}
int ReadSector(unsigned char *Name, unsigned char *databuff)
{
	int i, k, Page;
	unsigned  long CurrentSector;
	if (DataRead == 0) //第一次读取,先查找文件,然后进行读取
		{
			Page = BootSector + RsdSector + 2 * SectorofFatSize;
			ReadPage(0 + Page / 32, Page % 32, databuff);
			while (databuff[0] != 0)
			{//遍历整个目录
				for (i=0; i<16; i++)
				{
					if (!memcmp(Name, &databuff[i * 32], 11))
					{
						Current_Cluster = databuff[32 * i + 27] * 256 + databuff[32 * i + 26];
						printuf("Current_Cluster : %x", (Current_Cluster & 0xff00) >> 8);
						printuf("%x\n", Current_Cluster);
						for (k=31; k>27; k--) 
						{
							DataRemain = (DataRemain << 8) | databuff[i * 32 + k];
						}
								//ReadPage((Current_Cluster+Sector_Offset)/32,(Current_Cluster+Sector_Offset)%32,databuff);
								
						CurrentSector = (Current_Cluster - 2) * SecPerClus + FirstDataSec;
						ReadPage(CurrentSector / 32, CurrentSector % 32, databuff);
								
						DataRead += 512;
						DataRemain -= 512;
						if (DataRemain < 0) 
						{
							DataRead = 0;
							return (DataRemain + 512);
						}
						else
						{
							return (512);
						}
					}
				}
				Page++;
				ReadPage(0 + Page / 32, Page % 32, databuff);
		  }
		  printu("\nfile is not found!");
		  return (0);
		}
	else
		{
//			if((Current_Cluster+Sector_Offset+DataRead/BytesPerSec)%32) Current_Cluster=NextCluster(Current_Cluster);
//			ReadPage((Current_Cluster+Sector_Offset)/32,(Current_Cluster+Sector_Offset+DataRead/BytesPerSec)%32,databuff);
			Current_Cluster++;
			CurrentSector = (Current_Cluster - 2) * SecPerClus + FirstDataSec;
			ReadPage(CurrentSector / 32, CurrentSector % 32, databuff);

			DataRead += 512;
//			if(!((Current_Cluster+Sector_Offset+DataRead/BytesPerSec)%32)) Current_Cluster=NextCluster(Current_Cluster+32);
//			if(!((Current_Cluster+Sector_Offset+DataRead/BytesPerSec)%32)) Current_Cluster+=32;//默认歌曲文件是顺序存放的。
			DataRemain -= 512;
			if (DataRemain < 0) 
			{
				DataRead = 0;
				return (DataRemain + 512);
			}
			else return (512);
		}

}

unsigned int NextCluster(unsigned int CurrentCluster)
{
	unsigned int i, j;
	if (FAT_TYPE == FAT12)
	{
		ReadPage(Begin_Cluster + (BootSector + RsdSector + (CurrentCluster * 3 / 2) / BytesPerSec) / SecPerClus, 
		(BootSector + RsdSector + (CurrentCluster * 3 / 2) / BytesPerSec) % SecPerClus, Page_Buf);
		if (CurrentCluster % 2 == 0)
		{
			j = Page_Buf[(CurrentCluster * 3 / 2) % BytesPerSec + 1];
			i = Page_Buf[(CurrentCluster * 3 / 2) % BytesPerSec] | (j << 8);
			i &= 0x0fff;
		}
		else 
		{
			j = Page_Buf[(CurrentCluster * 3 / 2) % BytesPerSec + 1];
			i = Page_Buf[(CurrentCluster * 3 / 2) % BytesPerSec] | (j << 8);
			i = (i >> 4);
		}
		return (i);
	}
	else if (FAT_TYPE == FAT16)
	{
		ReadPage(Begin_Cluster + (BootSector+RsdSector + (CurrentCluster * 2) / BytesPerSec) / 32,
		(BootSector + RsdSector + (CurrentCluster * 2) / BytesPerSec) % 32, Page_Buf);
		i = Page_Buf[(CurrentCluster * 2) % BytesPerSec + 1] * 256 + Page_Buf[(CurrentCluster * 2) % BytesPerSec];
		return (i);
	}
	else if (FAT_TYPE == FAT32)
	{
		ReadPage(Begin_Cluster + (BootSector+RsdSector + (CurrentCluster * 4) / BytesPerSec) / SecPerClus, (BootSector + RsdSector + (CurrentCluster * 4) / BytesPerSec) % SecPerClus, Page_Buf);
		i = Page_Buf[(CurrentCluster * 4) % BytesPerSec + 3] * 256 * 256 * 256 + Page_Buf[(CurrentCluster * 4) % BytesPerSec + 2] 
			* 256 * 256 + Page_Buf[(CurrentCluster * 4) % BytesPerSec + 1] * 256 + Page_Buf[(CurrentCluster * 4) % BytesPerSec];
		return (i);
	}
}




⌨️ 快捷键说明

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