/// <summary>
        /// Builds a directory entry and populates its correct type, children and siblings.
        /// </summary>
        /// <param name="entry">The directory sector entry.</param>
        /// <param name="entries">The current entries.</param>
        /// <param name="sectors">The data sectors.</param>
        /// <param name="fat">The FAT.</param>
        /// <returns>The correct DirectoryEntry object.</returns>
        public static DirectoryEntry CreateEntry(DirectorySectorEntry entry,
                                                 DirectorySectorEntryCollection entries,
                                                 SectorCollection sectors,
                                                 Sect[] fat)
        {
            DirectoryEntry newEntry = null;

            switch (entry.Type)
            {
            case Stgty.Storage:
                newEntry = new StorageEntry(entry.Name);
                break;

            case Stgty.Stream:
                newEntry = new StreamEntry(entry.Name, entry.Size, entry.SectStart, sectors, fat);
                break;

            default:
                newEntry = new GenericDirectoryEntry(entry.Name, entry.Type);
                break;
            }

            if (!entry.LeftSibling.IsEof)
            {
                newEntry.LeftSibling = CreateEntry(entries[entry.LeftSibling],
                                                   entries,
                                                   sectors,
                                                   fat);
            }

            if (!entry.RightSibling.IsEof)
            {
                newEntry.RightSibling = CreateEntry(entries[entry.RightSibling],
                                                    entries,
                                                    sectors,
                                                    fat);
            }

            if (!entry.Child.IsEof)
            {
                newEntry.Child = CreateEntry(entries[entry.Child],
                                             entries,
                                             sectors,
                                             fat);
            }

            return(newEntry);
        }
		/// <summary>
		/// Builds a directory entry and populates its correct type, children and siblings.
		/// </summary>
		/// <param name="entry">The directory sector entry.</param>
		/// <param name="entries">The current entries.</param>
		/// <param name="sectors">The data sectors.</param>
		/// <param name="fat">The FAT.</param>
		/// <returns>The correct DirectoryEntry object.</returns>
		public static DirectoryEntry CreateEntry(DirectorySectorEntry entry, 
			DirectorySectorEntryCollection entries, 
			SectorCollection sectors, 
			Sect[] fat)
		{
			DirectoryEntry newEntry = null;
			switch(entry.Type)
			{
				case Stgty.Storage :
					newEntry = new StorageEntry(entry.Name);
					break;
				case Stgty.Stream :
					newEntry = new StreamEntry(entry.Name, entry.Size, entry.SectStart, sectors, fat);
					break;
				default:
					newEntry = new GenericDirectoryEntry(entry.Name, entry.Type);
					break;
			}

			if(!entry.LeftSibling.IsEof)
				newEntry.LeftSibling = CreateEntry(entries[entry.LeftSibling],
					entries,
					sectors,
					fat);

			if(!entry.RightSibling.IsEof)
				newEntry.RightSibling = CreateEntry(entries[entry.RightSibling],
					entries,
					sectors,
					fat);

			if(!entry.Child.IsEof)
				newEntry.Child = CreateEntry(entries[entry.Child],
					entries,
					sectors,
					fat);

			return newEntry;
		}
Exemple #3
0
        private void Init(Stream stream)
        {
            // stream size sanity checker
            // compound files are always blocks of 512 bytes
            Debug.Assert((stream.Length % 512) == 0);

            // read in the first sector
            StorageSector sector = new StorageSector(stream);
            // interpret sector as header sector
            HeaderSector header = new HeaderSector(sector.GetStream());

            // read in all remaining sectors
            SectorCollection sectors = new SectorCollection((int)(stream.Length / Constants.SECTOR_SIZE));

            while (stream.Position != stream.Length)
            {
                sector = new StorageSector(stream);
                sectors.Add(sector);
            }

            // build the fat index
            List <Sect> index = new List <Sect>((int)(Constants.MAX_SECT * header.SectFatCount));

            // read first 109 fat entries
            for (int i = 0; i < header.SectFat.Length; ++i)
            {
                Sect fatSect = header.SectFat[i];
                if (!fatSect.IsFree)
                {
                    FatSector fat = new FatSector(((StorageSector)sectors[fatSect]).GetStream());
                    index.AddRange(fat.SectFat);
                    sectors[fatSect] = fat;
                }
            }

            // read remaining fat entries
            int  difCount;
            Sect difIndex;

            for (difIndex = header.SectDifStart, difCount = 0;
                 !difIndex.IsEndOfChain && difCount < header.SectDifCount;
                 ++difCount)
            {
                DifSector dif = new DifSector(((StorageSector)sectors[difIndex]).GetStream());
                sectors[difIndex] = dif;

                for (int i = 0; i < dif.SectFat.Length; ++i)
                {
                    Sect fatSect = dif.SectFat[i];

                    if (!fatSect.IsFree)
                    {
                        FatSector fat = new FatSector(((StorageSector)sectors[fatSect]).GetStream());
                        index.AddRange(fat.SectFat);
                        sectors[fatSect] = fat;
                    }
                }

                difIndex = dif.NextDif;
            }
            Debug.Assert(difCount == header.SectDifCount);

            // read in mini fat sectors
            Debug.Assert(index.Count == (header.SectFatCount * Constants.MAX_SECT));
            Debug.Assert(index.Capacity == index.Count);

            Sect[] fatSects = index.ToArray();

            Sect miniFatSect;
            int  miniFatCount;

            for (miniFatSect = header.SectMiniFatStart, miniFatCount = 0;
                 !miniFatSect.IsEndOfChain && miniFatCount < header.SectMiniFatCount;
                 miniFatSect = fatSects[miniFatSect.ToInt()], ++miniFatCount)
            {
                MiniFatSector miniFat = new MiniFatSector(((StorageSector)sectors[miniFatSect]).GetStream());
                sectors[miniFatSect] = miniFat;
            }

            Debug.Assert(miniFatCount == header.SectMiniFatCount);

            // read in directory sectors
            DirectorySectorEntryCollection dirs = new DirectorySectorEntryCollection();

            for (Sect dirSect = header.SectDirStart;
                 !dirSect.IsEndOfChain;
                 dirSect = fatSects[dirSect.ToInt()])
            {
                DirectorySector dir = new DirectorySector(((StorageSector)sectors[dirSect]).GetStream());

                foreach (DirectorySectorEntry entry in dir.Entries)
                {
                    dirs.Add(entry);
                }

                sectors[dirSect] = dir;
            }

            _directory = new Directory(dirs, sectors, fatSects);
        }
