GDROMExplorer/SEGATools/Stream/SubStream.cs
2021-07-26 13:04:16 -07:00

151 lines
4.7 KiB
C#

// Decompiled with JetBrains decompiler
// Type: SEGATools.Stream.SubStream
// Assembly: SEGATools, Version=1.0.3.0, Culture=neutral, PublicKeyToken=611be24fdeb07e08
// MVID: D631183F-57B1-40A1-B502-5364D288307A
// Assembly location: SEGATools.dll
using System;
using System.IO;
namespace SEGATools.Stream
{
public class SubStream : System.IO.Stream
{
private System.IO.Stream sourceStream;
private long startOffset;
private long length;
private bool disposeSourceStream;
private bool disposed;
public SubStream(System.IO.Stream source, long offset, long length, bool autoReleaseSource)
{
if (offset < 0L)
throw new ArgumentOutOfRangeException(nameof (offset));
if (length < 0L)
throw new ArgumentOutOfRangeException(nameof (length));
this.disposed = false;
this.sourceStream = source;
this.startOffset = offset;
this.length = length;
this.disposeSourceStream = autoReleaseSource;
this.Seek(0L, SeekOrigin.Begin);
}
public override bool CanWrite => !this.disposed && this.sourceStream != null && this.sourceStream.CanWrite;
public override bool CanSeek => !this.disposed && this.sourceStream != null && this.sourceStream.CanSeek;
public override bool CanRead => !this.disposed && this.sourceStream != null && this.sourceStream.CanRead;
public override long Length => this.length;
public override long Position
{
get => this.sourceStream.Position - this.startOffset;
set => this.Seek(value, SeekOrigin.Begin);
}
public override long Seek(long offset, SeekOrigin origin)
{
this.CheckCanSeek();
switch (origin)
{
case SeekOrigin.Begin:
return this.sourceStream.Seek(this.startOffset + offset, origin) - this.startOffset;
case SeekOrigin.Current:
return this.sourceStream.Seek(offset, origin) - this.startOffset;
case SeekOrigin.End:
return this.sourceStream.Seek(this.startOffset + this.length + offset, SeekOrigin.Begin) - this.startOffset;
default:
throw new ArgumentException(string.Format("invalid origin \"{0}\": only Begin, Current and End are valid values", (object) origin), nameof (origin));
}
}
public override int Read(byte[] buffer, int offset, int count)
{
this.CheckBufferArguments(buffer, offset, count);
this.CheckCanRead();
int count1 = (int) Math.Min((long) count, this.startOffset + this.length - this.Position);
return this.sourceStream.Read(buffer, offset, count1);
}
public override void Write(byte[] buffer, int offset, int count)
{
this.CheckBufferArguments(buffer, offset, count);
this.CheckCanWrite();
if (this.Length - this.Position < (long) count)
throw new ArgumentException();
this.sourceStream.Write(buffer, offset, count);
}
public override void WriteByte(byte value)
{
this.CheckCanWrite();
if (this.Length - this.Position < 1L)
throw new ArgumentException();
this.sourceStream.WriteByte(value);
}
public override void Close()
{
if (this.sourceStream == null || !this.disposeSourceStream)
return;
this.sourceStream.Close();
}
public override void SetLength(long value) => throw new NotSupportedException();
public override void Flush() => throw new NotSupportedException();
private void CheckBufferArguments(byte[] buffer, int offset, int count)
{
if (buffer == null)
throw new ArgumentNullException(nameof (buffer));
if (offset < 0)
throw new ArgumentOutOfRangeException(nameof (offset));
if (count < 0)
throw new ArgumentOutOfRangeException(nameof (count));
if (offset + count > buffer.Length)
throw new ArgumentException();
}
private void CheckCanWrite()
{
if (!this.CanWrite)
throw new NotSupportedException();
if (this.disposed)
throw new ObjectDisposedException(nameof (SubStream));
}
private void CheckCanRead()
{
if (!this.CanRead)
throw new NotSupportedException();
if (this.disposed)
throw new ObjectDisposedException(nameof (SubStream));
}
private void CheckCanSeek()
{
if (!this.CanSeek)
throw new NotSupportedException();
if (this.disposed)
throw new ObjectDisposedException(nameof (SubStream));
}
public new virtual void Dispose()
{
this.Dispose(true);
GC.SuppressFinalize((object) this);
}
protected new virtual void Dispose(bool disposing)
{
if (this.disposed)
return;
if (disposing)
this.Close();
this.disposed = true;
}
}
}