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

📄 fatlite.c

📁 VxWorks BSP框架源代码包含头文件和驱动
💻 C
📖 第 1 页 / 共 5 页
字号:
/*----------------------------------------------------------------------*//*		        m o u n t V o l u m e				*//*									*//* Mounts the Flash volume.						*//*									*//* In case the inserted volume has changed, or on the first access to   *//* the file system, it should be mounted before file operations can be  *//* done on it.								*//* Mounting a volume has the effect of discarding all open files (the   *//* files cannot be properly closed since the original volume is gone),  *//* and turning off the media-change indication to allow file processing *//* calls.								*//*									*//* The volume automatically becomes unmounted if it is removed or       *//* changed.								*//*                                                                      *//* Parameters:                                                          *//*	vol		: Pointer identifying drive			*//*                                                                      *//* Returns:                                                             *//*	FLStatus	: 0 on success, otherwise failed                *//*----------------------------------------------------------------------*/static FLStatus mountVolume(Volume vol){  SectorNo noOfSectors;  PartitionTable FAR0 *partitionTable;  DOSBootSector FAR0 *bootSector;  checkStatus(dismountVolume(&vol));  checkStatus(flMount(&vol - vols,&vol.tl,&vol.flash)); /* Try to mount translation layer */  /* Read in paritition table */  partitionTable = (PartitionTable FAR0 *) findSector(&vol,0);  if(partitionTable == NULL)    return flSectorNotFound;  /* *BUG* *BUG* Doesn't work if SECTOR_SIZE < 512 */  if (LE2(partitionTable->signature) == PARTITION_SIGNATURE &&      partitionTable->type != 0)    vol.bootSectorNo =	(unsigned) UNAL4(partitionTable->startingSectorOfPartition);  else    vol.bootSectorNo = 0;	/* If partition table is undetected,				   assume sector 0 is DOS boot block */  vol.firstFATSectorNo = vol.secondFATSectorNo = 0; /* Disable FAT monitoring */  vol.flags |= VOLUME_ABS_MOUNTED;  /* Enough to do abs operations */  bootSector = (DOSBootSector FAR0 *) findSector(&vol,vol.bootSectorNo);  if(bootSector == NULL)    return flSectorNotFound;  /* Do the customary sanity checks */  if (!(bootSector->bpb.jumpInstruction[0] == 0xe9 ||	(bootSector->bpb.jumpInstruction[0] == 0xeb &&	 bootSector->bpb.jumpInstruction[2] == 0x90))) {  #ifdef DEBUG_PRINT    DEBUG_PRINT("Debug: did not recognize format.\n");  #endif    return flNonFATformat;  }  /* See if we handle this sector size */  if (UNAL2(bootSector->bpb.bytesPerSector) != SECTOR_SIZE)    return flFormatNotSupported;  vol.sectorsPerCluster = bootSector->bpb.sectorsPerCluster;  vol.numberOfFATS = bootSector->bpb.noOfFATS;  vol.sectorsPerFAT = LE2(bootSector->bpb.sectorsPerFAT);  vol.firstFATSectorNo = vol.bootSectorNo +			    LE2(bootSector->bpb.reservedSectors);  vol.secondFATSectorNo = vol.firstFATSectorNo +			     LE2(bootSector->bpb.sectorsPerFAT);  vol.rootDirectorySectorNo = vol.firstFATSectorNo +		   bootSector->bpb.noOfFATS * LE2(bootSector->bpb.sectorsPerFAT);  vol.sectorsInRootDirectory =	(UNAL2(bootSector->bpb.rootDirectoryEntries) * DIRECTORY_ENTRY_SIZE - 1) /		SECTOR_SIZE + 1;  vol.firstDataSectorNo = vol.rootDirectorySectorNo +			     vol.sectorsInRootDirectory;  noOfSectors = UNAL2(bootSector->bpb.totalSectorsInVolumeDOS3);  if (noOfSectors == 0)    noOfSectors = (SectorNo) LE4(bootSector->bpb.totalSectorsInVolume);  vol.maxCluster = (unsigned) ((noOfSectors - vol.firstDataSectorNo) /				vol.sectorsPerCluster) + 1;  if (vol.maxCluster < 4085) {#ifdef FAT_12BIT    vol.flags |= VOLUME_12BIT_FAT;	/* 12-bit FAT */#else#ifdef DEBUG_PRINT    DEBUG_PRINT("Debug: FAT_12BIT must be defined.\n");#endif    return flFormatNotSupported;#endif  }  vol.bytesPerCluster = vol.sectorsPerCluster * SECTOR_SIZE;  vol.allocationRover = 2;	/* Set rover at first cluster */  vol.flags |= VOLUME_MOUNTED;	/* That's it */  return flOK;}#if defined(DEFRAGMENT_VOLUME) || defined(SINGLE_BUFFER)/*----------------------------------------------------------------------*//*		      	 d e f r a g m e n t V o l u m e		*//*									*//* Performs a general defragmentation and recycling of non-writable	*//* Flash areas, to achieve optimal write speed.				*//*                                                                      *//* NOTE: The required number of sectors (in irLength) may be changed    *//* (from another execution thread) while defragmentation is active. In  *//* particular, the defragmentation may be cut short after it began by	*//* modifying the irLength field to 0.					*//*									*//* Parameters:                                                          *//*	ioreq->irLength	: Minimum number of sectors to make available   *//*			  for writes.					*//*                                                                      *//* Returns:                                                             *//*	ioreq->irLength	: Actual number of sectors available for writes	*//*	FLStatus	: 0 on success, otherwise failed                *//*----------------------------------------------------------------------*/static FLStatus defragmentVolume(Volume vol, IOreq FAR2 *ioreq){  return vol.tl.defragment(vol.tl.rec,&ioreq->irLength);}#endif /* DEFRAGMENT_VOLUME */#ifdef FORMAT_VOLUME/*----------------------------------------------------------------------*//*		      f l F o r m a t V o l u m e			*//*									*//* Formats a volume, writing a new and empty file-system. All existing  *//* data is destroyed. Optionally, a low-level FTL formatting is also    *//* done.								*//* Formatting leaves the volume in the dismounted state, so that a	*//* flMountVolume call is necessary after it.				*//*                                                                      *//* Parameters:                                                          *//*	irHandle	: Drive number (0, 1, ...)			*//*	irFlags		: NO_FTL_FORMAT: Do FAT formatting only		*//*			  FTL_FORMAT: Do FTL & FAT formatting           *//*			  FTL_FORMAT_IF_NEEDED: Do FTL formatting only	*//*				      if current format is invalid	*//*	irData		: Address of FormatParams structure to use	*//*                                                                      *//* Returns:                                                             *//*	FLStatus	: 0 on success, otherwise failed                *//*----------------------------------------------------------------------*/static FLStatus formatVolume(Volume vol, IOreq FAR2 *ioreq){  FormatParams FAR1 *formatParams = (FormatParams FAR1 *) ioreq->irData;  checkStatus(dismountVolume(&vol));  if (ioreq->irFlags == FTL_FORMAT) {    checkStatus(flFormat(&vol - vols,formatParams));  }  else {    FLStatus status = flMount(&vol - vols,&vol.tl,&vol.flash);    if ((status == flUnknownMedia || status == flBadFormat) &&	ioreq->irFlags == FTL_FORMAT_IF_NEEDED)      status = flFormat(&vol - vols,formatParams);    if (status != flOK)      return status;  }  checkStatus(flMount(&vol - vols,&vol.tl,&vol.flash));  checkStatus(flDosFormat(&vol.tl,formatParams));  return flOK;}#endif /* FORMAT_VOLUME */#ifdef ABS_READ_WRITE/*----------------------------------------------------------------------*//*		             a b s R e a d 				*//*									*//* Reads absolute sectors by sector no.					*//*									*//* Parameters:                                                          *//*	irHandle	: Drive number (0, 1, ...)			*//*      irData		: Address of user buffer to read into		*//*	irSectorNo	: First sector no. to read (sector 0 is the	*//*			  DOS boot sector).				*//*	irSectorCount	: Number of consectutive sectors to read	*//*                                                                      *//* Returns:                                                             *//*	FLStatus	: 0 on success, otherwise failed                *//*	irSectorCount	: Number of sectors actually read		*//*----------------------------------------------------------------------*/static FLStatus absRead(Volume vol, IOreq FAR2 *ioreq){  char FAR1 *userBuffer = (char FAR1 *) ioreq->irData;  SectorNo currSector = vol.bootSectorNo + ioreq->irSectorNo;  unsigned sectorCount = ioreq->irSectorCount;  for (ioreq->irSectorCount = 0;       ioreq->irSectorCount < sectorCount;       ioreq->irSectorCount++, currSector++, userBuffer += SECTOR_SIZE) {    const void FAR0 *mappedSector = findSector(&vol,currSector);    if (mappedSector)      tffscpy(userBuffer,mappedSector,SECTOR_SIZE);    else      tffsset(userBuffer,0,SECTOR_SIZE);  }  return flOK;}/*----------------------------------------------------------------------*//*		      r e p l a c e F A T s e c t o r 			*//*									*//* Monitors sector deletions in the FAT.				*//*									*//* When a FAT block is about to be written by an absolute write, this   *//* routine will first scan whether any sectors are being logically	*//* deleted by this FAT update, and if so, it will delete-sector them	*//* before the actual FAT update takes place.				*//*									*//* Parameters:                                                          *//*	vol		: Pointer identifying drive			*//*	sectorNo	: FAT Sector no. about to be written		*//*      newFATsector	: Address of FAT sector about to be written	*//*                                                                      *//* Returns:                                                             *//*	FLStatus	: 0 on success, otherwise failed                *//*----------------------------------------------------------------------*/FLStatus replaceFATsector(Volume vol,			SectorNo sectorNo,			const char FAR1 *newFATsector){  const char FAR0 *oldFATsector = (const char FAR0 *) findSector(&vol,sectorNo);#ifdef FAT_12BIT  unsigned FAThalfBytes = vol.flags & VOLUME_12BIT_FAT ? 3 : 4;  unsigned firstCluster =	(FAThalfBytes == 3) ?	(((unsigned) (sectorNo - vol.firstFATSectorNo) * (2 * SECTOR_SIZE) + 2) / 3) :	((unsigned) (sectorNo - vol.firstFATSectorNo) * (SECTOR_SIZE / 2));  SectorNo firstSector =	((SectorNo) firstCluster - 2) * vol.sectorsPerCluster + vol.firstDataSectorNo;  unsigned int halfByteOffset =	(firstCluster * FAThalfBytes) & (2 * SECTOR_SIZE - 1);  if (oldFATsector == NULL)    return flOK;  /* Find if any clusters were logically deleted, and if so, delete them */  /* NOTE: We are skipping over 12-bit FAT entries which span more than  */  /*       one sector. Nobody's perfect anyway.                          */  for (; halfByteOffset < (2 * SECTOR_SIZE - 2);       firstSector += vol.sectorsPerCluster, halfByteOffset += FAThalfBytes) {    unsigned short oldFATentry, newFATentry;#ifdef TFFS_BIG_ENDIAN    oldFATentry = LE2(*(LEushort FAR0 *)(oldFATsector + (halfByteOffset / 2)));    newFATentry = LE2(*(LEushort FAR1 *)(newFATsector + (halfByteOffset / 2)));#else    oldFATentry = UNAL2(*(Unaligned FAR0 *)(oldFATsector + (halfByteOffset / 2)));    newFATentry = UNAL2(*(Unaligned FAR1 *)(newFATsector + (halfByteOffset / 2)));#endif /* TFFS_BIG_ENDIAN */    if (halfByteOffset & 1) {      oldFATentry >>= 4;      newFATentry >>= 4;    }    else if (FAThalfBytes == 3) {      oldFATentry &= 0xfff;      newFATentry &= 0xfff;    }#else  unsigned firstCluster =	((unsigned) (sectorNo - vol.firstFATSectorNo) * (SECTOR_SIZE / 2));  SectorNo firstSector =	((SectorNo) firstCluster - 2) * vol.sectorsPerCluster + vol.firstDataSectorNo;  unsigned int byteOffset;  if (oldFATsector == NULL)    return flOK;  /* Find if any clusters were logically deleted, and if so, delete them */  for (byteOffset = 0; byteOffset < SECTOR_SIZE;       firstSector += vol.sectorsPerCluster, byteOffset += 2) {    unsigned short oldFATentry = LE2(*(LEushort FAR0 *)(oldFATsector + byteOffset));    unsigned short newFATentry = LE2(*(LEushort FAR1 *)(newFATsector + byteOffset));#endif    if (oldFATentry != FAT_FREE && newFATentry == FAT_FREE)      checkStatus(vol.tl.deleteSector(vol.tl.rec,firstSector,vol.sectorsPerCluster));    /* make sure sector is still there */    oldFATsector = (const char FAR0 *) findSector(&vol,sectorNo);  }  return flOK;}/*----------------------------------------------------------------------*//*                  d i s a b l e F A T m o n i t o r                   *//*                                                                      *//* Turns off FAT monitor.                                               *//*                                                                      *//* Parameters:                                                          *//*      vol             : Pointer identifying drive                     *//*                                                                      *//* Returns:                                                             *//*      always flOK                                                     *//*----------------------------------------------------------------------*/static FLStatus disableFATmonitor(Volume vol){  vol.firstFATSectorNo = vol.secondFATSectorNo = 0; /* Disable FAT monitoring */  return flOK;}/*----------------------------------------------------------------------*//*		           a b s W r i t e 				*//*									*//* Writes absolute sectors by sector no.				*//*									*//* Parameters:                                                          *//*	irHandle	: Drive number (0, 1, ...)			*//*      irData		: Address of user buffer to write from		*//*	irSectorNo	: First sector no. to write (sector 0 is the	*//*			  DOS boot sector).				*//*	irSectorCount	: Number of consectutive sectors to write	*//*                                                                      *//* Returns:                                                             *//*	FLStatus	: 0 on success, otherwise failed                *//*	irSectorCount	: Number of sectors actually written		*//*----------------------------------------------------------------------*/static FLStatus absWrite(Volume vol, IOreq FAR2 *ioreq){  char FAR1 *userBuffer = (char FAR1 *) ioreq->irData;  SectorNo currSector = vol.bootSectorNo + ioreq->irSectorNo;  unsigned sectorCount = ioreq->irSectorCount;  if (currSector < vol.secondFATSectorNo &&      currSector + sectorCount > vol.firstFATSectorNo) {    unsigned iSector;

⌨️ 快捷键说明

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