예제 #1
0
        /// <summary>
        /// Read a directory entry
        /// </summary>
        /// <param name="stream">The stream to read</param>
        private DirectoryEntry ReadDirectoryEntry(CBinaryReader stream)
        {
            DirectoryEntry entry = null;

            try
            {
                long position = stream.Position;

                entry        = new DirectoryEntry();
                entry.Length = stream.ReadByte();
                entry.ExtendedAttributeRecordlength = stream.ReadByte();

                entry.ExtentLba = stream.ReadUInt32();
                if (entry.ExtentLba != stream.ReadUInt32BE())
                {
                    throw new FrameworkException("Error while reading DirectoryEntry : ExtentLBA is not valid");
                }

                entry.ExtentSize = stream.ReadUInt32();
                if (entry.ExtentSize != stream.ReadUInt32BE())
                {
                    throw new FrameworkException("Error while reading DirectoryEntry : ExtentSize is not valid");
                }

                byte[] buffer = stream.ReadBytes(7);
                entry.Date = new DateTime(buffer[0] + 1900, buffer[1], buffer[2], buffer[3], buffer[4], buffer[5], DateTimeKind.Utc);

                entry.Flags        = stream.ReadByte();
                entry.FileUnitSize = stream.ReadByte();
                entry.Interleave   = stream.ReadByte();

                entry.VolumeSequenceNumber = stream.ReadUInt16();
                if (entry.VolumeSequenceNumber != stream.ReadUInt16BE())
                {
                    throw new FrameworkException("Error while reading DirectoryEntry : VolumeSequenceNumber is not valid");
                }

                byte nameLength = stream.ReadByte();
                entry.Name = _regFileName.Match(stream.ReadAsciiString(nameLength, false)).Groups[1].Value;

                if (nameLength % 2 == 0)
                {
                    stream.Position += 1;
                }

                if (_isXa && (stream.Position != position + entry.Length))
                {
                    entry.XaEntry            = new XaEntry();
                    entry.XaEntry.GroupId    = stream.ReadUInt16BE();
                    entry.XaEntry.UserId     = stream.ReadUInt16BE();
                    entry.XaEntry.Attributes = stream.ReadUInt16BE();

                    entry.XaEntry.Signature = stream.ReadAsciiString(2);
                    if (entry.XaEntry.Signature != XaEntry.XA_SIGNATURE)
                    {
                        throw new FrameworkException("Error while reading DirectoryEntry : XaEntry is not valid");
                    }

                    entry.XaEntry.FileNumber = stream.ReadByte();
                    entry.XaEntry.Unused     = stream.ReadBytes(5);
                }
            }
            catch (FrameworkException ex)
            {
                throw ex;
            }
            catch (Exception)
            {
                throw new FrameworkException("Error while reading DirectoryEntry : DirectoryEntry is not valid");
            }

            return(entry);
        }
예제 #2
0
        /// <summary>
        /// Read a primary volume descriptor
        /// </summary>
        /// <param name="stream">The stream to read</param>
        private PrimaryVolumeDescriptor ReadPrimaryVolumeDescriptor(CBinaryReader stream)
        {
            PrimaryVolumeDescriptor descriptor;

            try
            {
                byte version = stream.ReadByte();

                descriptor = new PrimaryVolumeDescriptor(version);

                descriptor.Unused1  = stream.ReadByte();
                descriptor.SystemId = stream.ReadAsciiString(32);
                descriptor.VolumeId = stream.ReadAsciiString(32);
                descriptor.Unused2  = stream.ReadBytes(8);

                descriptor.VolumeSpaceSize = stream.ReadUInt32();
                if (descriptor.VolumeSpaceSize != stream.ReadUInt32BE())
                {
                    throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : VolumeSpaceSize is not valid");
                }

                descriptor.Unused3 = stream.ReadBytes(32);

                descriptor.VolumeSetSize = stream.ReadUInt16();
                if (descriptor.VolumeSetSize != stream.ReadUInt16BE())
                {
                    throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : VolumeSetSize is not valid");
                }

                descriptor.VolumeSequenceNumber = stream.ReadUInt16();
                if (descriptor.VolumeSequenceNumber != stream.ReadUInt16BE())
                {
                    throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : VolumeSequenceNumber  is not valid");
                }

                descriptor.LogicalBlockSize = stream.ReadUInt16();
                if (descriptor.LogicalBlockSize != stream.ReadUInt16BE())
                {
                    throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : LogicalBlockSize  is not valid");
                }

                descriptor.PathTableSize = stream.ReadUInt32();
                if (descriptor.PathTableSize != stream.ReadUInt32BE())
                {
                    throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : PathTableSize  is not valid");
                }

                descriptor.TypeLPathTableLBA    = stream.ReadUInt32();
                descriptor.OptTypeLPathTableLBA = stream.ReadUInt32();
                descriptor.TypeMPathTableLBA    = stream.ReadUInt32BE();
                descriptor.OptTypeMPathTableLBA = stream.ReadUInt32BE();

                if (descriptor.OptTypeLPathTableLBA != 0 || descriptor.OptTypeMPathTableLBA != 0)
                {
                    _hasOptionalPathTable = true;
                }

                descriptor.RootDirectoryEntry = ReadDirectoryEntry(stream);

                // TODO : cas des fichiers
                descriptor.VolumeSetId         = stream.ReadAsciiString(128);
                descriptor.PublisherId         = stream.ReadAsciiString(128);
                descriptor.PreparerId          = stream.ReadAsciiString(128);
                descriptor.ApplicationId       = stream.ReadAsciiString(128);
                descriptor.CopyrightFileId     = stream.ReadAsciiString(38);
                descriptor.AbstractFileId      = stream.ReadAsciiString(36);
                descriptor.BibliographicFileId = stream.ReadAsciiString(37);
                //

                descriptor.CreationDate         = VolumeDescriptor.ToDateTime(stream.ReadBytes(17));
                descriptor.ModificationDate     = VolumeDescriptor.ToDateTime(stream.ReadBytes(17));
                descriptor.ExpirationDate       = VolumeDescriptor.ToDateTime(stream.ReadBytes(17));
                descriptor.EffectiveDate        = VolumeDescriptor.ToDateTime(stream.ReadBytes(17));
                descriptor.FileStructureVersion = stream.ReadByte();
                descriptor.Unused4         = stream.ReadByte();
                descriptor.ApplicationData = stream.ReadBytes(512);
                descriptor.Reserved        = stream.ReadBytes(653);

                // if the disk is CDROM/XA (and then contains an XaEntry in his DirectoryEntries),
                // "CD-XA001" can be read at offset 0x400 of the pvd (actually offset 0x8D of ApplicationData field)
                if (CBuffer.ReadAsciiString(descriptor.ApplicationData, 0x8D, 8) == VolumeDescriptor.VOLUME_XA)
                {
                    _isXa = true;
                }
            }
            catch (FrameworkException ex)
            {
                throw ex;
            }
            catch (Exception)
            {
                throw new FrameworkException("Error while reading PrimaryVolumeDescriptor : PrimaryVolumeDescriptor is not valid");
            }

            return(descriptor);
        }