示例#1
0
        internal TarArchiveEntry(TarArchive archive, string name, int index)
        {
            this.Archive  = archive;
            this.FullName = name;
            this.index    = index;

            LinkIndicator type;
            string        realname;

            if (name.EndsWith("/") || name.EndsWith("\\"))
            {
                type     = LinkIndicator.Directory;
                realname = name.TrimEnd('/', '\\');
            }
            else
            {
                type     = LinkIndicator.File;
                realname = name;
            }
            this.header = new TarIOFileHeader()
            {
                Filename = name,
                Type     = type
            };
        }
示例#2
0
        internal TarArchiveEntry CreateEntry(string name, Stream data)
        {
            lock (this)
            {
                TarIOEntry entry;
                this.realEntries.Add(entry = new TarIOEntry()
                {
                    Length = BLOCK_SIZE,
                    Offset = baseStream.Length + BLOCK_SIZE,
                    Entry  = new TarArchiveEntry(archive, name, this.realEntries.Count),
                });

                baseStream.Seek(0, SeekOrigin.End);
                baseStream.SetLength(baseStream.Length + BLOCK_SIZE * 2);

                var header = new TarIOFileHeader()
                {
                    Filename     = name,
                    LastModified = DateTime.Now,
                    Size         = data.Length,
                    Type         = LinkIndicator.File
                };
                header.Serialise(baseStream);

                entry.Stream = new TarIOFileItemStream(entry.Offset, entry.Length, baseStream);
                data.CopyTo(entry.Stream);

                return(entry.Entry);
            }
        }
示例#3
0
        public TarArchiveEntry CreateEntryFromFile(string filepath, string entryName)
        {
            var file = File.OpenRead(filepath);

            var header = new TarIOFileHeader()
            {
                Filename     = entryName,
                LastModified = File.GetLastWriteTime(filepath),
                Size         = file.Length,
                Type         = LinkIndicator.File
            };

            lock (this)
            {
                baseStream.Seek(0, SeekOrigin.End);

                long written = header.Serialise(baseStream);
                long delta   = TarIOBlockManager.BLOCK_SIZE - written;
                long padding = file.Length % TarIOBlockManager.BLOCK_SIZE;

                byte[] buffer = new byte[Math.Max(delta, padding)];
                baseStream.Write(buffer, 0, (int)delta);

                file.CopyTo(baseStream);
                baseStream.Write(buffer, 0, (int)padding);

                return(new TarArchiveEntry(archive, header, null));
            }
        }
示例#4
0
        public TarArchiveEntry CreateEntry(string entryName)
        {
            LinkIndicator type = LinkIndicator.File;

            if (entryName.EndsWith("\\") || entryName.EndsWith("/"))
            {
                type = LinkIndicator.Directory;
            }

            lock (this)
            {
                int  index  = this.realEntries.Count;
                long offset = this.baseStream.Length + BLOCK_SIZE;

                var header = new TarIOFileHeader()
                {
                    Type         = type,
                    Filename     = entryName,
                    LastModified = DateTime.Now,
                    Size         = 0
                };

                this.baseStream.Seek(0, SeekOrigin.End);
                long written = header.Serialise(this.baseStream);
                long delta   = BLOCK_SIZE - written;

                byte[] buffer = new byte[delta];
                this.baseStream.Write(buffer, 0, buffer.Length);
            }
        }
示例#5
0
        public TarArchiveEntry CreateEntry(string name)
        {
            LinkIndicator type = LinkIndicator.File;

            if (name.EndsWith("\\") || name.EndsWith("/"))
            {
                type = LinkIndicator.Directory;
            }

            var header = new TarIOFileHeader()
            {
                Filename     = name,
                LastModified = DateTime.Now,
                Size         = 0,
                Type         = type
            };

            long written = header.Serialise(BaseStream);
            long delta   = TarIOBlockManager.BLOCK_SIZE - written;

            byte[] buffer = new byte[delta];
            BaseStream.Write(buffer, 0, (int)delta);

            Position += TarIOBlockManager.BLOCK_SIZE;
            return(new TarArchiveEntry(Archive, header, null));
        }
