using System;
using System.Collections.Generic;
using System.Text;
using System.IO;
namespace DSDecmp.Formats
{
///
/// Base class for compression formats.
///
public abstract class CompressionFormat
{
///
/// Checks if the decompressor for this format supports the given file. Assumes the
/// file exists. Returns false when it is certain that the given file is not supported.
/// False positives may occur, as this method should not do any decompression, and
/// may mis-interpret a similar file format as compressed.
///
/// The name of the file to check.
/// False if the file can certainly not be decompressed using this decompressor.
/// True if the file may potentially be decompressed using this decompressor.
public bool Supports(string file)
{
// open the file, and delegate to the decompressor-specific code.
using (FileStream fstr = new FileStream(file, FileMode.Open))
{
return this.Supports(fstr);
}
}
///
/// Checks if the decompressor for this format supports the data from the given stream.
/// Returns false when it is certain that the given data is not supported.
/// False positives may occur, as this method should not do any decompression, and may
/// mis-interpret a similar data format as compressed.
///
/// The stream that may or may not contain compressed data. The
/// position of this stream may change during this call, but will be returned to its
/// original position when the method returns.
/// False if the data can certainly not be decompressed using this decompressor.
/// True if the data may potentially be decompressed using this decompressor.
public abstract bool Supports(Stream stream);
///
/// Decompresses the given file, writing the deocmpressed data to the given output file.
/// The output file will be overwritten if it already exists.
/// Assumes Supports(infile)
returns true
.
///
/// The file to decompress.
/// The target location of the decompressed file.
public void Decompress(string infile, string outfile)
{
// make sure the output directory exists
string outDirectory = Path.GetDirectoryName(outfile);
if (!Directory.Exists(outDirectory))
Directory.CreateDirectory(outDirectory);
// open the two given files, and delegate to the format-specific code.
using (FileStream inStream = new FileStream(infile, FileMode.Open),
outStream = new FileStream(outfile, FileMode.Create))
{
this.Decompress(inStream, inStream.Length, outStream);
}
}
///
/// Decompresses the given stream, writing the decompressed data to the given output stream.
/// Assumes Supports(instream)
returns true
.
/// After this call, the input stream will be positioned at the end of the compressed stream,
/// or at the initial position + inLength
, whichever comes first.
///
/// The stream to decompress. At the end of this method, the position
/// of this stream is directly after the compressed data.
/// The length of the input data. Not necessarily all of the
/// input data may be read (if there is padding, for example), however never more than
/// this number of bytes is read from the input stream.
/// The stream to write the decompressed data to.
/// When the given length of the input data
/// is not enough to properly decompress the input.
public abstract void Decompress(Stream instream, long inLength, Stream outstream);
///
/// Compresses the given input file, and writes the compressed data to the given
/// output file.
///
/// The file to compress.
/// The file to write the compressed data to.
/// The size of the compressed file.
public int Compress(string infile, string outfile)
{
// make sure the output directory exists
string outDirectory = Path.GetDirectoryName(outfile);
if (!Directory.Exists(outDirectory))
Directory.CreateDirectory(outDirectory);
// open the proper Streams, and delegate to the format-specific code.
using (FileStream inStream = File.Open(infile, FileMode.Open),
outStream = File.Create(outfile))
{
return this.Compress(inStream, inStream.Length, outStream);
}
}
///
/// Compresses the next inLength
bytes from the input stream,
/// and writes the compressed data to the given output stream.
///
/// The stream to read plaintext data from.
/// The length of the plaintext data.
/// The stream to write the compressed data to.
/// The size of the compressed stream.
public abstract int Compress(Stream instream, long inLength, Stream outstream);
}
}