public DirectoryEntry(FileSystemFAT fileSystem, long offset) { byte[] data = fileSystem.Store.GetBytes((ulong)offset, DIR_ENTRY_SIZE); DIR_Name = ASCIIEncoding.ASCII.GetString(data, 0, 11); DIR_Attr = (FATDirectoryAttributes)data[11]; DIR_NTRes = data[12]; DIR_CrtTimeTenth = data[13]; DIR_CrtTime = BitConverter.ToUInt16(data, 14); DIR_CrtDate = BitConverter.ToUInt16(data, 16); DIR_LstAccDate = BitConverter.ToUInt16(data, 18); DIR_FstClusHI = BitConverter.ToUInt16(data, 20); DIR_WrtTime = BitConverter.ToUInt16(data, 22); DIR_WrtDate = BitConverter.ToUInt16(data, 24); DIR_FstClusLO = BitConverter.ToUInt16(data, 26); DIR_FileSize = BitConverter.ToUInt32(data, 28); Free = data[0] == 0x0 || data[0] == 0x05 || data[0] == 0xE5; Last = data[0] == 0x0; string filename = DIR_Name.Substring(0, 8).Trim().ToLower(); string ext = DIR_Name.Substring(8).Trim().ToLower(); FileName = filename; if (ext != "") { if ((Attributes & FATDirectoryAttributes.ATTR_VOLUME_ID) == 0) { FileName += "."; } FileName += ext; } Offset = fileSystem.GetDiskOffsetOfFATCluster(ClusterNum); if (LongNameEntry) { LongName = string.Concat(Encoding.Unicode.GetString(data, 1, 10), Encoding.Unicode.GetString(data, 14, 12), Encoding.Unicode.GetString(data, 28, 4)); } }
public override byte[] GetBytes(ulong _offset, ulong _length) { long offset = (long)_offset; long length = (long)_length; long currentCluster = FirstCluster; lock (_clusterCache) { byte[] res = new byte[length]; long resindex = 0; // Find the first cluster we want to read. while (offset >= FileSystem.BytesPerCluster && currentCluster >= 0) { currentCluster = GetNextCluster(currentCluster); offset -= FileSystem.BytesPerCluster; } // Cache and retrieve the data for each cluster until we get all we need. while (length > 0 && currentCluster >= 0) { // Cache the current cluster. if (!_clusterCache.ContainsKey(currentCluster)) { _clusterCache[currentCluster] = FileSystem.Store.GetBytes( (ulong)FileSystem.GetDiskOffsetOfFATCluster(currentCluster), (ulong)FileSystem.BytesPerCluster); } // Read the cached data. long read = Math.Min(length, FileSystem.BytesPerCluster - offset); Array.Copy(_clusterCache[currentCluster], offset, res, resindex, read); offset = 0; length -= read; resindex += read; currentCluster = GetNextCluster(currentCluster); } return(res); } }
private IEnumerable <DirectoryEntry> GetDirectoryEntries() { // read all directory entries long pos = Offset; long clusterStart = Offset; long currentCluster = FirstCluster; string longName = ""; List <DirectoryEntry> res = new List <DirectoryEntry>(); // check if this is pointing at the root dir and is obviously not supposed to be if (_root || FirstCluster != FileSystem.RootCluster) { DirectoryEntry current = new DirectoryEntry(FileSystem, pos); while (!current.Last) { if (current.LongNameEntry) { longName = current.LongName + longName; } else { if (!(_root && FileSystem.Type == PartitionType.FAT16) && current.Invalid) { // this is an invalid entry, so the whole directory is probably invalid break; } if (longName.Contains("\0")) { longName = longName.Remove(longName.IndexOf("\0")); } if (longName != "") { current.FileName = longName; } //yield return current; res.Add(current); longName = ""; } if (_root && FileSystem.Type == PartitionType.FAT16 && pos - clusterStart >= FileSystem.RootEntryCount * DIR_ENTRY_SIZE) { break; } else if ((_root && FileSystem.Type == PartitionType.FAT16) || pos - clusterStart < FileSystem.BytesPerCluster) { pos += DIR_ENTRY_SIZE; } else { // check the FAT currentCluster = GetNextCluster(currentCluster); if (currentCluster < 0) { break; } pos = clusterStart = FileSystem.GetDiskOffsetOfFATCluster(currentCluster); } current = new DirectoryEntry(FileSystem, pos); } } return(res); }