示例#6
0
            public bool MoveNext()
            {
                // Dispose of previous entry, if present
                if (Current != null)
                {
                    Current.Dispose();
                }

                var nextHeader = new TarIOFileHeader(reader);

                entries.Position += TarIOBlockManager.BLOCK_SIZE;

                // Check for end of file blank header
                if (nextHeader.Filename.Length == 0 &&
                    nextHeader.Size == 0 && nextHeader.Type == 0)
                {
                    return(false);
                }

                // Create new entry
                Current = new TarArchiveEntry(entries.Archive, nextHeader,
                                              new TarIOFileItemStream(entries.Position, nextHeader.Size, entries.BaseStream));

                // Increment position by block-adjusted size
                entries.Position += (nextHeader.Size + TarIOBlockManager.BLOCK_SIZE - 1) & (-TarIOBlockManager.BLOCK_SIZE);

                return(true);
            }
示例#7
0
        internal TarArchiveEntry(TarArchive archive, TarIOFileHeader header)
        {
            this.Archive      = archive;
            this.FullName     = header.Filename;
            this.Name         = header.Filename.Split('/', '\\').Last();
            this.LastModified = header.LastModified;

            switch (header.Type)
            {
            case LinkIndicator.File:
            case LinkIndicator.ContiguousFile:
                this.Type = TarEntryType.File;
                break;

            case LinkIndicator.HardLink:
            case LinkIndicator.SymbolicLink:
            case LinkIndicator.CharacterSpecial:
            case LinkIndicator.BlockSpecial:
            case LinkIndicator.FIFO:
                this.Type = TarEntryType.Link;
                break;

            case LinkIndicator.Directory:
                this.Type = TarEntryType.Directory;
                break;

            case LinkIndicator.GlobalHeaderEx:
            case LinkIndicator.FileHeaderEx:
            case LinkIndicator.GnuDumpDirectory:
            case LinkIndicator.GnuLongLink:
            case LinkIndicator.GnuLongName:
            case LinkIndicator.GnuMultiVolume:
            case LinkIndicator.GnuSparse:
            case LinkIndicator.GnuVolumeHeader:
            case LinkIndicator.SolarisHeaderEx:
                this.Type = TarEntryType.Metadata;
                break;

            default:
                this.Type = TarEntryType.Other;
                break;
            }

            this.header = header;
        }
示例#8
0
        private void ParseFile()
        {
            byte[] blockBuffer = new byte[TarIOBlockManager.BLOCK_SIZE];
            long   position    = 0;

            while (true)
            {
                try
                {
                    using (var reader = new BinaryReader(baseStream, ASCIIEncoding.ASCII, true))
                    {
                        var  header = new TarIOFileHeader(reader);
                        long blocks = (header.Size + TarIOBlockManager.BLOCK_SIZE - 1) / TarIOBlockManager.BLOCK_SIZE;

                        position += TarIOBlockManager.BLOCK_SIZE;



                        this.RealEntries.Add(new TarArchiveEntry(this, header, this.RealEntries.Count));
                        this.RandomAccess.RegisterEntry(position, header.Size);

                        for (long i = 0; i < blocks; i++)
                        {
                            baseStream.Read(blockBuffer, 0, blockBuffer.Length);
                            position += TarIOBlockManager.BLOCK_SIZE;
                        }
                    }
                }
                catch (EndOfStreamException) { break; }
            }
            this.BlockManager.Position = position;
            this.RealEntries.RemoveRange(this.RealEntries.Count - 2, 2);

            if (!baseStream.CanSeek)
            {
                // Force the base stream to be reset
                this.baseStream.Dispose();
            }
        }
示例#9
0
        public TarArchiveEntry CreateEntry(string name, Stream data)
        {
            var header = new TarIOFileHeader()
            {
                Filename     = name,
                LastModified = DateTime.Now,
                Size         = data.Length,
                Type         = LinkIndicator.File
            };

            long written = header.Serialise(BaseStream);
            long delta   = TarIOBlockManager.BLOCK_SIZE - written;
            long padding = data.Length % TarIOBlockManager.BLOCK_SIZE;

            byte[] buffer = new byte[Math.Max(delta, padding)];
            BaseStream.Write(buffer, 0, (int)delta);

            data.CopyTo(BaseStream);
            BaseStream.Write(buffer, 0, (int)padding);

            Position += TarIOBlockManager.BLOCK_SIZE + (int)padding + data.Length;
            return(new TarArchiveEntry(Archive, header, null));
        }
示例#10
0
 internal TarArchiveEntry(TarArchive archive, TarIOFileHeader header, TarIOFileItemStream stream)
     : this(archive, header)
 {
     this.stream = stream;
 }
示例#11
0
 internal TarArchiveEntry(TarArchive archive, TarIOFileHeader header, int index)
     : this(archive, header)
 {
     this.index = index;
 }