📄 fatfs.h
字号:
#define VOLF_UNSUPPORTED (VOLF_32BIT_FAT | VOLF_UNCERTAIN)
#endif
typedef DWORD UNPACKFN(PVOLUME pvol, DWORD clusIndex, PDWORD pclusData);
typedef DWORD PACKFN(PVOLUME pvol, DWORD clusIndex, DWORD clusData, PDWORD pclusDataPrev);
struct _VOLUME {
HVOL v_hVol;
VOL_DLINK v_dlOpenVolumes;// list of open volumes on dsk
STM_DLINK v_dlOpenStreams;// list of DSTREAMs for this volume
#ifdef PATH_CACHING
CCH_DLINK v_dlCaches; // list of CACHEs for this volume
#endif
PDSK v_pdsk; // DSK the VOLUME is open on
PPARTINFO v_ppi; // pointer to partition info, if any
DWORD v_flags; // see VOLF_*
signed char v_volID; // file system volume ID (aka AFS index), INVALID_AFS if none
BYTE v_cCaches; // # cache entries currently attached
//
// Beginning of portion reset by InitVolume for INVALID volumes
//
BYTE v_bMediaDesc; // media descriptor from BPB
BYTE v_bVerifyCount; // number of read-after-write verifies left to perform
DWORD v_serialID; // volume serial # and label from boot sector
BYTE v_label[OEMNAMESIZE+1];
BYTE v_log2cbSec; // log2(bytes per sector)
BYTE v_log2cblkSec; // log2(blocks per sector)
BYTE v_log2csecClus; // log2(sectors per cluster)
BYTE v_log2cblkClus; // log2(blocks per cluster)
DWORD v_secVolBias; // sector bias for volume (ie, reserved sectors)
DWORD v_secBlkBias; // sector bias for block 0 (ie, reserved + hidden sectors)
DWORD v_blkClusBias; // block bias for cluster 0 (ie, # blocks in FAT + root dir)
DWORD v_cbClus; // bytes per cluster
DWORD v_clusEOF; // cluster EOF threshold
DWORD v_clusMax; // maximum cluster # for volume (starting w/DATA_CLUSTER)
DWORD v_clusAlloc; // last cluster alloc'ed, -1 if none yet
DWORD v_cclusFree; // # of free clusters, -1 if not known yet
DWORD v_csecFAT; // sectors per FAT
DWORD v_secEndFAT; // ending sector # (+1) of active FAT
DWORD v_secEndAllFATs;// ending sector # (+1) of all FATs
DWORD v_csecUsed; // total sectors used in FAT and root
DWORD v_csecTotal; // total sectors on volume
#ifdef FAT32
DWORD v_secFSInfo; // as obtained from BIGFATBPB->BGBPB_FSInfoSec
#endif
UNPACKFN *v_unpack; // FAT unpack function
PACKFN *v_pack; // FAT pack function
//
// End of portion reset by InitVolume for INVALID volumes
//
PDSTREAM v_pstmFAT; // stream used to read/write FAT
PDSTREAM v_pstmRoot; // stream used to read/write root directory
PWSTR v_pwsHostRoot; // pointer to local name of root (NULL if none)
DWORD v_cwsHostRoot; // length (in WCHARs) of local root name
CRITICAL_SECTION v_cs; // critical section for volume
CRITICAL_SECTION v_csStms; // critical section for OpenStreams list
#ifdef PATH_CACHING
CRITICAL_SECTION v_csCaches;// critical section for Caches list
#endif
#ifdef DISK_CACHING
LPBYTE v_pFATCacheBuffer; // Disk Cache Buffer
LPDWORD v_pFATCacheLookup; // Lookup buffer for Cache
DWORD v_CacheSize; // Size of the cache
#endif
DWORD v_flFATFS; // Per Volume FAT Flags
};
#define NO_CLUSTER 0
#define FREE_CLUSTER NO_CLUSTER
#define FAT_PSEUDO_CLUSTER 0
#define ROOT_PSEUDO_CLUSTER 1
#define DATA_CLUSTER 2 // first legitimate cluster number
#define EOF_CLUSTER ((unsigned)-1)
#define UNKNOWN_CLUSTER EOF_CLUSTER
#define ISROOTDIR(pstm) ((pstm)->s_clusFirst == (pstm)->s_pvol->v_pstmRoot->s_clusFirst)
#define ISPARENTROOTDIR(pstm) ((pstm)->s_sid.sid_clusDir == (pstm)->s_pvol->v_pstmRoot->s_clusFirst)
#define ISEOF(pvol, cl) ((cl) >= (pvol)->v_clusEOF)
#define CLUSTERTOBLOCK(pvol,cl) (((cl) << (pvol)->v_log2cblkClus) + (pvol)->v_blkClusBias)
#define CLUSTERTOSECTOR(pvol,cl) ((((cl)-DATA_CLUSTER) << (pvol)->v_log2csecClus) + (pvol)->v_csecUsed + (pvol)->v_secBlkBias)
#define UNPACK(pvol,index,pdata) ((pvol)->v_unpack((pvol),(index),(pdata)))
#define PACK(pvol,index,data,pold) ((pvol)->v_pack((pvol),(index),(data),(pold)))
// values for lr_id:
#define LOGID_NONE 0
#define LOGID_SCANVOLUME 1 // ScanVolume()
#define LOGID_BUFFERMODIFY 2 // ModifyBuffer()
#define LOGID_BUFFERWRITE 3 // CommitBuffer(PRE)
#define LOGID_BUFFERCOMMIT 4 // CommitBuffer(POST)
#define LOGID_DISKIO 5 // FAT_DeviceIoControl
#define LOGID_CREATEFILE 6 // FAT_CreateFileW
#define LOGID_CLOSEFILE 7 // FAT_CloseFile
#define LOGID_WRITEFILE 8 // FAT_WriteFile
#define LOGID_FLUSHFILEBUFFERS 9 // FAT_FlushFileBuffers
#define LOGID_SETENDOFFILE 10 // FAT_SetEndOfFile
#define LOGID_CREATEDIRECTORY 11 // FAT_CreateDirectoryW
#define LOGID_REMOVEDIRECTORY 12 // FAT_RemoveDirectoryW
#define LOGID_DELETEFILE 13 // FAT_DeleteFileW
#define LOGID_MOVEFILE 14 // FAT_MoveFileW
#define LOGID_TOTAL 15
struct _LOGREC {
WORD lr_size; // total size of LOGREC, including lr_size
BYTE lr_id; // see LOGID_* above
BYTE lr_flags; // reserved for flags (must be zero for now)
DWORD lr_owner; // non-zero thread ID if owned, zero if not
DWORD lr_serialID; // volume serial # from boot sector
DWORD lr_blk; // block # of modification
DWORD lr_off; // offset of modification within block
DWORD lr_cb; // size of modification, in bytes
DWORD lr_crc; // checksum of buffer (on LOGID_BUFFERCOMMIT)
#ifdef DEBUG
CHAR lr_desc[18]; // space for descriptive string
#endif
BYTE lr_abData[]; // original bytes
};
typedef struct _LOGREC LOGREC, *PLOGREC;
/* Data run:
*
* This structure is used to describe a contiguous run of data on the disk.
* Note that the start and end fields are stream-relative, whereas all the
* block and cluster fields are volume-relative.
*
* NOTE that although r_blk and r_clusThis convey similar information, we
* can't eliminate either of them. That's because the FAT (and possibly ROOT)
* streams are not cluster-mapped, so the only fields that get used in those
* cases are the first three (r_start, r_end and r_blk).
*/
typedef struct _RUN {
DWORD r_start; // starting byte position of run
DWORD r_end; // ending byte of run + 1
DWORD r_blk; // first block of run
DWORD r_clusThis; // first cluster of this run
DWORD r_clusNext; // next cluster after this run
DWORD r_clusPrev; // cluster preceding this run (0 if none)
} RUN, *PRUN;
/* Open stream structure:
*
* This structure holds the description of an open file or directory. The
* SHANDLE & FHANDLE structures for the same file or directory must point to the
* same DSTREAM structure.
*/
// values for s_flags:
#define STF_INIT 0x0001 // stream has been initialized by DIRENTRY
#define STF_DEMANDPAGED 0x0002 // stream can be demand-paged
#define STF_CREATE_TIME 0x0004 // an explicit create time has been set
#define STF_ACCESS_TIME 0x0008 // an explicit access time has been set
#define STF_WRITE_TIME 0x0010 // an explicit write time has been set
#define STF_VOLUME 0x0020 // this stream is VOLUME-based (ie, not a file)
#define STF_UNMOUNTED 0x0040 // this stream currently unavailable (volume unmounted)
#define STF_BUFCURHELD 0x0080 // pbufCur is currently in use and being held
#define STF_WRITETHRU 0x0100 // somebody has opened the stream in write-through mode
#define STF_VISITED 0x0200 // stream has been visited (see FAT_CloseAllFiles)
#define STF_DIRTY_INFO 0x0400 // stream info out of sync with DIRENTRY
#define STF_DIRTY_DATA 0x0800 // stream data has been modified
#define STF_DIRTY_CLUS 0x1000 // starting cluster in stream info out of sync with DIRENTRY
#define STF_PRIVATE 0x8000 // stream is private (may be a duplicate, but it's for non-shared read-access only)
#define STF_DIRTY (STF_DIRTY_INFO | STF_DIRTY_DATA)
#define MAX_DIRSIZE 0x7FFFFFFF
typedef struct _DSID { // structure for unique data stream IDs (similar to OIDs)
DWORD sid_ordDir; // ordinal in directory of stream's DIRENTRY
DWORD sid_clusDir; // cluster of dir containing stream's DIRENTRY
} DSID;
typedef DSID *PDSID;
#define SETSID(psid,pos,clus) (psid)->sid_ordDir = (pos)/sizeof(DIRENTRY), (psid)->sid_clusDir = (clus)
#if !defined(OIDHIGH) || !defined(OIDLOW)
#define SETSIDFROMOID(psid,oid) (psid)->sid_ordDir = 0, (psid)->sid_clusDir = UNKNOWN_CLUSTER
#else
#define SETSIDFROMOID(psid,oid) (psid)->sid_ordDir = OIDHIGH(oid), (psid)->sid_clusDir = OIDLOW(oid)
#endif
#if !defined(AFSFROMOID) // either AFSFROMOID or OIDAFS must be defined externally...
#define AFSFROMOID(oid) OIDAFS(oid)
#endif
#if !defined(OIDFROMAFS) // either OIDFROMAFS or PACKOID must be defined externally...
#define OIDFROMAFS(iAFS) PACKOID(iAFS,0,0)
#endif
#if !defined(INVALID_OID)
#define INVALID_OID ((CEOID)(INVALID_HANDLE_VALUE))
#endif
#if !defined(PACKOID)
#define OIDFROMSID(pvol,psid) INVALID_OID
#define OIDFROMSTREAM(pstm) INVALID_OID
#else
#define OIDFROMSID(pvol,psid) PACKOID((pvol)->v_volID, (psid)?((PDSID)(psid))->sid_ordDir:0, (psid)?((PDSID)(psid))->sid_clusDir:0)
#define OIDFROMSTREAM(pstm) OIDFROMSID((pstm)->s_pvol, &(pstm)->s_sid)
#endif
struct _DSTREAM {
STM_DLINK s_dlOpenStreams;// linkage for v_dlOpenStreams
FH_DLINK s_dlOpenHandles;// list of FHANDLE's or SHANDLE's
PVOLUME s_pvol; // VOLUME the DSTREAM is open on
long s_refs; // usage count for the stream
WORD s_flags; // stream status flags (see STF_*)
WORD s_cwPath; // # characters in path to this stream (excluding NULL)
RUN s_run; // run info from current/last operation
PBUF s_pbufCur; // pointer to stream's current buffer, if any
DWORD s_offbufCur; // stream offset associated with current buffer
DWORD s_size; // length of the stream
CRITICAL_SECTION s_cs; // critical section for this stream
//
// Beginning of portion that actually relates to non-STF_VOLUME streams only!
// (actually, s_cwPath belongs down here as well, but since it's a WORD, it fits
// better up above)
//
DSID s_sid; // unique stream ID
DSID s_sidParent; // unique stream ID for parent
DWORD s_offDir; // offset in block of stream's DIRENTRY
DWORD s_blkDir; // block of dir containing stream's DIRENTRY
DWORD s_clusFirst; // first cluster in stream
FILETIME s_ftCreate; // creation time from DIRENTRY
FILETIME s_ftAccess; // last access time from DIRENTRY
FILETIME s_ftWrite; // last write time from DIRENTRY
BYTE s_attr; // file attribute byte
BYTE s_achOEM[OEMNAMESIZE+1];
};
/* Open file handle structure:
*
* There is one these for each open file handle on the volume. It holds the
* current file position, the file access mode, etc.
*/
// values for fh_flags:
#define FHF_FAILUI 0x01 // Used to determine if we need to put up a UI window on failure
#define FHF_LOCKED 0x10 // volume-level lock granted
#define FHF_VOLUME 0x20 // volume-level access only (ie, CreateFile("VOL:"))
#define FHF_UNMOUNTED 0x40 // this handle currently unavailable (volume has been unmounted)
#define FHF_FHANDLE 0x80 // this bit NOT set for SHANDLEs
struct _FHANDLE {
FH_DLINK fh_dlOpenHandles;
PDSTREAM fh_pstm; // DSTREAM for the file
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -