Infinite loop encountered while reading Mini FAT sector chain
Structured Storage .net component - pure C#
Brought to you by:
ironfede
Hi,
Another problem I have encountered while processing test files sourced from the internet. The attached file appears to have a blank sector in the Mini FAT sector chain that triggers an infinite loop.
I have used the refined version of GetMiniSectorChain below to address this in my application.
Gary
private List<Sector> GetMiniSectorChain(int secID)
{
List<Sector> result
= new List<Sector>();
if (secID != Sector.ENDOFCHAIN)
{
List<Sector> miniFAT = GetNormalSectorChain(header.FirstMiniFATSectorID);
List<Sector> miniStream = GetNormalSectorChain(RootEntry.StartSetc);
StreamView miniFATView
= new StreamView(miniFAT, GetSectorSize(), header.MiniFATSectorsNumber * Sector.MINISECTOR_SIZE, sourceStream);
StreamView miniStreamView =
new StreamView(miniStream, GetSectorSize(), rootStorage.Size, sourceStream);
BinaryReader miniFATReader = new BinaryReader(miniFATView);
// list to guard against cycles in the sector list
var visitedSectors = new List<int>();
int nextSecID = secID;
while (true)
{
if (nextSecID == Sector.ENDOFCHAIN)
break;
// check we have not been here before!
if (visitedSectors.Contains(nextSecID))
{
throw new CFCorruptedFileException("Cyclic sector chain detected in MiniFAT");
}
visitedSectors.Add(nextSecID);
Sector ms = new Sector(Sector.MINISECTOR_SIZE, sourceStream);
ms.Id = nextSecID;
ms.Type = SectorType.Mini;
miniStreamView.Seek(nextSecID * Sector.MINISECTOR_SIZE, SeekOrigin.Begin);
miniStreamView.Read(ms.GetData(), 0, Sector.MINISECTOR_SIZE);
result.Add(ms);
miniFATView.Seek(nextSecID * 4, SeekOrigin.Begin);
nextSecID = miniFATReader.ReadInt32();
}
}
return result;
}
Thank You very much for the accurate report.
Fix will be included in the main branch.
Best Regards,
Federico