Exemple #4
0
 /// <summary>
 /// Constructor.
 /// </summary>
 /// <param name="entries">The directory sector entries.</param>
 /// <param name="sectors">All the sectors.</param>
 /// <param name="fat">The FAT.</param>
 public Directory(DirectorySectorEntryCollection entries, SectorCollection sectors, Sect[] fat)
 {
     _root = DirectoryEntryFactory.CreateEntry(entries[Sid.ZERO], entries, sectors, fat);
 }
		private void Init(Stream stream)
		{
			// stream size sanity checker
			// compound files are always blocks of 512 bytes
			Debug.Assert((stream.Length % 512) == 0);
			
			// read in the first sector
			StorageSector sector = new StorageSector(stream);
			// interpret sector as header sector
			HeaderSector header = new HeaderSector(sector.GetStream());

			// read in all remaining sectors
			SectorCollection sectors = new SectorCollection((int)(stream.Length / Constants.SECTOR_SIZE));
			while(stream.Position != stream.Length)
			{
				sector = new StorageSector(stream);
				sectors.Add(sector);
			}

			// build the fat index
			List<Sect> index = new List<Sect>((int)(Constants.MAX_SECT * header.SectFatCount));

			// read first 109 fat entries
			for(int i = 0; i < header.SectFat.Length; ++i)
			{
				Sect fatSect = header.SectFat[i];
				if(!fatSect.IsFree)
				{
					FatSector fat = new FatSector(((StorageSector)sectors[fatSect]).GetStream());
					index.AddRange(fat.SectFat);
					sectors[fatSect] = fat;
				}
			}

			// read remaining fat entries
			int difCount;
			Sect difIndex;									 
			for(difIndex = header.SectDifStart, difCount = 0;
				!difIndex.IsEndOfChain && difCount < header.SectDifCount; 
				++difCount)
			{
				DifSector dif = new DifSector(((StorageSector)sectors[difIndex]).GetStream());
				sectors[difIndex] = dif;

				for(int i = 0; i < dif.SectFat.Length; ++i)
				{
					Sect fatSect = dif.SectFat[i];

					if(!fatSect.IsFree)
					{
						FatSector fat = new FatSector(((StorageSector)sectors[fatSect]).GetStream());
						index.AddRange(fat.SectFat);
						sectors[fatSect] = fat;
					}
				}
				
				difIndex = dif.NextDif;
			}
			Debug.Assert(difCount == header.SectDifCount);

			// read in mini fat sectors
			Debug.Assert(index.Count == (header.SectFatCount * Constants.MAX_SECT));
			Debug.Assert(index.Capacity == index.Count);

			Sect[] fatSects = index.ToArray();

			Sect miniFatSect;
			int miniFatCount;
			for(miniFatSect = header.SectMiniFatStart, miniFatCount = 0;
				!miniFatSect.IsEndOfChain && miniFatCount < header.SectMiniFatCount;
				miniFatSect = fatSects[miniFatSect.ToInt()], ++miniFatCount)
			{
				MiniFatSector miniFat = new MiniFatSector(((StorageSector)sectors[miniFatSect]).GetStream());
				sectors[miniFatSect] = miniFat;
			}

			Debug.Assert(miniFatCount == header.SectMiniFatCount);

			// read in directory sectors
			DirectorySectorEntryCollection dirs = new DirectorySectorEntryCollection();

			for(Sect dirSect = header.SectDirStart;
				!dirSect.IsEndOfChain;
				dirSect = fatSects[dirSect.ToInt()])
			{
				DirectorySector dir = new DirectorySector(((StorageSector)sectors[dirSect]).GetStream());
				
				foreach(DirectorySectorEntry entry in dir.Entries)
					dirs.Add(entry);

				sectors[dirSect] = dir;
			}

			_directory = new Directory(dirs, sectors, fatSects);
		}