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

📄 fat.c

📁 嵌入式文件系统 EFSL 0.3.5 / 嵌入式文件系统 EFSL 0.3.5
💻 C
📖 第 1 页 / 共 2 页
字号:
/*****************************************************************************\*                     EFSL - Embedded Filesystems Library                     **                     -----------------------------------                     **                                                                             ** Filename : fat.c                                                            ** Release  : 0.3 - devel                                                      ** Description : This file contains all the functions dealing with the FAT     **               in a Microsoft FAT filesystem. It belongs under fs.c          **                                                                             ** This program is free software; you can redistribute it and/or               ** modify it under the terms of the GNU General Public License                 ** as published by the Free Software Foundation; version 2                     ** of the License.                                                             **                                                                             ** This program is distributed in the hope that it will be useful,             ** but WITHOUT ANY WARRANTY; without even the implied warranty of              ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the               ** GNU General Public License for more details.                                **                                                                             ** As a special exception, if other files instantiate templates or             ** use macros or inline functions from this file, or you compile this          ** file and link it with other works to produce a work based on this file,     ** this file does not by itself cause the resulting work to be covered         ** by the GNU General Public License. However the source code for this         ** file must still be made available in accordance with section (3) of         ** the GNU General Public License.                                             **                                                                             ** This exception does not invalidate any other reasons why a work based       ** on this file might be covered by the GNU General Public License.            **                                                                             **                                                    (c)2006 Lennart Yseboodt **                                                    (c)2006 Michael De Nil   *\*****************************************************************************//*****************************************************************************/#include "fs.h"/*****************************************************************************//* ****************************************************************************   * unsigned long fat_getSectorAddressFatEntry(FileSystem *fs,unsigned long cluster_addr) * Description: Returns the sectornumber that holds the fat entry for cluster cluster_addr. * This works for all FAT types. * Return value: Sectornumber, or 0. Warning, no boundary check.*/euint32 fat_getSectorAddressFatEntry(FileSystem *fs,euint32 cluster_addr){ 	euint32 base = fs->volumeId.ReservedSectorCount,res;		switch(fs->type){		case FAT12:			res=(cluster_addr*3/1024);			if(res>=fs->FatSectorCount){				return(0);			}else{				return(base+res);			}			break;		case FAT16:			res=cluster_addr/256;			if(res>=fs->FatSectorCount){				return(0);			}else{				return(base+res);			}			break;		case FAT32:			res=cluster_addr/128;			if(res>=fs->FatSectorCount){				return(0);			}else{				return(base+res);			}			break; 	}	return(0);}/*****************************************************************************/ /* ****************************************************************************   * unsigned long fat_getNextClusterAddress(FileSystem *fs,unsigned long cluster_addr * Description: This function loads the sector of the fat which contains the entry * for cluster_addr. It then fetches and (if required) calculates it's value. * This value is the EoC marker -or- the number of the next cluster in the chain. * Return value: Clusternumber or EoC*/euint32 fat_getNextClusterAddress(FileSystem *fs,euint32 cluster_addr,euint16 *linear){	euint8 *buf; 	euint8 hb,lb;	euint16 offset;	euint32 sector;	euint32 nextcluster=0;		sector=fat_getSectorAddressFatEntry(fs,cluster_addr);	if( (fs->FatSectorCount <= (sector-fs->volumeId.ReservedSectorCount)) || sector==0 )	{		return(0);	}		buf=part_getSect(fs->part,sector,IOM_MODE_READONLY);			switch(fs->type)	{		case FAT12:			offset = ((cluster_addr%1024)*3/2)%512;			hb = buf[offset];			if(offset == 511){				part_relSect(fs->part,buf);				buf=part_getSect(fs->part,sector+1,IOM_MODE_READONLY);				lb = buf[0];			}else{				lb = buf[offset + 1];			}			if(cluster_addr%2==0){				nextcluster = ( ((lb&0x0F)<<8) + (hb) );			}else{				nextcluster = ( (lb<<4) + (hb>>4) );			}			break;		case FAT16:			offset=cluster_addr%256;			nextcluster = *((euint16 *)buf + offset);			break;		case FAT32:			offset=cluster_addr%128;			nextcluster = *((euint32 *)buf + offset);			break;	}		part_relSect(fs->part,buf);		return(nextcluster);}/*****************************************************************************/ /* ****************************************************************************   * void fat_setNextClusterAddress(FileSystem *fs,unsigned long cluster_addr,unsigned long next_cluster_addr) * Description: This function makes an entry in the fattable for cluster_addr. The value it puts there * is next_cluster_addr. */void fat_setNextClusterAddress(FileSystem *fs,euint32 cluster_addr,euint32 next_cluster_addr){	euint8 *buf,*buf2; 	euint16 offset;	euint32 sector;		sector=fat_getSectorAddressFatEntry(fs,cluster_addr);	if(fs->FatSectorCount<sector){		DBG((TXT("HARDERROR:::fat_getNextClusterAddress READ PAST FAT BOUNDARY\n")));		return;	}		buf=part_getSect(fs->part,sector,IOM_MODE_READWRITE);			switch(fs->type){		case FAT12:			offset = ((cluster_addr%1024)*3/2)%512;			if(offset == 511){				if(cluster_addr%2==0){					buf[offset]=next_cluster_addr&0xFF;				}else{					buf[offset]=(buf[offset]&0xF)+((next_cluster_addr<<4)&0xF0);				}				buf2=part_getSect(fs->part,fat_getSectorAddressFatEntry(fs,cluster_addr)+1,IOM_MODE_READWRITE);				if(cluster_addr%2==0){					buf2[0]=(buf2[0]&0xF0)+((next_cluster_addr>>8)&0xF);				}else{					buf2[0]=(next_cluster_addr>>4)&0xFF;				}				part_relSect(fs->part,buf2);			}else{				if(cluster_addr%2==0){					buf[offset]=next_cluster_addr&0xFF;					buf[offset+1]=(buf[offset+1]&0xF0)+((next_cluster_addr>>8)&0xF);				}else{					buf[offset]=(buf[offset]&0xF)+((next_cluster_addr<<4)&0xF0);					buf[offset+1]=(next_cluster_addr>>4)&0xFF;				}			}			part_relSect(fs->part,buf);			break;		case FAT16:			offset=cluster_addr%256;			*((euint16*)buf+offset)=next_cluster_addr;			part_relSect(fs->part,buf);			break;		case FAT32:			offset=cluster_addr%128;			*((euint32*)buf+offset)=next_cluster_addr;			part_relSect(fs->part,buf);			break;	}	}/*****************************************************************************/ /* ****************************************************************************   * short fat_isEocMarker(FileSystem *fs,unsigned long fat_entry) * Description: Checks if a certain value is the EoC marker for the filesystem * noted in fs->type. * Return value: Returns 0 when it is the EoC marker, and 1 otherwise.*/eint16 fat_isEocMarker(FileSystem *fs,euint32 fat_entry){	switch(fs->type){		case FAT12:			if(fat_entry<0xFF8){				return(0);			}			break;		case FAT16:			if(fat_entry<0xFFF8){				return(0);			}			break;		case FAT32:			if((fat_entry&0x0FFFFFFF)<0xFFFFFF8){				return(0);			}			break;	}	return(1);}/*****************************************************************************/ /* ****************************************************************************   * unsigned long fat_giveEocMarker(FileSystem *fs) * Description: Returns an EoC markernumber valid for the filesystem noted in * fs->type. * Note, for FAT32, the upper 4 bits are set to zero, although they should be un * touched according to MicroSoft specifications. I didn't care. * Return value: The EoC marker cast to an ulong.*/euint32 fat_giveEocMarker(FileSystem *fs){	switch(fs->type)	{		case FAT12:			return(0xFFF);			break;		case FAT16:			return(0xFFFF);			break;		case FAT32:			return(0x0FFFFFFF);			break;	}	return(0);}/*****************************************************************************/ /* ****************************************************************************   * euint32 fat_getNextClusterAddressWBuf(FileSystem *fs,euint32 cluster_addr, euint8* buf) * Description: This function retrieves the contents of a FAT field. It does not fetch * it's own buffer, it is given as a parameter. (ioman makes this function rather obsolete) * Only in the case of a FAT12 crosssector data entry a sector is retrieved here. * Return value: The value of the clusterfield is returned.*/euint32 fat_getNextClusterAddressWBuf(FileSystem *fs,euint32 cluster_addr, euint8* buf){	euint8  *buf2; /* For FAT12 fallover only */	euint8 hb,lb;	euint16 offset;	euint32 nextcluster=0;		switch(fs->type)	{		case FAT12:			offset = ((cluster_addr%1024)*3/2)%512;			hb = buf[offset];			if(offset == 511){				buf2=part_getSect(fs->part,fat_getSectorAddressFatEntry(fs,cluster_addr)+1,IOM_MODE_READONLY);				lb = buf2[0];

⌨️ 快捷键说明

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