123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238 |
- /*++
- Copyright (c) 2005, Intel Corporation. All rights reserved.<BR>
- This program and the accompanying materials are licensed and made available
- under the terms and conditions of the BSD License which accompanies this
- distribution. The full text of the license may be found at
- http://opensource.org/licenses/bsd-license.php
- THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
- WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
- Module Name:
- DirectoryCache.c
- Abstract:
- Functions for directory cache operation
- Revision History
- --*/
- #include "Fat.h"
- STATIC
- VOID
- FatFreeODir (
- IN FAT_ODIR *ODir
- )
- /*++
- Routine Description:
- Free the directory structure and release the memory.
- Arguments:
- ODir - The directory to be freed.
- Returns:
- None.
- --*/
- {
- FAT_DIRENT *DirEnt;
- //
- // Release Directory Entry Nodes
- //
- while (!IsListEmpty (&ODir->ChildList)) {
- DirEnt = DIRENT_FROM_LINK (ODir->ChildList.ForwardLink);
- RemoveEntryList (&DirEnt->Link);
- //
- // Make sure the OFile has been closed
- //
- ASSERT (DirEnt->OFile == NULL);
- FatFreeDirEnt (DirEnt);
- }
- FreePool (ODir);
- }
- STATIC
- FAT_ODIR *
- FatAllocateODir (
- IN FAT_OFILE *OFile
- )
- /*++
- Routine Description:
- Allocate the directory structure.
- Arguments:
- OFile - The corresponding OFile.
- Returns:
- None.
- --*/
- {
- FAT_ODIR *ODir;
- ODir = AllocateZeroPool (sizeof (FAT_ODIR));
- if (ODir != NULL) {
- //
- // Initialize the directory entry list
- //
- ODir->Signature = FAT_ODIR_SIGNATURE;
- InitializeListHead (&ODir->ChildList);
- ODir->CurrentCursor = &ODir->ChildList;
- }
- return ODir;
- }
- VOID
- FatDiscardODir (
- IN FAT_OFILE *OFile
- )
- /*++
- Routine Description:
- Discard the directory structure when an OFile will be freed.
- Volume will cache this directory if the OFile does not represent a deleted file.
- Arguments:
- OFile - The OFile whose directory structure is to be discarded.
- Returns:
- None.
- --*/
- {
- FAT_ODIR *ODir;
- FAT_VOLUME *Volume;
- Volume = OFile->Volume;
- ODir = OFile->ODir;
- if (!OFile->DirEnt->Invalid) {
- //
- // If OFile does not represent a deleted file, then we will cache the directory
- // We use OFile's first cluster as the directory's tag
- //
- ODir->DirCacheTag = OFile->FileCluster;
- InsertHeadList (&Volume->DirCacheList, &ODir->DirCacheLink);
- if (Volume->DirCacheCount == FAT_MAX_DIR_CACHE_COUNT) {
- //
- // Replace the least recent used directory
- //
- ODir = ODIR_FROM_DIRCACHELINK (Volume->DirCacheList.BackLink);
- RemoveEntryList (&ODir->DirCacheLink);
- } else {
- //
- // No need to find a replace
- //
- Volume->DirCacheCount++;
- ODir = NULL;
- }
- }
- //
- // Release ODir Structure
- //
- if (ODir != NULL) {
- FatFreeODir (ODir);
- }
- }
- VOID
- FatRequestODir (
- IN FAT_OFILE *OFile
- )
- /*++
- Routine Description:
- Request the directory structure when an OFile is newly generated.
- If the directory structure is cached by volume, then just return this directory;
- Otherwise, allocate a new one for OFile.
- Arguments:
- OFile - The OFile which requests directory structure.
- Returns:
- None.
- --*/
- {
- UINTN DirCacheTag;
- FAT_VOLUME *Volume;
- FAT_ODIR *ODir;
- FAT_ODIR *CurrentODir;
- LIST_ENTRY *CurrentODirLink;
- Volume = OFile->Volume;
- ODir = NULL;
- DirCacheTag = OFile->FileCluster;
- for (CurrentODirLink = Volume->DirCacheList.ForwardLink;
- CurrentODirLink != &Volume->DirCacheList;
- CurrentODirLink = CurrentODirLink->ForwardLink
- ) {
- CurrentODir = ODIR_FROM_DIRCACHELINK (CurrentODirLink);
- if (CurrentODir->DirCacheTag == DirCacheTag) {
- RemoveEntryList (&CurrentODir->DirCacheLink);
- Volume->DirCacheCount--;
- ODir = CurrentODir;
- break;
- }
- }
- if (ODir == NULL) {
- //
- // This directory is not cached, then allocate a new one
- //
- ODir = FatAllocateODir (OFile);
- }
- OFile->ODir = ODir;
- }
- VOID
- FatCleanupODirCache (
- IN FAT_VOLUME *Volume
- )
- /*++
- Routine Description:
- Clean up all the cached directory structures when the volume is going to be abandoned.
- Arguments:
- Volume - FAT file system volume.
- Returns:
- None.
- --*/
- {
- FAT_ODIR *ODir;
- while (Volume->DirCacheCount > 0) {
- ODir = ODIR_FROM_DIRCACHELINK (Volume->DirCacheList.BackLink);
- RemoveEntryList (&ODir->DirCacheLink);
- FatFreeODir (ODir);
- Volume->DirCacheCount--;
- }
- }
|