GIT: perform LF normalization
This commit is contained in:
@@ -1,116 +1,116 @@
|
||||
// ComHelper.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-June-13 17:04:06>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines a COM Helper class.
|
||||
//
|
||||
// Created: Tue, 08 Sep 2009 22:03
|
||||
//
|
||||
|
||||
using Interop=System.Runtime.InteropServices;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// This class exposes a set of COM-accessible wrappers for static
|
||||
/// methods available on the ZipFile class. You don't need this
|
||||
/// class unless you are using DotNetZip from a COM environment.
|
||||
/// </summary>
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000F")]
|
||||
[System.Runtime.InteropServices.ComVisible(true)]
|
||||
#if !NETCF
|
||||
[System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.AutoDispatch)]
|
||||
#endif
|
||||
|
||||
public class ComHelper
|
||||
{
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.IsZipFile(string)">ZipFile.IsZipFile(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
/// <returns>true if the file contains a valid zip file.</returns>
|
||||
public bool IsZipFile(string filename)
|
||||
{
|
||||
return ZipFile.IsZipFile(filename);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.IsZipFile(string, bool)">ZipFile.IsZipFile(string, bool)</see>
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// We cannot use "overloaded" Method names in COM interop.
|
||||
/// So, here, we use a unique name.
|
||||
/// </remarks>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
/// <returns>true if the file contains a valid zip file.</returns>
|
||||
public bool IsZipFileWithExtract(string filename)
|
||||
{
|
||||
return ZipFile.IsZipFile(filename, true);
|
||||
}
|
||||
|
||||
#if !NETCF
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.CheckZip(string)">ZipFile.CheckZip(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
public bool CheckZip(string filename)
|
||||
{
|
||||
return ZipFile.CheckZip(filename);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A COM-friendly wrapper for the static method <see cref="ZipFile.CheckZipPassword(string,string)"/>.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <param name="password">The password to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
public bool CheckZipPassword(string filename, string password)
|
||||
{
|
||||
return ZipFile.CheckZipPassword(filename, password);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.FixZipDirectory(string)">ZipFile.FixZipDirectory(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to fix.</param>
|
||||
public void FixZipDirectory(string filename)
|
||||
{
|
||||
ZipFile.FixZipDirectory(filename);
|
||||
}
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.LibraryVersion">ZipFile.LibraryVersion</see>
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// the version number on the DotNetZip assembly, formatted as a string.
|
||||
/// </returns>
|
||||
public string GetZipLibraryVersion()
|
||||
{
|
||||
return ZipFile.LibraryVersion.ToString();
|
||||
}
|
||||
|
||||
}
|
||||
// ComHelper.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-June-13 17:04:06>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines a COM Helper class.
|
||||
//
|
||||
// Created: Tue, 08 Sep 2009 22:03
|
||||
//
|
||||
|
||||
using Interop=System.Runtime.InteropServices;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// This class exposes a set of COM-accessible wrappers for static
|
||||
/// methods available on the ZipFile class. You don't need this
|
||||
/// class unless you are using DotNetZip from a COM environment.
|
||||
/// </summary>
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000F")]
|
||||
[System.Runtime.InteropServices.ComVisible(true)]
|
||||
#if !NETCF
|
||||
[System.Runtime.InteropServices.ClassInterface(System.Runtime.InteropServices.ClassInterfaceType.AutoDispatch)]
|
||||
#endif
|
||||
|
||||
public class ComHelper
|
||||
{
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.IsZipFile(string)">ZipFile.IsZipFile(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
/// <returns>true if the file contains a valid zip file.</returns>
|
||||
public bool IsZipFile(string filename)
|
||||
{
|
||||
return ZipFile.IsZipFile(filename);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.IsZipFile(string, bool)">ZipFile.IsZipFile(string, bool)</see>
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// We cannot use "overloaded" Method names in COM interop.
|
||||
/// So, here, we use a unique name.
|
||||
/// </remarks>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
/// <returns>true if the file contains a valid zip file.</returns>
|
||||
public bool IsZipFileWithExtract(string filename)
|
||||
{
|
||||
return ZipFile.IsZipFile(filename, true);
|
||||
}
|
||||
|
||||
#if !NETCF
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.CheckZip(string)">ZipFile.CheckZip(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
public bool CheckZip(string filename)
|
||||
{
|
||||
return ZipFile.CheckZip(filename);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A COM-friendly wrapper for the static method <see cref="ZipFile.CheckZipPassword(string,string)"/>.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="filename">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <param name="password">The password to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
public bool CheckZipPassword(string filename, string password)
|
||||
{
|
||||
return ZipFile.CheckZipPassword(filename, password);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.FixZipDirectory(string)">ZipFile.FixZipDirectory(string)</see>
|
||||
/// </summary>
|
||||
/// <param name="filename">The filename to of the zip file to fix.</param>
|
||||
public void FixZipDirectory(string filename)
|
||||
{
|
||||
ZipFile.FixZipDirectory(filename);
|
||||
}
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// A wrapper for <see cref="ZipFile.LibraryVersion">ZipFile.LibraryVersion</see>
|
||||
/// </summary>
|
||||
/// <returns>
|
||||
/// the version number on the DotNetZip assembly, formatted as a string.
|
||||
/// </returns>
|
||||
public string GetZipLibraryVersion()
|
||||
{
|
||||
return ZipFile.LibraryVersion.ToString();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
@@ -1,135 +1,135 @@
|
||||
// EncryptionAlgorithm.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-October-21 17:24:45>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the EncryptionAgorithm enum
|
||||
//
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum that provides the various encryption algorithms supported by this
|
||||
/// library.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// <c>PkzipWeak</c> implies the use of Zip 2.0 encryption, which is known to be
|
||||
/// weak and subvertible.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A note on interoperability: Values of <c>PkzipWeak</c> and <c>None</c> are
|
||||
/// specified in <see
|
||||
/// href="http://www.pkware.com/documents/casestudies/APPNOTE.TXT">PKWARE's zip
|
||||
/// specification</see>, and are considered to be "standard". Zip archives
|
||||
/// produced using these options will be interoperable with many other zip tools
|
||||
/// and libraries, including Windows Explorer.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Values of <c>WinZipAes128</c> and <c>WinZipAes256</c> are not part of the Zip
|
||||
/// specification, but rather imply the use of a vendor-specific extension from
|
||||
/// WinZip. If you want to produce interoperable Zip archives, do not use these
|
||||
/// values. For example, if you produce a zip archive using WinZipAes256, you
|
||||
/// will be able to open it in Windows Explorer on Windows XP and Vista, but you
|
||||
/// will not be able to extract entries; trying this will lead to an "unspecified
|
||||
/// error". For this reason, some people have said that a zip archive that uses
|
||||
/// WinZip's AES encryption is not actually a zip archive at all. A zip archive
|
||||
/// produced this way will be readable with the WinZip tool (Version 11 and
|
||||
/// beyond).
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// There are other third-party tools and libraries, both commercial and
|
||||
/// otherwise, that support WinZip's AES encryption. These will be able to read
|
||||
/// AES-encrypted zip archives produced by DotNetZip, and conversely applications
|
||||
/// that use DotNetZip to read zip archives will be able to read AES-encrypted
|
||||
/// archives produced by those tools or libraries. Consult the documentation for
|
||||
/// those other tools and libraries to find out if WinZip's AES encryption is
|
||||
/// supported.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// In case you care: According to <see
|
||||
/// href="http://www.winzip.com/aes_info.htm">the WinZip specification</see>, the
|
||||
/// actual AES key used is derived from the <see cref="ZipEntry.Password"/> via an
|
||||
/// algorithm that complies with <see
|
||||
/// href="http://www.ietf.org/rfc/rfc2898.txt">RFC 2898</see>, using an iteration
|
||||
/// count of 1000. The algorithm is sometimes referred to as PBKDF2, which stands
|
||||
/// for "Password Based Key Derivation Function #2".
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A word about password strength and length: The AES encryption technology is
|
||||
/// very good, but any system is only as secure as the weakest link. If you want
|
||||
/// to secure your data, be sure to use a password that is hard to guess. To make
|
||||
/// it harder to guess (increase its "entropy"), you should make it longer. If
|
||||
/// you use normal characters from an ASCII keyboard, a password of length 20 will
|
||||
/// be strong enough that it will be impossible to guess. For more information on
|
||||
/// that, I'd encourage you to read <see
|
||||
/// href="http://www.redkestrel.co.uk/Articles/RandomPasswordStrength.html">this
|
||||
/// article.</see>
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The WinZip AES algorithms are not supported with the version of DotNetZip that
|
||||
/// runs on the .NET Compact Framework. This is because .NET CF lacks the
|
||||
/// HMACSHA1 class that is required for producing the archive.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public enum EncryptionAlgorithm
|
||||
{
|
||||
/// <summary>
|
||||
/// No encryption at all.
|
||||
/// </summary>
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Traditional or Classic pkzip encryption.
|
||||
/// </summary>
|
||||
PkzipWeak,
|
||||
|
||||
#if AESCRYPTO
|
||||
/// <summary>
|
||||
/// WinZip AES encryption (128 key bits).
|
||||
/// </summary>
|
||||
WinZipAes128,
|
||||
|
||||
/// <summary>
|
||||
/// WinZip AES encryption (256 key bits).
|
||||
/// </summary>
|
||||
WinZipAes256,
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// An encryption algorithm that is not supported by DotNetZip.
|
||||
/// </summary>
|
||||
Unsupported = 4,
|
||||
|
||||
|
||||
// others... not implemented (yet?)
|
||||
}
|
||||
|
||||
}
|
||||
// EncryptionAlgorithm.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-October-21 17:24:45>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the EncryptionAgorithm enum
|
||||
//
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum that provides the various encryption algorithms supported by this
|
||||
/// library.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// <c>PkzipWeak</c> implies the use of Zip 2.0 encryption, which is known to be
|
||||
/// weak and subvertible.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A note on interoperability: Values of <c>PkzipWeak</c> and <c>None</c> are
|
||||
/// specified in <see
|
||||
/// href="http://www.pkware.com/documents/casestudies/APPNOTE.TXT">PKWARE's zip
|
||||
/// specification</see>, and are considered to be "standard". Zip archives
|
||||
/// produced using these options will be interoperable with many other zip tools
|
||||
/// and libraries, including Windows Explorer.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Values of <c>WinZipAes128</c> and <c>WinZipAes256</c> are not part of the Zip
|
||||
/// specification, but rather imply the use of a vendor-specific extension from
|
||||
/// WinZip. If you want to produce interoperable Zip archives, do not use these
|
||||
/// values. For example, if you produce a zip archive using WinZipAes256, you
|
||||
/// will be able to open it in Windows Explorer on Windows XP and Vista, but you
|
||||
/// will not be able to extract entries; trying this will lead to an "unspecified
|
||||
/// error". For this reason, some people have said that a zip archive that uses
|
||||
/// WinZip's AES encryption is not actually a zip archive at all. A zip archive
|
||||
/// produced this way will be readable with the WinZip tool (Version 11 and
|
||||
/// beyond).
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// There are other third-party tools and libraries, both commercial and
|
||||
/// otherwise, that support WinZip's AES encryption. These will be able to read
|
||||
/// AES-encrypted zip archives produced by DotNetZip, and conversely applications
|
||||
/// that use DotNetZip to read zip archives will be able to read AES-encrypted
|
||||
/// archives produced by those tools or libraries. Consult the documentation for
|
||||
/// those other tools and libraries to find out if WinZip's AES encryption is
|
||||
/// supported.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// In case you care: According to <see
|
||||
/// href="http://www.winzip.com/aes_info.htm">the WinZip specification</see>, the
|
||||
/// actual AES key used is derived from the <see cref="ZipEntry.Password"/> via an
|
||||
/// algorithm that complies with <see
|
||||
/// href="http://www.ietf.org/rfc/rfc2898.txt">RFC 2898</see>, using an iteration
|
||||
/// count of 1000. The algorithm is sometimes referred to as PBKDF2, which stands
|
||||
/// for "Password Based Key Derivation Function #2".
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A word about password strength and length: The AES encryption technology is
|
||||
/// very good, but any system is only as secure as the weakest link. If you want
|
||||
/// to secure your data, be sure to use a password that is hard to guess. To make
|
||||
/// it harder to guess (increase its "entropy"), you should make it longer. If
|
||||
/// you use normal characters from an ASCII keyboard, a password of length 20 will
|
||||
/// be strong enough that it will be impossible to guess. For more information on
|
||||
/// that, I'd encourage you to read <see
|
||||
/// href="http://www.redkestrel.co.uk/Articles/RandomPasswordStrength.html">this
|
||||
/// article.</see>
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The WinZip AES algorithms are not supported with the version of DotNetZip that
|
||||
/// runs on the .NET Compact Framework. This is because .NET CF lacks the
|
||||
/// HMACSHA1 class that is required for producing the archive.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public enum EncryptionAlgorithm
|
||||
{
|
||||
/// <summary>
|
||||
/// No encryption at all.
|
||||
/// </summary>
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// Traditional or Classic pkzip encryption.
|
||||
/// </summary>
|
||||
PkzipWeak,
|
||||
|
||||
#if AESCRYPTO
|
||||
/// <summary>
|
||||
/// WinZip AES encryption (128 key bits).
|
||||
/// </summary>
|
||||
WinZipAes128,
|
||||
|
||||
/// <summary>
|
||||
/// WinZip AES encryption (256 key bits).
|
||||
/// </summary>
|
||||
WinZipAes256,
|
||||
#endif
|
||||
|
||||
/// <summary>
|
||||
/// An encryption algorithm that is not supported by DotNetZip.
|
||||
/// </summary>
|
||||
Unsupported = 4,
|
||||
|
||||
|
||||
// others... not implemented (yet?)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,300 +1,300 @@
|
||||
// Exceptions.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-12 12:19:10>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines exceptions used in the class library.
|
||||
//
|
||||
|
||||
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
#if !NETCF
|
||||
using System.Runtime.Serialization;
|
||||
#endif
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
///// <summary>
|
||||
///// Base exception type for all custom exceptions in the Zip library. It acts as a marker class.
|
||||
///// </summary>
|
||||
//[AttributeUsage(AttributeTargets.Class)]
|
||||
//public class ZipExceptionAttribute : Attribute { }
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when an <c>ZipEntry.ExtractWithPassword()</c> method is invoked
|
||||
/// with an incorrect password.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000B")]
|
||||
public class BadPasswordException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadPasswordException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadPasswordException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadPasswordException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadPasswordException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Indicates that a read was attempted on a stream, and bad or incomplete data was
|
||||
/// received.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000A")]
|
||||
public class BadReadException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadReadException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadReadException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadReadException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{
|
||||
}
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadReadException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when an CRC check fails upon extracting an entry from a zip archive.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00009")]
|
||||
public class BadCrcException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadCrcException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadCrcException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadCrcException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when errors occur saving a self-extracting archive.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00008")]
|
||||
public class SfxGenerationException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public SfxGenerationException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public SfxGenerationException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected SfxGenerationException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Indicates that an operation was attempted on a ZipFile which was not possible
|
||||
/// given the state of the instance. For example, if you call <c>Save()</c> on a ZipFile
|
||||
/// which has no filename set, you can get this exception.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00007")]
|
||||
public class BadStateException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadStateException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadStateException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadStateException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{}
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadStateException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Base class for all exceptions defined by and throw by the Zip library.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00006")]
|
||||
public class ZipException : Exception
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public ZipException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public ZipException(String message) : base(message) { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public ZipException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{ }
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected ZipException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
// Exceptions.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-12 12:19:10>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines exceptions used in the class library.
|
||||
//
|
||||
|
||||
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
#if !NETCF
|
||||
using System.Runtime.Serialization;
|
||||
#endif
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
///// <summary>
|
||||
///// Base exception type for all custom exceptions in the Zip library. It acts as a marker class.
|
||||
///// </summary>
|
||||
//[AttributeUsage(AttributeTargets.Class)]
|
||||
//public class ZipExceptionAttribute : Attribute { }
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when an <c>ZipEntry.ExtractWithPassword()</c> method is invoked
|
||||
/// with an incorrect password.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000B")]
|
||||
public class BadPasswordException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadPasswordException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadPasswordException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadPasswordException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadPasswordException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Indicates that a read was attempted on a stream, and bad or incomplete data was
|
||||
/// received.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d0000A")]
|
||||
public class BadReadException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadReadException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadReadException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadReadException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{
|
||||
}
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadReadException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when an CRC check fails upon extracting an entry from a zip archive.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00009")]
|
||||
public class BadCrcException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadCrcException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadCrcException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadCrcException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Issued when errors occur saving a self-extracting archive.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00008")]
|
||||
public class SfxGenerationException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public SfxGenerationException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public SfxGenerationException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected SfxGenerationException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Indicates that an operation was attempted on a ZipFile which was not possible
|
||||
/// given the state of the instance. For example, if you call <c>Save()</c> on a ZipFile
|
||||
/// which has no filename set, you can get this exception.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00007")]
|
||||
public class BadStateException : ZipException
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public BadStateException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public BadStateException(String message)
|
||||
: base(message)
|
||||
{ }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public BadStateException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{}
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected BadStateException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Base class for all exceptions defined by and throw by the Zip library.
|
||||
/// </summary>
|
||||
#if !SILVERLIGHT
|
||||
[Serializable]
|
||||
#endif
|
||||
[System.Runtime.InteropServices.GuidAttribute("ebc25cf6-9120-4283-b972-0e5520d00006")]
|
||||
public class ZipException : Exception
|
||||
{
|
||||
/// <summary>
|
||||
/// Default ctor.
|
||||
/// </summary>
|
||||
public ZipException() { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
public ZipException(String message) : base(message) { }
|
||||
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="message">The message in the exception.</param>
|
||||
/// <param name="innerException">The innerException for this exception.</param>
|
||||
public ZipException(String message, Exception innerException)
|
||||
: base(message, innerException)
|
||||
{ }
|
||||
|
||||
#if ! (NETCF || SILVERLIGHT)
|
||||
/// <summary>
|
||||
/// Come on, you know how exceptions work. Why are you looking at this documentation?
|
||||
/// </summary>
|
||||
/// <param name="info">The serialization info for the exception.</param>
|
||||
/// <param name="context">The streaming context from which to deserialize.</param>
|
||||
protected ZipException(SerializationInfo info, StreamingContext context)
|
||||
: base(info, context)
|
||||
{ }
|
||||
#endif
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,85 +1,85 @@
|
||||
// ExtractExistingFileAction.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-25 08:44:37>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the ExtractExistingFileAction enum
|
||||
//
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// An enum for the options when extracting an entry would overwrite an existing file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This enum describes the actions that the library can take when an
|
||||
/// <c>Extract()</c> or <c>ExtractWithPassword()</c> method is called to extract an
|
||||
/// entry to a filesystem, and the extraction would overwrite an existing filesystem
|
||||
/// file.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
public enum ExtractExistingFileAction
|
||||
{
|
||||
/// <summary>
|
||||
/// Throw an exception when extraction would overwrite an existing file. (For
|
||||
/// COM clients, this is a 0 (zero).)
|
||||
/// </summary>
|
||||
Throw,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, overwrite the file silently.
|
||||
/// The overwrite will happen even if the target file is marked as read-only.
|
||||
/// (For COM clients, this is a 1.)
|
||||
/// </summary>
|
||||
OverwriteSilently,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, don't overwrite the file, silently.
|
||||
/// (For COM clients, this is a 2.)
|
||||
/// </summary>
|
||||
DoNotOverwrite,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, invoke the ExtractProgress
|
||||
/// event, using an event type of <see
|
||||
/// cref="ZipProgressEventType.Extracting_ExtractEntryWouldOverwrite"/>. In
|
||||
/// this way, the application can decide, just-in-time, whether to overwrite the
|
||||
/// file. For example, a GUI application may wish to pop up a dialog to allow
|
||||
/// the user to choose. You may want to examine the <see
|
||||
/// cref="ExtractProgressEventArgs.ExtractLocation"/> property before making
|
||||
/// the decision. If, after your processing in the Extract progress event, you
|
||||
/// want to NOT extract the file, set <see cref="ZipEntry.ExtractExistingFile"/>
|
||||
/// on the <c>ZipProgressEventArgs.CurrentEntry</c> to <c>DoNotOverwrite</c>.
|
||||
/// If you do want to extract the file, set <c>ZipEntry.ExtractExistingFile</c>
|
||||
/// to <c>OverwriteSilently</c>. If you want to cancel the Extraction, set
|
||||
/// <c>ZipProgressEventArgs.Cancel</c> to true. Cancelling differs from using
|
||||
/// DoNotOverwrite in that a cancel will not extract any further entries, if
|
||||
/// there are any. (For COM clients, the value of this enum is a 3.)
|
||||
/// </summary>
|
||||
InvokeExtractProgressEvent,
|
||||
}
|
||||
|
||||
}
|
||||
// ExtractExistingFileAction.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-25 08:44:37>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the ExtractExistingFileAction enum
|
||||
//
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// An enum for the options when extracting an entry would overwrite an existing file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This enum describes the actions that the library can take when an
|
||||
/// <c>Extract()</c> or <c>ExtractWithPassword()</c> method is called to extract an
|
||||
/// entry to a filesystem, and the extraction would overwrite an existing filesystem
|
||||
/// file.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
public enum ExtractExistingFileAction
|
||||
{
|
||||
/// <summary>
|
||||
/// Throw an exception when extraction would overwrite an existing file. (For
|
||||
/// COM clients, this is a 0 (zero).)
|
||||
/// </summary>
|
||||
Throw,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, overwrite the file silently.
|
||||
/// The overwrite will happen even if the target file is marked as read-only.
|
||||
/// (For COM clients, this is a 1.)
|
||||
/// </summary>
|
||||
OverwriteSilently,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, don't overwrite the file, silently.
|
||||
/// (For COM clients, this is a 2.)
|
||||
/// </summary>
|
||||
DoNotOverwrite,
|
||||
|
||||
/// <summary>
|
||||
/// When extraction would overwrite an existing file, invoke the ExtractProgress
|
||||
/// event, using an event type of <see
|
||||
/// cref="ZipProgressEventType.Extracting_ExtractEntryWouldOverwrite"/>. In
|
||||
/// this way, the application can decide, just-in-time, whether to overwrite the
|
||||
/// file. For example, a GUI application may wish to pop up a dialog to allow
|
||||
/// the user to choose. You may want to examine the <see
|
||||
/// cref="ExtractProgressEventArgs.ExtractLocation"/> property before making
|
||||
/// the decision. If, after your processing in the Extract progress event, you
|
||||
/// want to NOT extract the file, set <see cref="ZipEntry.ExtractExistingFile"/>
|
||||
/// on the <c>ZipProgressEventArgs.CurrentEntry</c> to <c>DoNotOverwrite</c>.
|
||||
/// If you do want to extract the file, set <c>ZipEntry.ExtractExistingFile</c>
|
||||
/// to <c>OverwriteSilently</c>. If you want to cancel the Extraction, set
|
||||
/// <c>ZipProgressEventArgs.Cancel</c> to true. Cancelling differs from using
|
||||
/// DoNotOverwrite in that a cancel will not extract any further entries, if
|
||||
/// there are any. (For COM clients, the value of this enum is a 3.)
|
||||
/// </summary>
|
||||
InvokeExtractProgressEvent,
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,114 +1,114 @@
|
||||
// OffsetStream.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-27 12:50:35>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines logic for handling reading of zip archives embedded
|
||||
// into larger streams. The initial position of the stream serves as
|
||||
// the base offset for all future Seek() operations.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
internal class OffsetStream : System.IO.Stream, System.IDisposable
|
||||
{
|
||||
private Int64 _originalPosition;
|
||||
private Stream _innerStream;
|
||||
|
||||
public OffsetStream(Stream s)
|
||||
: base()
|
||||
{
|
||||
_originalPosition = s.Position;
|
||||
_innerStream = s;
|
||||
}
|
||||
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
return _innerStream.Read(buffer, offset, count);
|
||||
}
|
||||
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return _innerStream.CanRead; }
|
||||
}
|
||||
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return _innerStream.CanSeek; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override void Flush()
|
||||
{
|
||||
_innerStream.Flush();
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get
|
||||
{
|
||||
return _innerStream.Length;
|
||||
}
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { return _innerStream.Position - _originalPosition; }
|
||||
set { _innerStream.Position = _originalPosition + value; }
|
||||
}
|
||||
|
||||
|
||||
public override long Seek(long offset, System.IO.SeekOrigin origin)
|
||||
{
|
||||
return _innerStream.Seek(_originalPosition + offset, origin) - _originalPosition;
|
||||
}
|
||||
|
||||
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
void IDisposable.Dispose()
|
||||
{
|
||||
Close();
|
||||
}
|
||||
|
||||
public override void Close()
|
||||
{
|
||||
base.Close();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// OffsetStream.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-27 12:50:35>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines logic for handling reading of zip archives embedded
|
||||
// into larger streams. The initial position of the stream serves as
|
||||
// the base offset for all future Seek() operations.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
internal class OffsetStream : System.IO.Stream, System.IDisposable
|
||||
{
|
||||
private Int64 _originalPosition;
|
||||
private Stream _innerStream;
|
||||
|
||||
public OffsetStream(Stream s)
|
||||
: base()
|
||||
{
|
||||
_originalPosition = s.Position;
|
||||
_innerStream = s;
|
||||
}
|
||||
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
return _innerStream.Read(buffer, offset, count);
|
||||
}
|
||||
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return _innerStream.CanRead; }
|
||||
}
|
||||
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return _innerStream.CanSeek; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override void Flush()
|
||||
{
|
||||
_innerStream.Flush();
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get
|
||||
{
|
||||
return _innerStream.Length;
|
||||
}
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { return _innerStream.Position - _originalPosition; }
|
||||
set { _innerStream.Position = _originalPosition + value; }
|
||||
}
|
||||
|
||||
|
||||
public override long Seek(long offset, System.IO.SeekOrigin origin)
|
||||
{
|
||||
return _innerStream.Seek(_originalPosition + offset, origin) - _originalPosition;
|
||||
}
|
||||
|
||||
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
void IDisposable.Dispose()
|
||||
{
|
||||
Close();
|
||||
}
|
||||
|
||||
public override void Close()
|
||||
{
|
||||
base.Close();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,51 +1,51 @@
|
||||
// ZipConstants.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006, 2007, 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-27 23:22:32>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines a few constants that are used in the project.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
using System;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
static class ZipConstants
|
||||
{
|
||||
public const UInt32 PackedToRemovableMedia = 0x30304b50;
|
||||
public const UInt32 Zip64EndOfCentralDirectoryRecordSignature = 0x06064b50;
|
||||
public const UInt32 Zip64EndOfCentralDirectoryLocatorSignature = 0x07064b50;
|
||||
public const UInt32 EndOfCentralDirectorySignature = 0x06054b50;
|
||||
public const int ZipEntrySignature = 0x04034b50;
|
||||
public const int ZipEntryDataDescriptorSignature = 0x08074b50;
|
||||
public const int SplitArchiveSignature = 0x08074b50;
|
||||
public const int ZipDirEntrySignature = 0x02014b50;
|
||||
|
||||
|
||||
// These are dictated by the Zip Spec.See APPNOTE.txt
|
||||
public const int AesKeySize = 192; // 128, 192, 256
|
||||
public const int AesBlockSize = 128; // ???
|
||||
|
||||
public const UInt16 AesAlgId128 = 0x660E;
|
||||
public const UInt16 AesAlgId192 = 0x660F;
|
||||
public const UInt16 AesAlgId256 = 0x6610;
|
||||
|
||||
}
|
||||
}
|
||||
// ZipConstants.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006, 2007, 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-August-27 23:22:32>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines a few constants that are used in the project.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
using System;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
static class ZipConstants
|
||||
{
|
||||
public const UInt32 PackedToRemovableMedia = 0x30304b50;
|
||||
public const UInt32 Zip64EndOfCentralDirectoryRecordSignature = 0x06064b50;
|
||||
public const UInt32 Zip64EndOfCentralDirectoryLocatorSignature = 0x07064b50;
|
||||
public const UInt32 EndOfCentralDirectorySignature = 0x06054b50;
|
||||
public const int ZipEntrySignature = 0x04034b50;
|
||||
public const int ZipEntryDataDescriptorSignature = 0x08074b50;
|
||||
public const int SplitArchiveSignature = 0x08074b50;
|
||||
public const int ZipDirEntrySignature = 0x02014b50;
|
||||
|
||||
|
||||
// These are dictated by the Zip Spec.See APPNOTE.txt
|
||||
public const int AesKeySize = 192; // 128, 192, 256
|
||||
public const int AesBlockSize = 128; // ???
|
||||
|
||||
public const UInt16 AesAlgId128 = 0x660E;
|
||||
public const UInt16 AesAlgId192 = 0x660F;
|
||||
public const UInt16 AesAlgId256 = 0x6610;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,455 +1,455 @@
|
||||
// ZipCrypto.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2008, 2009, 2011 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-28 06:30:59>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module provides the implementation for "traditional" Zip encryption.
|
||||
//
|
||||
// Created Tue Apr 15 17:39:56 2008
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
using System;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// This class implements the "traditional" or "classic" PKZip encryption,
|
||||
/// which today is considered to be weak. On the other hand it is
|
||||
/// ubiquitous. This class is intended for use only by the DotNetZip
|
||||
/// library.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// Most uses of the DotNetZip library will not involve direct calls into
|
||||
/// the ZipCrypto class. Instead, the ZipCrypto class is instantiated and
|
||||
/// used by the ZipEntry() class when encryption or decryption on an entry
|
||||
/// is employed. If for some reason you really wanted to use a weak
|
||||
/// encryption algorithm in some other application, you might use this
|
||||
/// library. But you would be much better off using one of the built-in
|
||||
/// strong encryption libraries in the .NET Framework, like the AES
|
||||
/// algorithm or SHA.
|
||||
/// </remarks>
|
||||
internal class ZipCrypto
|
||||
{
|
||||
/// <summary>
|
||||
/// The default constructor for ZipCrypto.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// This class is intended for internal use by the library only. It's
|
||||
/// probably not useful to you. Seriously. Stop reading this
|
||||
/// documentation. It's a waste of your time. Go do something else.
|
||||
/// Check the football scores. Go get an ice cream with a friend.
|
||||
/// Seriously.
|
||||
/// </remarks>
|
||||
///
|
||||
private ZipCrypto() { }
|
||||
|
||||
public static ZipCrypto ForWrite(string password)
|
||||
{
|
||||
ZipCrypto z = new ZipCrypto();
|
||||
if (password == null)
|
||||
throw new BadPasswordException("This entry requires a password.");
|
||||
z.InitCipher(password);
|
||||
return z;
|
||||
}
|
||||
|
||||
|
||||
public static ZipCrypto ForRead(string password, ZipEntry e)
|
||||
{
|
||||
System.IO.Stream s = e._archiveStream;
|
||||
e._WeakEncryptionHeader = new byte[12];
|
||||
byte[] eh = e._WeakEncryptionHeader;
|
||||
ZipCrypto z = new ZipCrypto();
|
||||
|
||||
if (password == null)
|
||||
throw new BadPasswordException("This entry requires a password.");
|
||||
|
||||
z.InitCipher(password);
|
||||
|
||||
ZipEntry.ReadWeakEncryptionHeader(s, eh);
|
||||
|
||||
// Decrypt the header. This has a side effect of "further initializing the
|
||||
// encryption keys" in the traditional zip encryption.
|
||||
byte[] DecryptedHeader = z.DecryptMessage(eh, eh.Length);
|
||||
|
||||
// CRC check
|
||||
// According to the pkzip spec, the final byte in the decrypted header
|
||||
// is the highest-order byte in the CRC. We check it here.
|
||||
if (DecryptedHeader[11] != (byte)((e._Crc32 >> 24) & 0xff))
|
||||
{
|
||||
// In the case that bit 3 of the general purpose bit flag is set to
|
||||
// indicate the presence of an 'Extended File Header' or a 'data
|
||||
// descriptor' (signature 0x08074b50), the last byte of the decrypted
|
||||
// header is sometimes compared with the high-order byte of the
|
||||
// lastmodified time, rather than the high-order byte of the CRC, to
|
||||
// verify the password.
|
||||
//
|
||||
// This is not documented in the PKWare Appnote.txt. It was
|
||||
// discovered this by analysis of the Crypt.c source file in the
|
||||
// InfoZip library http://www.info-zip.org/pub/infozip/
|
||||
//
|
||||
// The reason for this is that the CRC for a file cannot be known
|
||||
// until the entire contents of the file have been streamed. This
|
||||
// means a tool would have to read the file content TWICE in its
|
||||
// entirety in order to perform PKZIP encryption - once to compute
|
||||
// the CRC, and again to actually encrypt.
|
||||
//
|
||||
// This is so important for performance that using the timeblob as
|
||||
// the verification should be the standard practice for DotNetZip
|
||||
// when using PKZIP encryption. This implies that bit 3 must be
|
||||
// set. The downside is that some tools still cannot cope with ZIP
|
||||
// files that use bit 3. Therefore, DotNetZip DOES NOT force bit 3
|
||||
// when PKZIP encryption is in use, and instead, reads the stream
|
||||
// twice.
|
||||
//
|
||||
|
||||
if ((e._BitField & 0x0008) != 0x0008)
|
||||
{
|
||||
throw new BadPasswordException("The password did not match.");
|
||||
}
|
||||
else if (DecryptedHeader[11] != (byte)((e._TimeBlob >> 8) & 0xff))
|
||||
{
|
||||
throw new BadPasswordException("The password did not match.");
|
||||
}
|
||||
|
||||
// We have a good password.
|
||||
}
|
||||
else
|
||||
{
|
||||
// A-OK
|
||||
}
|
||||
return z;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// From AppNote.txt:
|
||||
/// unsigned char decrypt_byte()
|
||||
/// local unsigned short temp
|
||||
/// temp :=- Key(2) | 2
|
||||
/// decrypt_byte := (temp * (temp ^ 1)) bitshift-right 8
|
||||
/// end decrypt_byte
|
||||
/// </summary>
|
||||
private byte MagicByte
|
||||
{
|
||||
get
|
||||
{
|
||||
UInt16 t = (UInt16)((UInt16)(_Keys[2] & 0xFFFF) | 2);
|
||||
return (byte)((t * (t ^ 1)) >> 8);
|
||||
}
|
||||
}
|
||||
|
||||
// Decrypting:
|
||||
// From AppNote.txt:
|
||||
// loop for i from 0 to 11
|
||||
// C := buffer(i) ^ decrypt_byte()
|
||||
// update_keys(C)
|
||||
// buffer(i) := C
|
||||
// end loop
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Call this method on a cipher text to render the plaintext. You must
|
||||
/// first initialize the cipher with a call to InitCipher.
|
||||
/// </summary>
|
||||
///
|
||||
/// <example>
|
||||
/// <code>
|
||||
/// var cipher = new ZipCrypto();
|
||||
/// cipher.InitCipher(Password);
|
||||
/// // Decrypt the header. This has a side effect of "further initializing the
|
||||
/// // encryption keys" in the traditional zip encryption.
|
||||
/// byte[] DecryptedMessage = cipher.DecryptMessage(EncryptedMessage);
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <param name="cipherText">The encrypted buffer.</param>
|
||||
/// <param name="length">
|
||||
/// The number of bytes to encrypt.
|
||||
/// Should be less than or equal to CipherText.Length.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>The plaintext.</returns>
|
||||
public byte[] DecryptMessage(byte[] cipherText, int length)
|
||||
{
|
||||
if (cipherText == null)
|
||||
throw new ArgumentNullException("cipherText");
|
||||
|
||||
if (length > cipherText.Length)
|
||||
throw new ArgumentOutOfRangeException("length",
|
||||
"Bad length during Decryption: the length parameter must be smaller than or equal to the size of the destination array.");
|
||||
|
||||
byte[] plainText = new byte[length];
|
||||
for (int i = 0; i < length; i++)
|
||||
{
|
||||
byte C = (byte)(cipherText[i] ^ MagicByte);
|
||||
UpdateKeys(C);
|
||||
plainText[i] = C;
|
||||
}
|
||||
return plainText;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is the converse of DecryptMessage. It encrypts the plaintext
|
||||
/// and produces a ciphertext.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="plainText">The plain text buffer.</param>
|
||||
///
|
||||
/// <param name="length">
|
||||
/// The number of bytes to encrypt.
|
||||
/// Should be less than or equal to plainText.Length.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>The ciphertext.</returns>
|
||||
public byte[] EncryptMessage(byte[] plainText, int length)
|
||||
{
|
||||
if (plainText == null)
|
||||
throw new ArgumentNullException("plaintext");
|
||||
|
||||
if (length > plainText.Length)
|
||||
throw new ArgumentOutOfRangeException("length",
|
||||
"Bad length during Encryption: The length parameter must be smaller than or equal to the size of the destination array.");
|
||||
|
||||
byte[] cipherText = new byte[length];
|
||||
for (int i = 0; i < length; i++)
|
||||
{
|
||||
byte C = plainText[i];
|
||||
cipherText[i] = (byte)(plainText[i] ^ MagicByte);
|
||||
UpdateKeys(C);
|
||||
}
|
||||
return cipherText;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// This initializes the cipher with the given password.
|
||||
/// See AppNote.txt for details.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="passphrase">
|
||||
/// The passphrase for encrypting or decrypting with this cipher.
|
||||
/// </param>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <code>
|
||||
/// Step 1 - Initializing the encryption keys
|
||||
/// -----------------------------------------
|
||||
/// Start with these keys:
|
||||
/// Key(0) := 305419896 (0x12345678)
|
||||
/// Key(1) := 591751049 (0x23456789)
|
||||
/// Key(2) := 878082192 (0x34567890)
|
||||
///
|
||||
/// Then, initialize the keys with a password:
|
||||
///
|
||||
/// loop for i from 0 to length(password)-1
|
||||
/// update_keys(password(i))
|
||||
/// end loop
|
||||
///
|
||||
/// Where update_keys() is defined as:
|
||||
///
|
||||
/// update_keys(char):
|
||||
/// Key(0) := crc32(key(0),char)
|
||||
/// Key(1) := Key(1) + (Key(0) bitwiseAND 000000ffH)
|
||||
/// Key(1) := Key(1) * 134775813 + 1
|
||||
/// Key(2) := crc32(key(2),key(1) rightshift 24)
|
||||
/// end update_keys
|
||||
///
|
||||
/// Where crc32(old_crc,char) is a routine that given a CRC value and a
|
||||
/// character, returns an updated CRC value after applying the CRC-32
|
||||
/// algorithm described elsewhere in this document.
|
||||
///
|
||||
/// </code>
|
||||
///
|
||||
/// <para>
|
||||
/// After the keys are initialized, then you can use the cipher to
|
||||
/// encrypt the plaintext.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Essentially we encrypt the password with the keys, then discard the
|
||||
/// ciphertext for the password. This initializes the keys for later use.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
public void InitCipher(string passphrase)
|
||||
{
|
||||
byte[] p = SharedUtilities.StringToByteArray(passphrase);
|
||||
for (int i = 0; i < passphrase.Length; i++)
|
||||
UpdateKeys(p[i]);
|
||||
}
|
||||
|
||||
|
||||
private void UpdateKeys(byte byteValue)
|
||||
{
|
||||
_Keys[0] = (UInt32)crc32.ComputeCrc32((int)_Keys[0], byteValue);
|
||||
_Keys[1] = _Keys[1] + (byte)_Keys[0];
|
||||
_Keys[1] = _Keys[1] * 0x08088405 + 1;
|
||||
_Keys[2] = (UInt32)crc32.ComputeCrc32((int)_Keys[2], (byte)(_Keys[1] >> 24));
|
||||
}
|
||||
|
||||
///// <summary>
|
||||
///// The byte array representing the seed keys used.
|
||||
///// Get this after calling InitCipher. The 12 bytes represents
|
||||
///// what the zip spec calls the "EncryptionHeader".
|
||||
///// </summary>
|
||||
//public byte[] KeyHeader
|
||||
//{
|
||||
// get
|
||||
// {
|
||||
// byte[] result = new byte[12];
|
||||
// result[0] = (byte)(_Keys[0] & 0xff);
|
||||
// result[1] = (byte)((_Keys[0] >> 8) & 0xff);
|
||||
// result[2] = (byte)((_Keys[0] >> 16) & 0xff);
|
||||
// result[3] = (byte)((_Keys[0] >> 24) & 0xff);
|
||||
// result[4] = (byte)(_Keys[1] & 0xff);
|
||||
// result[5] = (byte)((_Keys[1] >> 8) & 0xff);
|
||||
// result[6] = (byte)((_Keys[1] >> 16) & 0xff);
|
||||
// result[7] = (byte)((_Keys[1] >> 24) & 0xff);
|
||||
// result[8] = (byte)(_Keys[2] & 0xff);
|
||||
// result[9] = (byte)((_Keys[2] >> 8) & 0xff);
|
||||
// result[10] = (byte)((_Keys[2] >> 16) & 0xff);
|
||||
// result[11] = (byte)((_Keys[2] >> 24) & 0xff);
|
||||
// return result;
|
||||
// }
|
||||
//}
|
||||
|
||||
// private fields for the crypto stuff:
|
||||
private UInt32[] _Keys = { 0x12345678, 0x23456789, 0x34567890 };
|
||||
private Ionic.Crc.CRC32 crc32 = new Ionic.Crc.CRC32();
|
||||
|
||||
}
|
||||
|
||||
internal enum CryptoMode
|
||||
{
|
||||
Encrypt,
|
||||
Decrypt
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A Stream for reading and concurrently decrypting data from a zip file,
|
||||
/// or for writing and concurrently encrypting data to a zip file.
|
||||
/// </summary>
|
||||
internal class ZipCipherStream : System.IO.Stream
|
||||
{
|
||||
private ZipCrypto _cipher;
|
||||
private System.IO.Stream _s;
|
||||
private CryptoMode _mode;
|
||||
|
||||
/// <summary> The constructor. </summary>
|
||||
/// <param name="s">The underlying stream</param>
|
||||
/// <param name="mode">To either encrypt or decrypt.</param>
|
||||
/// <param name="cipher">The pre-initialized ZipCrypto object.</param>
|
||||
public ZipCipherStream(System.IO.Stream s, ZipCrypto cipher, CryptoMode mode)
|
||||
: base()
|
||||
{
|
||||
_cipher = cipher;
|
||||
_s = s;
|
||||
_mode = mode;
|
||||
}
|
||||
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (_mode == CryptoMode.Encrypt)
|
||||
throw new NotSupportedException("This stream does not encrypt via Read()");
|
||||
|
||||
if (buffer == null)
|
||||
throw new ArgumentNullException("buffer");
|
||||
|
||||
byte[] db = new byte[count];
|
||||
int n = _s.Read(db, 0, count);
|
||||
byte[] decrypted = _cipher.DecryptMessage(db, n);
|
||||
for (int i = 0; i < n; i++)
|
||||
{
|
||||
buffer[offset + i] = decrypted[i];
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (_mode == CryptoMode.Decrypt)
|
||||
throw new NotSupportedException("This stream does not Decrypt via Write()");
|
||||
|
||||
if (buffer == null)
|
||||
throw new ArgumentNullException("buffer");
|
||||
|
||||
// workitem 7696
|
||||
if (count == 0) return;
|
||||
|
||||
byte[] plaintext = null;
|
||||
if (offset != 0)
|
||||
{
|
||||
plaintext = new byte[count];
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
plaintext[i] = buffer[offset + i];
|
||||
}
|
||||
}
|
||||
else plaintext = buffer;
|
||||
|
||||
byte[] encrypted = _cipher.EncryptMessage(plaintext, count);
|
||||
_s.Write(encrypted, 0, encrypted.Length);
|
||||
}
|
||||
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return (_mode == CryptoMode.Decrypt); }
|
||||
}
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return (_mode == CryptoMode.Encrypt); }
|
||||
}
|
||||
|
||||
public override void Flush()
|
||||
{
|
||||
//throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
set { throw new NotSupportedException(); }
|
||||
}
|
||||
public override long Seek(long offset, System.IO.SeekOrigin origin)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
// ZipCrypto.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2008, 2009, 2011 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-28 06:30:59>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module provides the implementation for "traditional" Zip encryption.
|
||||
//
|
||||
// Created Tue Apr 15 17:39:56 2008
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
using System;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// This class implements the "traditional" or "classic" PKZip encryption,
|
||||
/// which today is considered to be weak. On the other hand it is
|
||||
/// ubiquitous. This class is intended for use only by the DotNetZip
|
||||
/// library.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// Most uses of the DotNetZip library will not involve direct calls into
|
||||
/// the ZipCrypto class. Instead, the ZipCrypto class is instantiated and
|
||||
/// used by the ZipEntry() class when encryption or decryption on an entry
|
||||
/// is employed. If for some reason you really wanted to use a weak
|
||||
/// encryption algorithm in some other application, you might use this
|
||||
/// library. But you would be much better off using one of the built-in
|
||||
/// strong encryption libraries in the .NET Framework, like the AES
|
||||
/// algorithm or SHA.
|
||||
/// </remarks>
|
||||
internal class ZipCrypto
|
||||
{
|
||||
/// <summary>
|
||||
/// The default constructor for ZipCrypto.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// This class is intended for internal use by the library only. It's
|
||||
/// probably not useful to you. Seriously. Stop reading this
|
||||
/// documentation. It's a waste of your time. Go do something else.
|
||||
/// Check the football scores. Go get an ice cream with a friend.
|
||||
/// Seriously.
|
||||
/// </remarks>
|
||||
///
|
||||
private ZipCrypto() { }
|
||||
|
||||
public static ZipCrypto ForWrite(string password)
|
||||
{
|
||||
ZipCrypto z = new ZipCrypto();
|
||||
if (password == null)
|
||||
throw new BadPasswordException("This entry requires a password.");
|
||||
z.InitCipher(password);
|
||||
return z;
|
||||
}
|
||||
|
||||
|
||||
public static ZipCrypto ForRead(string password, ZipEntry e)
|
||||
{
|
||||
System.IO.Stream s = e._archiveStream;
|
||||
e._WeakEncryptionHeader = new byte[12];
|
||||
byte[] eh = e._WeakEncryptionHeader;
|
||||
ZipCrypto z = new ZipCrypto();
|
||||
|
||||
if (password == null)
|
||||
throw new BadPasswordException("This entry requires a password.");
|
||||
|
||||
z.InitCipher(password);
|
||||
|
||||
ZipEntry.ReadWeakEncryptionHeader(s, eh);
|
||||
|
||||
// Decrypt the header. This has a side effect of "further initializing the
|
||||
// encryption keys" in the traditional zip encryption.
|
||||
byte[] DecryptedHeader = z.DecryptMessage(eh, eh.Length);
|
||||
|
||||
// CRC check
|
||||
// According to the pkzip spec, the final byte in the decrypted header
|
||||
// is the highest-order byte in the CRC. We check it here.
|
||||
if (DecryptedHeader[11] != (byte)((e._Crc32 >> 24) & 0xff))
|
||||
{
|
||||
// In the case that bit 3 of the general purpose bit flag is set to
|
||||
// indicate the presence of an 'Extended File Header' or a 'data
|
||||
// descriptor' (signature 0x08074b50), the last byte of the decrypted
|
||||
// header is sometimes compared with the high-order byte of the
|
||||
// lastmodified time, rather than the high-order byte of the CRC, to
|
||||
// verify the password.
|
||||
//
|
||||
// This is not documented in the PKWare Appnote.txt. It was
|
||||
// discovered this by analysis of the Crypt.c source file in the
|
||||
// InfoZip library http://www.info-zip.org/pub/infozip/
|
||||
//
|
||||
// The reason for this is that the CRC for a file cannot be known
|
||||
// until the entire contents of the file have been streamed. This
|
||||
// means a tool would have to read the file content TWICE in its
|
||||
// entirety in order to perform PKZIP encryption - once to compute
|
||||
// the CRC, and again to actually encrypt.
|
||||
//
|
||||
// This is so important for performance that using the timeblob as
|
||||
// the verification should be the standard practice for DotNetZip
|
||||
// when using PKZIP encryption. This implies that bit 3 must be
|
||||
// set. The downside is that some tools still cannot cope with ZIP
|
||||
// files that use bit 3. Therefore, DotNetZip DOES NOT force bit 3
|
||||
// when PKZIP encryption is in use, and instead, reads the stream
|
||||
// twice.
|
||||
//
|
||||
|
||||
if ((e._BitField & 0x0008) != 0x0008)
|
||||
{
|
||||
throw new BadPasswordException("The password did not match.");
|
||||
}
|
||||
else if (DecryptedHeader[11] != (byte)((e._TimeBlob >> 8) & 0xff))
|
||||
{
|
||||
throw new BadPasswordException("The password did not match.");
|
||||
}
|
||||
|
||||
// We have a good password.
|
||||
}
|
||||
else
|
||||
{
|
||||
// A-OK
|
||||
}
|
||||
return z;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// From AppNote.txt:
|
||||
/// unsigned char decrypt_byte()
|
||||
/// local unsigned short temp
|
||||
/// temp :=- Key(2) | 2
|
||||
/// decrypt_byte := (temp * (temp ^ 1)) bitshift-right 8
|
||||
/// end decrypt_byte
|
||||
/// </summary>
|
||||
private byte MagicByte
|
||||
{
|
||||
get
|
||||
{
|
||||
UInt16 t = (UInt16)((UInt16)(_Keys[2] & 0xFFFF) | 2);
|
||||
return (byte)((t * (t ^ 1)) >> 8);
|
||||
}
|
||||
}
|
||||
|
||||
// Decrypting:
|
||||
// From AppNote.txt:
|
||||
// loop for i from 0 to 11
|
||||
// C := buffer(i) ^ decrypt_byte()
|
||||
// update_keys(C)
|
||||
// buffer(i) := C
|
||||
// end loop
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Call this method on a cipher text to render the plaintext. You must
|
||||
/// first initialize the cipher with a call to InitCipher.
|
||||
/// </summary>
|
||||
///
|
||||
/// <example>
|
||||
/// <code>
|
||||
/// var cipher = new ZipCrypto();
|
||||
/// cipher.InitCipher(Password);
|
||||
/// // Decrypt the header. This has a side effect of "further initializing the
|
||||
/// // encryption keys" in the traditional zip encryption.
|
||||
/// byte[] DecryptedMessage = cipher.DecryptMessage(EncryptedMessage);
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <param name="cipherText">The encrypted buffer.</param>
|
||||
/// <param name="length">
|
||||
/// The number of bytes to encrypt.
|
||||
/// Should be less than or equal to CipherText.Length.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>The plaintext.</returns>
|
||||
public byte[] DecryptMessage(byte[] cipherText, int length)
|
||||
{
|
||||
if (cipherText == null)
|
||||
throw new ArgumentNullException("cipherText");
|
||||
|
||||
if (length > cipherText.Length)
|
||||
throw new ArgumentOutOfRangeException("length",
|
||||
"Bad length during Decryption: the length parameter must be smaller than or equal to the size of the destination array.");
|
||||
|
||||
byte[] plainText = new byte[length];
|
||||
for (int i = 0; i < length; i++)
|
||||
{
|
||||
byte C = (byte)(cipherText[i] ^ MagicByte);
|
||||
UpdateKeys(C);
|
||||
plainText[i] = C;
|
||||
}
|
||||
return plainText;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is the converse of DecryptMessage. It encrypts the plaintext
|
||||
/// and produces a ciphertext.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="plainText">The plain text buffer.</param>
|
||||
///
|
||||
/// <param name="length">
|
||||
/// The number of bytes to encrypt.
|
||||
/// Should be less than or equal to plainText.Length.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>The ciphertext.</returns>
|
||||
public byte[] EncryptMessage(byte[] plainText, int length)
|
||||
{
|
||||
if (plainText == null)
|
||||
throw new ArgumentNullException("plaintext");
|
||||
|
||||
if (length > plainText.Length)
|
||||
throw new ArgumentOutOfRangeException("length",
|
||||
"Bad length during Encryption: The length parameter must be smaller than or equal to the size of the destination array.");
|
||||
|
||||
byte[] cipherText = new byte[length];
|
||||
for (int i = 0; i < length; i++)
|
||||
{
|
||||
byte C = plainText[i];
|
||||
cipherText[i] = (byte)(plainText[i] ^ MagicByte);
|
||||
UpdateKeys(C);
|
||||
}
|
||||
return cipherText;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// This initializes the cipher with the given password.
|
||||
/// See AppNote.txt for details.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="passphrase">
|
||||
/// The passphrase for encrypting or decrypting with this cipher.
|
||||
/// </param>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <code>
|
||||
/// Step 1 - Initializing the encryption keys
|
||||
/// -----------------------------------------
|
||||
/// Start with these keys:
|
||||
/// Key(0) := 305419896 (0x12345678)
|
||||
/// Key(1) := 591751049 (0x23456789)
|
||||
/// Key(2) := 878082192 (0x34567890)
|
||||
///
|
||||
/// Then, initialize the keys with a password:
|
||||
///
|
||||
/// loop for i from 0 to length(password)-1
|
||||
/// update_keys(password(i))
|
||||
/// end loop
|
||||
///
|
||||
/// Where update_keys() is defined as:
|
||||
///
|
||||
/// update_keys(char):
|
||||
/// Key(0) := crc32(key(0),char)
|
||||
/// Key(1) := Key(1) + (Key(0) bitwiseAND 000000ffH)
|
||||
/// Key(1) := Key(1) * 134775813 + 1
|
||||
/// Key(2) := crc32(key(2),key(1) rightshift 24)
|
||||
/// end update_keys
|
||||
///
|
||||
/// Where crc32(old_crc,char) is a routine that given a CRC value and a
|
||||
/// character, returns an updated CRC value after applying the CRC-32
|
||||
/// algorithm described elsewhere in this document.
|
||||
///
|
||||
/// </code>
|
||||
///
|
||||
/// <para>
|
||||
/// After the keys are initialized, then you can use the cipher to
|
||||
/// encrypt the plaintext.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Essentially we encrypt the password with the keys, then discard the
|
||||
/// ciphertext for the password. This initializes the keys for later use.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
public void InitCipher(string passphrase)
|
||||
{
|
||||
byte[] p = SharedUtilities.StringToByteArray(passphrase);
|
||||
for (int i = 0; i < passphrase.Length; i++)
|
||||
UpdateKeys(p[i]);
|
||||
}
|
||||
|
||||
|
||||
private void UpdateKeys(byte byteValue)
|
||||
{
|
||||
_Keys[0] = (UInt32)crc32.ComputeCrc32((int)_Keys[0], byteValue);
|
||||
_Keys[1] = _Keys[1] + (byte)_Keys[0];
|
||||
_Keys[1] = _Keys[1] * 0x08088405 + 1;
|
||||
_Keys[2] = (UInt32)crc32.ComputeCrc32((int)_Keys[2], (byte)(_Keys[1] >> 24));
|
||||
}
|
||||
|
||||
///// <summary>
|
||||
///// The byte array representing the seed keys used.
|
||||
///// Get this after calling InitCipher. The 12 bytes represents
|
||||
///// what the zip spec calls the "EncryptionHeader".
|
||||
///// </summary>
|
||||
//public byte[] KeyHeader
|
||||
//{
|
||||
// get
|
||||
// {
|
||||
// byte[] result = new byte[12];
|
||||
// result[0] = (byte)(_Keys[0] & 0xff);
|
||||
// result[1] = (byte)((_Keys[0] >> 8) & 0xff);
|
||||
// result[2] = (byte)((_Keys[0] >> 16) & 0xff);
|
||||
// result[3] = (byte)((_Keys[0] >> 24) & 0xff);
|
||||
// result[4] = (byte)(_Keys[1] & 0xff);
|
||||
// result[5] = (byte)((_Keys[1] >> 8) & 0xff);
|
||||
// result[6] = (byte)((_Keys[1] >> 16) & 0xff);
|
||||
// result[7] = (byte)((_Keys[1] >> 24) & 0xff);
|
||||
// result[8] = (byte)(_Keys[2] & 0xff);
|
||||
// result[9] = (byte)((_Keys[2] >> 8) & 0xff);
|
||||
// result[10] = (byte)((_Keys[2] >> 16) & 0xff);
|
||||
// result[11] = (byte)((_Keys[2] >> 24) & 0xff);
|
||||
// return result;
|
||||
// }
|
||||
//}
|
||||
|
||||
// private fields for the crypto stuff:
|
||||
private UInt32[] _Keys = { 0x12345678, 0x23456789, 0x34567890 };
|
||||
private Ionic.Crc.CRC32 crc32 = new Ionic.Crc.CRC32();
|
||||
|
||||
}
|
||||
|
||||
internal enum CryptoMode
|
||||
{
|
||||
Encrypt,
|
||||
Decrypt
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A Stream for reading and concurrently decrypting data from a zip file,
|
||||
/// or for writing and concurrently encrypting data to a zip file.
|
||||
/// </summary>
|
||||
internal class ZipCipherStream : System.IO.Stream
|
||||
{
|
||||
private ZipCrypto _cipher;
|
||||
private System.IO.Stream _s;
|
||||
private CryptoMode _mode;
|
||||
|
||||
/// <summary> The constructor. </summary>
|
||||
/// <param name="s">The underlying stream</param>
|
||||
/// <param name="mode">To either encrypt or decrypt.</param>
|
||||
/// <param name="cipher">The pre-initialized ZipCrypto object.</param>
|
||||
public ZipCipherStream(System.IO.Stream s, ZipCrypto cipher, CryptoMode mode)
|
||||
: base()
|
||||
{
|
||||
_cipher = cipher;
|
||||
_s = s;
|
||||
_mode = mode;
|
||||
}
|
||||
|
||||
public override int Read(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (_mode == CryptoMode.Encrypt)
|
||||
throw new NotSupportedException("This stream does not encrypt via Read()");
|
||||
|
||||
if (buffer == null)
|
||||
throw new ArgumentNullException("buffer");
|
||||
|
||||
byte[] db = new byte[count];
|
||||
int n = _s.Read(db, 0, count);
|
||||
byte[] decrypted = _cipher.DecryptMessage(db, n);
|
||||
for (int i = 0; i < n; i++)
|
||||
{
|
||||
buffer[offset + i] = decrypted[i];
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
public override void Write(byte[] buffer, int offset, int count)
|
||||
{
|
||||
if (_mode == CryptoMode.Decrypt)
|
||||
throw new NotSupportedException("This stream does not Decrypt via Write()");
|
||||
|
||||
if (buffer == null)
|
||||
throw new ArgumentNullException("buffer");
|
||||
|
||||
// workitem 7696
|
||||
if (count == 0) return;
|
||||
|
||||
byte[] plaintext = null;
|
||||
if (offset != 0)
|
||||
{
|
||||
plaintext = new byte[count];
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
plaintext[i] = buffer[offset + i];
|
||||
}
|
||||
}
|
||||
else plaintext = buffer;
|
||||
|
||||
byte[] encrypted = _cipher.EncryptMessage(plaintext, count);
|
||||
_s.Write(encrypted, 0, encrypted.Length);
|
||||
}
|
||||
|
||||
|
||||
public override bool CanRead
|
||||
{
|
||||
get { return (_mode == CryptoMode.Decrypt); }
|
||||
}
|
||||
public override bool CanSeek
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override bool CanWrite
|
||||
{
|
||||
get { return (_mode == CryptoMode.Encrypt); }
|
||||
}
|
||||
|
||||
public override void Flush()
|
||||
{
|
||||
//throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override long Length
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
}
|
||||
|
||||
public override long Position
|
||||
{
|
||||
get { throw new NotSupportedException(); }
|
||||
set { throw new NotSupportedException(); }
|
||||
}
|
||||
public override long Seek(long offset, System.IO.SeekOrigin origin)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
|
||||
public override void SetLength(long value)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,381 +1,381 @@
|
||||
// ZipDirEntry.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006-2011 Dino Chiesa .
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-11 12:03:03>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines members of the ZipEntry class for reading the
|
||||
// Zip file central directory.
|
||||
//
|
||||
// Created: Tue, 27 Mar 2007 15:30
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
partial class ZipEntry
|
||||
{
|
||||
/// <summary>
|
||||
/// True if the referenced entry is a directory.
|
||||
/// </summary>
|
||||
internal bool AttributesIndicateDirectory
|
||||
{
|
||||
get { return ((_InternalFileAttrs == 0) && ((_ExternalFileAttrs & 0x0010) == 0x0010)); }
|
||||
}
|
||||
|
||||
|
||||
internal void ResetDirEntry()
|
||||
{
|
||||
// __FileDataPosition is the position of the file data for an entry.
|
||||
// It is _RelativeOffsetOfLocalHeader + size of local header.
|
||||
|
||||
// We cannot know the __FileDataPosition until we read the local
|
||||
// header.
|
||||
|
||||
// The local header is not necessarily the same length as the record
|
||||
// in the central directory.
|
||||
|
||||
// Set to -1, to indicate we need to read this later.
|
||||
this.__FileDataPosition = -1;
|
||||
|
||||
// set _LengthOfHeader to 0, to indicate we need to read later.
|
||||
this._LengthOfHeader = 0;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides a human-readable string with information about the ZipEntry.
|
||||
/// </summary>
|
||||
public string Info
|
||||
{
|
||||
get
|
||||
{
|
||||
var builder = new System.Text.StringBuilder();
|
||||
builder
|
||||
.Append(string.Format(" ZipEntry: {0}\n", this.FileName))
|
||||
.Append(string.Format(" Version Made By: {0}\n", this._VersionMadeBy))
|
||||
.Append(string.Format(" Needed to extract: {0}\n", this.VersionNeeded));
|
||||
|
||||
if (this._IsDirectory)
|
||||
builder.Append(" Entry type: directory\n");
|
||||
else
|
||||
{
|
||||
builder.Append(string.Format(" File type: {0}\n", this._IsText? "text":"binary"))
|
||||
.Append(string.Format(" Compression: {0}\n", this.CompressionMethod))
|
||||
.Append(string.Format(" Compressed: 0x{0:X}\n", this.CompressedSize))
|
||||
.Append(string.Format(" Uncompressed: 0x{0:X}\n", this.UncompressedSize))
|
||||
.Append(string.Format(" CRC32: 0x{0:X8}\n", this._Crc32));
|
||||
}
|
||||
builder.Append(string.Format(" Disk Number: {0}\n", this._diskNumber));
|
||||
if (this._RelativeOffsetOfLocalHeader > 0xFFFFFFFF)
|
||||
builder
|
||||
.Append(string.Format(" Relative Offset: 0x{0:X16}\n", this._RelativeOffsetOfLocalHeader));
|
||||
else
|
||||
builder
|
||||
.Append(string.Format(" Relative Offset: 0x{0:X8}\n", this._RelativeOffsetOfLocalHeader));
|
||||
|
||||
builder
|
||||
.Append(string.Format(" Bit Field: 0x{0:X4}\n", this._BitField))
|
||||
.Append(string.Format(" Encrypted?: {0}\n", this._sourceIsEncrypted))
|
||||
.Append(string.Format(" Timeblob: 0x{0:X8}\n", this._TimeBlob))
|
||||
.Append(string.Format(" Time: {0}\n", Ionic.Zip.SharedUtilities.PackedToDateTime(this._TimeBlob)));
|
||||
|
||||
builder.Append(string.Format(" Is Zip64?: {0}\n", this._InputUsesZip64));
|
||||
if (!string.IsNullOrEmpty(this._Comment))
|
||||
{
|
||||
builder.Append(string.Format(" Comment: {0}\n", this._Comment));
|
||||
}
|
||||
builder.Append("\n");
|
||||
return builder.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// workitem 10330
|
||||
private class CopyHelper
|
||||
{
|
||||
private static System.Text.RegularExpressions.Regex re =
|
||||
new System.Text.RegularExpressions.Regex(" \\(copy (\\d+)\\)$");
|
||||
|
||||
private static int callCount = 0;
|
||||
|
||||
internal static string AppendCopyToFileName(string f)
|
||||
{
|
||||
callCount++;
|
||||
if (callCount > 25)
|
||||
throw new OverflowException("overflow while creating filename");
|
||||
|
||||
int n = 1;
|
||||
int r = f.LastIndexOf(".");
|
||||
|
||||
if (r == -1)
|
||||
{
|
||||
// there is no extension
|
||||
System.Text.RegularExpressions.Match m = re.Match(f);
|
||||
if (m.Success)
|
||||
{
|
||||
n = Int32.Parse(m.Groups[1].Value) + 1;
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, m.Index) + copy;
|
||||
}
|
||||
else
|
||||
{
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f + copy;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//System.Console.WriteLine("HasExtension");
|
||||
System.Text.RegularExpressions.Match m = re.Match(f.Substring(0, r));
|
||||
if (m.Success)
|
||||
{
|
||||
n = Int32.Parse(m.Groups[1].Value) + 1;
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, m.Index) + copy + f.Substring(r);
|
||||
}
|
||||
else
|
||||
{
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, r) + copy + f.Substring(r);
|
||||
}
|
||||
|
||||
//System.Console.WriteLine("returning f({0})", f);
|
||||
}
|
||||
return f;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Reads one entry from the zip directory structure in the zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="zf">
|
||||
/// The zipfile for which a directory entry will be read. From this param, the
|
||||
/// method gets the ReadStream and the expected text encoding
|
||||
/// (ProvisionalAlternateEncoding) which is used if the entry is not marked
|
||||
/// UTF-8.
|
||||
/// </param>
|
||||
///
|
||||
/// <param name="previouslySeen">
|
||||
/// a list of previously seen entry names; used to prevent duplicates.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>the entry read from the archive.</returns>
|
||||
internal static ZipEntry ReadDirEntry(ZipFile zf,
|
||||
Dictionary<String,Object> previouslySeen)
|
||||
{
|
||||
System.IO.Stream s = zf.ReadStream;
|
||||
System.Text.Encoding expectedEncoding = (zf.AlternateEncodingUsage == ZipOption.Always)
|
||||
? zf.AlternateEncoding
|
||||
: ZipFile.DefaultEncoding;
|
||||
|
||||
int signature = Ionic.Zip.SharedUtilities.ReadSignature(s);
|
||||
// return null if this is not a local file header signature
|
||||
if (IsNotValidZipDirEntrySig(signature))
|
||||
{
|
||||
s.Seek(-4, System.IO.SeekOrigin.Current);
|
||||
// workitem 10178
|
||||
Ionic.Zip.SharedUtilities.Workaround_Ladybug318918(s);
|
||||
|
||||
// Getting "not a ZipDirEntry signature" here is not always wrong or an
|
||||
// error. This can happen when walking through a zipfile. After the
|
||||
// last ZipDirEntry, we expect to read an
|
||||
// EndOfCentralDirectorySignature. When we get this is how we know
|
||||
// we've reached the end of the central directory.
|
||||
if (signature != ZipConstants.EndOfCentralDirectorySignature &&
|
||||
signature != ZipConstants.Zip64EndOfCentralDirectoryRecordSignature &&
|
||||
signature != ZipConstants.ZipEntrySignature // workitem 8299
|
||||
)
|
||||
{
|
||||
throw new BadReadException(String.Format(" Bad signature (0x{0:X8}) at position 0x{1:X8}", signature, s.Position));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
int bytesRead = 42 + 4;
|
||||
byte[] block = new byte[42];
|
||||
int n = s.Read(block, 0, block.Length);
|
||||
if (n != block.Length) return null;
|
||||
|
||||
int i = 0;
|
||||
ZipEntry zde = new ZipEntry();
|
||||
zde.AlternateEncoding = expectedEncoding;
|
||||
zde._Source = ZipEntrySource.ZipFile;
|
||||
zde._container = new ZipContainer(zf);
|
||||
|
||||
unchecked
|
||||
{
|
||||
zde._VersionMadeBy = (short)(block[i++] + block[i++] * 256);
|
||||
zde._VersionNeeded = (short)(block[i++] + block[i++] * 256);
|
||||
zde._BitField = (short)(block[i++] + block[i++] * 256);
|
||||
zde._CompressionMethod = (Int16)(block[i++] + block[i++] * 256);
|
||||
zde._TimeBlob = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
zde._LastModified = Ionic.Zip.SharedUtilities.PackedToDateTime(zde._TimeBlob);
|
||||
zde._timestamp |= ZipEntryTimestamp.DOS;
|
||||
|
||||
zde._Crc32 = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
zde._CompressedSize = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
zde._UncompressedSize = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
}
|
||||
|
||||
// preserve
|
||||
zde._CompressionMethod_FromZipFile = zde._CompressionMethod;
|
||||
|
||||
zde._filenameLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._extraFieldLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._commentLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._diskNumber = (UInt32)(block[i++] + block[i++] * 256);
|
||||
|
||||
zde._InternalFileAttrs = (short)(block[i++] + block[i++] * 256);
|
||||
zde._ExternalFileAttrs = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
|
||||
zde._RelativeOffsetOfLocalHeader = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
|
||||
// workitem 7801
|
||||
zde.IsText = ((zde._InternalFileAttrs & 0x01) == 0x01);
|
||||
|
||||
block = new byte[zde._filenameLength];
|
||||
n = s.Read(block, 0, block.Length);
|
||||
bytesRead += n;
|
||||
if ((zde._BitField & 0x0800) == 0x0800)
|
||||
{
|
||||
// UTF-8 is in use
|
||||
zde._FileNameInArchive = Ionic.Zip.SharedUtilities.Utf8StringFromBuffer(block);
|
||||
}
|
||||
else
|
||||
{
|
||||
zde._FileNameInArchive = Ionic.Zip.SharedUtilities.StringFromBuffer(block, expectedEncoding);
|
||||
}
|
||||
|
||||
// workitem 10330
|
||||
// insure unique entry names
|
||||
while (previouslySeen.ContainsKey(zde._FileNameInArchive))
|
||||
{
|
||||
zde._FileNameInArchive = CopyHelper.AppendCopyToFileName(zde._FileNameInArchive);
|
||||
zde._metadataChanged = true;
|
||||
}
|
||||
|
||||
if (zde.AttributesIndicateDirectory)
|
||||
zde.MarkAsDirectory(); // may append a slash to filename if nec.
|
||||
// workitem 6898
|
||||
else if (zde._FileNameInArchive.EndsWith("/")) zde.MarkAsDirectory();
|
||||
|
||||
zde._CompressedFileDataSize = zde._CompressedSize;
|
||||
if ((zde._BitField & 0x01) == 0x01)
|
||||
{
|
||||
// this may change after processing the Extra field
|
||||
zde._Encryption_FromZipFile = zde._Encryption =
|
||||
EncryptionAlgorithm.PkzipWeak;
|
||||
zde._sourceIsEncrypted = true;
|
||||
}
|
||||
|
||||
if (zde._extraFieldLength > 0)
|
||||
{
|
||||
zde._InputUsesZip64 = (zde._CompressedSize == 0xFFFFFFFF ||
|
||||
zde._UncompressedSize == 0xFFFFFFFF ||
|
||||
zde._RelativeOffsetOfLocalHeader == 0xFFFFFFFF);
|
||||
|
||||
// Console.WriteLine(" Input uses Z64?: {0}", zde._InputUsesZip64);
|
||||
|
||||
bytesRead += zde.ProcessExtraField(s, zde._extraFieldLength);
|
||||
zde._CompressedFileDataSize = zde._CompressedSize;
|
||||
}
|
||||
|
||||
// we've processed the extra field, so we know the encryption method is set now.
|
||||
if (zde._Encryption == EncryptionAlgorithm.PkzipWeak)
|
||||
{
|
||||
// the "encryption header" of 12 bytes precedes the file data
|
||||
zde._CompressedFileDataSize -= 12;
|
||||
}
|
||||
#if AESCRYPTO
|
||||
else if (zde.Encryption == EncryptionAlgorithm.WinZipAes128 ||
|
||||
zde.Encryption == EncryptionAlgorithm.WinZipAes256)
|
||||
{
|
||||
zde._CompressedFileDataSize = zde.CompressedSize -
|
||||
(ZipEntry.GetLengthOfCryptoHeaderBytes(zde.Encryption) + 10);
|
||||
zde._LengthOfTrailer = 10;
|
||||
}
|
||||
#endif
|
||||
|
||||
// tally the trailing descriptor
|
||||
if ((zde._BitField & 0x0008) == 0x0008)
|
||||
{
|
||||
// sig, CRC, Comp and Uncomp sizes
|
||||
if (zde._InputUsesZip64)
|
||||
zde._LengthOfTrailer += 24;
|
||||
else
|
||||
zde._LengthOfTrailer += 16;
|
||||
}
|
||||
|
||||
// workitem 12744
|
||||
zde.AlternateEncoding = ((zde._BitField & 0x0800) == 0x0800)
|
||||
? System.Text.Encoding.UTF8
|
||||
:expectedEncoding;
|
||||
|
||||
zde.AlternateEncodingUsage = ZipOption.Always;
|
||||
|
||||
if (zde._commentLength > 0)
|
||||
{
|
||||
block = new byte[zde._commentLength];
|
||||
n = s.Read(block, 0, block.Length);
|
||||
bytesRead += n;
|
||||
if ((zde._BitField & 0x0800) == 0x0800)
|
||||
{
|
||||
// UTF-8 is in use
|
||||
zde._Comment = Ionic.Zip.SharedUtilities.Utf8StringFromBuffer(block);
|
||||
}
|
||||
else
|
||||
{
|
||||
zde._Comment = Ionic.Zip.SharedUtilities.StringFromBuffer(block, expectedEncoding);
|
||||
}
|
||||
}
|
||||
//zde._LengthOfDirEntry = bytesRead;
|
||||
return zde;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Returns true if the passed-in value is a valid signature for a ZipDirEntry.
|
||||
/// </summary>
|
||||
/// <param name="signature">the candidate 4-byte signature value.</param>
|
||||
/// <returns>true, if the signature is valid according to the PKWare spec.</returns>
|
||||
internal static bool IsNotValidZipDirEntrySig(int signature)
|
||||
{
|
||||
return (signature != ZipConstants.ZipDirEntrySignature);
|
||||
}
|
||||
|
||||
|
||||
private Int16 _VersionMadeBy;
|
||||
private Int16 _InternalFileAttrs;
|
||||
private Int32 _ExternalFileAttrs;
|
||||
|
||||
//private Int32 _LengthOfDirEntry;
|
||||
private Int16 _filenameLength;
|
||||
private Int16 _extraFieldLength;
|
||||
private Int16 _commentLength;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
// ZipDirEntry.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006-2011 Dino Chiesa .
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-11 12:03:03>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines members of the ZipEntry class for reading the
|
||||
// Zip file central directory.
|
||||
//
|
||||
// Created: Tue, 27 Mar 2007 15:30
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
partial class ZipEntry
|
||||
{
|
||||
/// <summary>
|
||||
/// True if the referenced entry is a directory.
|
||||
/// </summary>
|
||||
internal bool AttributesIndicateDirectory
|
||||
{
|
||||
get { return ((_InternalFileAttrs == 0) && ((_ExternalFileAttrs & 0x0010) == 0x0010)); }
|
||||
}
|
||||
|
||||
|
||||
internal void ResetDirEntry()
|
||||
{
|
||||
// __FileDataPosition is the position of the file data for an entry.
|
||||
// It is _RelativeOffsetOfLocalHeader + size of local header.
|
||||
|
||||
// We cannot know the __FileDataPosition until we read the local
|
||||
// header.
|
||||
|
||||
// The local header is not necessarily the same length as the record
|
||||
// in the central directory.
|
||||
|
||||
// Set to -1, to indicate we need to read this later.
|
||||
this.__FileDataPosition = -1;
|
||||
|
||||
// set _LengthOfHeader to 0, to indicate we need to read later.
|
||||
this._LengthOfHeader = 0;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Provides a human-readable string with information about the ZipEntry.
|
||||
/// </summary>
|
||||
public string Info
|
||||
{
|
||||
get
|
||||
{
|
||||
var builder = new System.Text.StringBuilder();
|
||||
builder
|
||||
.Append(string.Format(" ZipEntry: {0}\n", this.FileName))
|
||||
.Append(string.Format(" Version Made By: {0}\n", this._VersionMadeBy))
|
||||
.Append(string.Format(" Needed to extract: {0}\n", this.VersionNeeded));
|
||||
|
||||
if (this._IsDirectory)
|
||||
builder.Append(" Entry type: directory\n");
|
||||
else
|
||||
{
|
||||
builder.Append(string.Format(" File type: {0}\n", this._IsText? "text":"binary"))
|
||||
.Append(string.Format(" Compression: {0}\n", this.CompressionMethod))
|
||||
.Append(string.Format(" Compressed: 0x{0:X}\n", this.CompressedSize))
|
||||
.Append(string.Format(" Uncompressed: 0x{0:X}\n", this.UncompressedSize))
|
||||
.Append(string.Format(" CRC32: 0x{0:X8}\n", this._Crc32));
|
||||
}
|
||||
builder.Append(string.Format(" Disk Number: {0}\n", this._diskNumber));
|
||||
if (this._RelativeOffsetOfLocalHeader > 0xFFFFFFFF)
|
||||
builder
|
||||
.Append(string.Format(" Relative Offset: 0x{0:X16}\n", this._RelativeOffsetOfLocalHeader));
|
||||
else
|
||||
builder
|
||||
.Append(string.Format(" Relative Offset: 0x{0:X8}\n", this._RelativeOffsetOfLocalHeader));
|
||||
|
||||
builder
|
||||
.Append(string.Format(" Bit Field: 0x{0:X4}\n", this._BitField))
|
||||
.Append(string.Format(" Encrypted?: {0}\n", this._sourceIsEncrypted))
|
||||
.Append(string.Format(" Timeblob: 0x{0:X8}\n", this._TimeBlob))
|
||||
.Append(string.Format(" Time: {0}\n", Ionic.Zip.SharedUtilities.PackedToDateTime(this._TimeBlob)));
|
||||
|
||||
builder.Append(string.Format(" Is Zip64?: {0}\n", this._InputUsesZip64));
|
||||
if (!string.IsNullOrEmpty(this._Comment))
|
||||
{
|
||||
builder.Append(string.Format(" Comment: {0}\n", this._Comment));
|
||||
}
|
||||
builder.Append("\n");
|
||||
return builder.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// workitem 10330
|
||||
private class CopyHelper
|
||||
{
|
||||
private static System.Text.RegularExpressions.Regex re =
|
||||
new System.Text.RegularExpressions.Regex(" \\(copy (\\d+)\\)$");
|
||||
|
||||
private static int callCount = 0;
|
||||
|
||||
internal static string AppendCopyToFileName(string f)
|
||||
{
|
||||
callCount++;
|
||||
if (callCount > 25)
|
||||
throw new OverflowException("overflow while creating filename");
|
||||
|
||||
int n = 1;
|
||||
int r = f.LastIndexOf(".");
|
||||
|
||||
if (r == -1)
|
||||
{
|
||||
// there is no extension
|
||||
System.Text.RegularExpressions.Match m = re.Match(f);
|
||||
if (m.Success)
|
||||
{
|
||||
n = Int32.Parse(m.Groups[1].Value) + 1;
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, m.Index) + copy;
|
||||
}
|
||||
else
|
||||
{
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f + copy;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
//System.Console.WriteLine("HasExtension");
|
||||
System.Text.RegularExpressions.Match m = re.Match(f.Substring(0, r));
|
||||
if (m.Success)
|
||||
{
|
||||
n = Int32.Parse(m.Groups[1].Value) + 1;
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, m.Index) + copy + f.Substring(r);
|
||||
}
|
||||
else
|
||||
{
|
||||
string copy = String.Format(" (copy {0})", n);
|
||||
f = f.Substring(0, r) + copy + f.Substring(r);
|
||||
}
|
||||
|
||||
//System.Console.WriteLine("returning f({0})", f);
|
||||
}
|
||||
return f;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Reads one entry from the zip directory structure in the zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <param name="zf">
|
||||
/// The zipfile for which a directory entry will be read. From this param, the
|
||||
/// method gets the ReadStream and the expected text encoding
|
||||
/// (ProvisionalAlternateEncoding) which is used if the entry is not marked
|
||||
/// UTF-8.
|
||||
/// </param>
|
||||
///
|
||||
/// <param name="previouslySeen">
|
||||
/// a list of previously seen entry names; used to prevent duplicates.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>the entry read from the archive.</returns>
|
||||
internal static ZipEntry ReadDirEntry(ZipFile zf,
|
||||
Dictionary<String,Object> previouslySeen)
|
||||
{
|
||||
System.IO.Stream s = zf.ReadStream;
|
||||
System.Text.Encoding expectedEncoding = (zf.AlternateEncodingUsage == ZipOption.Always)
|
||||
? zf.AlternateEncoding
|
||||
: ZipFile.DefaultEncoding;
|
||||
|
||||
int signature = Ionic.Zip.SharedUtilities.ReadSignature(s);
|
||||
// return null if this is not a local file header signature
|
||||
if (IsNotValidZipDirEntrySig(signature))
|
||||
{
|
||||
s.Seek(-4, System.IO.SeekOrigin.Current);
|
||||
// workitem 10178
|
||||
Ionic.Zip.SharedUtilities.Workaround_Ladybug318918(s);
|
||||
|
||||
// Getting "not a ZipDirEntry signature" here is not always wrong or an
|
||||
// error. This can happen when walking through a zipfile. After the
|
||||
// last ZipDirEntry, we expect to read an
|
||||
// EndOfCentralDirectorySignature. When we get this is how we know
|
||||
// we've reached the end of the central directory.
|
||||
if (signature != ZipConstants.EndOfCentralDirectorySignature &&
|
||||
signature != ZipConstants.Zip64EndOfCentralDirectoryRecordSignature &&
|
||||
signature != ZipConstants.ZipEntrySignature // workitem 8299
|
||||
)
|
||||
{
|
||||
throw new BadReadException(String.Format(" Bad signature (0x{0:X8}) at position 0x{1:X8}", signature, s.Position));
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
int bytesRead = 42 + 4;
|
||||
byte[] block = new byte[42];
|
||||
int n = s.Read(block, 0, block.Length);
|
||||
if (n != block.Length) return null;
|
||||
|
||||
int i = 0;
|
||||
ZipEntry zde = new ZipEntry();
|
||||
zde.AlternateEncoding = expectedEncoding;
|
||||
zde._Source = ZipEntrySource.ZipFile;
|
||||
zde._container = new ZipContainer(zf);
|
||||
|
||||
unchecked
|
||||
{
|
||||
zde._VersionMadeBy = (short)(block[i++] + block[i++] * 256);
|
||||
zde._VersionNeeded = (short)(block[i++] + block[i++] * 256);
|
||||
zde._BitField = (short)(block[i++] + block[i++] * 256);
|
||||
zde._CompressionMethod = (Int16)(block[i++] + block[i++] * 256);
|
||||
zde._TimeBlob = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
zde._LastModified = Ionic.Zip.SharedUtilities.PackedToDateTime(zde._TimeBlob);
|
||||
zde._timestamp |= ZipEntryTimestamp.DOS;
|
||||
|
||||
zde._Crc32 = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
zde._CompressedSize = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
zde._UncompressedSize = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
}
|
||||
|
||||
// preserve
|
||||
zde._CompressionMethod_FromZipFile = zde._CompressionMethod;
|
||||
|
||||
zde._filenameLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._extraFieldLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._commentLength = (short)(block[i++] + block[i++] * 256);
|
||||
zde._diskNumber = (UInt32)(block[i++] + block[i++] * 256);
|
||||
|
||||
zde._InternalFileAttrs = (short)(block[i++] + block[i++] * 256);
|
||||
zde._ExternalFileAttrs = block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256;
|
||||
|
||||
zde._RelativeOffsetOfLocalHeader = (uint)(block[i++] + block[i++] * 256 + block[i++] * 256 * 256 + block[i++] * 256 * 256 * 256);
|
||||
|
||||
// workitem 7801
|
||||
zde.IsText = ((zde._InternalFileAttrs & 0x01) == 0x01);
|
||||
|
||||
block = new byte[zde._filenameLength];
|
||||
n = s.Read(block, 0, block.Length);
|
||||
bytesRead += n;
|
||||
if ((zde._BitField & 0x0800) == 0x0800)
|
||||
{
|
||||
// UTF-8 is in use
|
||||
zde._FileNameInArchive = Ionic.Zip.SharedUtilities.Utf8StringFromBuffer(block);
|
||||
}
|
||||
else
|
||||
{
|
||||
zde._FileNameInArchive = Ionic.Zip.SharedUtilities.StringFromBuffer(block, expectedEncoding);
|
||||
}
|
||||
|
||||
// workitem 10330
|
||||
// insure unique entry names
|
||||
while (previouslySeen.ContainsKey(zde._FileNameInArchive))
|
||||
{
|
||||
zde._FileNameInArchive = CopyHelper.AppendCopyToFileName(zde._FileNameInArchive);
|
||||
zde._metadataChanged = true;
|
||||
}
|
||||
|
||||
if (zde.AttributesIndicateDirectory)
|
||||
zde.MarkAsDirectory(); // may append a slash to filename if nec.
|
||||
// workitem 6898
|
||||
else if (zde._FileNameInArchive.EndsWith("/")) zde.MarkAsDirectory();
|
||||
|
||||
zde._CompressedFileDataSize = zde._CompressedSize;
|
||||
if ((zde._BitField & 0x01) == 0x01)
|
||||
{
|
||||
// this may change after processing the Extra field
|
||||
zde._Encryption_FromZipFile = zde._Encryption =
|
||||
EncryptionAlgorithm.PkzipWeak;
|
||||
zde._sourceIsEncrypted = true;
|
||||
}
|
||||
|
||||
if (zde._extraFieldLength > 0)
|
||||
{
|
||||
zde._InputUsesZip64 = (zde._CompressedSize == 0xFFFFFFFF ||
|
||||
zde._UncompressedSize == 0xFFFFFFFF ||
|
||||
zde._RelativeOffsetOfLocalHeader == 0xFFFFFFFF);
|
||||
|
||||
// Console.WriteLine(" Input uses Z64?: {0}", zde._InputUsesZip64);
|
||||
|
||||
bytesRead += zde.ProcessExtraField(s, zde._extraFieldLength);
|
||||
zde._CompressedFileDataSize = zde._CompressedSize;
|
||||
}
|
||||
|
||||
// we've processed the extra field, so we know the encryption method is set now.
|
||||
if (zde._Encryption == EncryptionAlgorithm.PkzipWeak)
|
||||
{
|
||||
// the "encryption header" of 12 bytes precedes the file data
|
||||
zde._CompressedFileDataSize -= 12;
|
||||
}
|
||||
#if AESCRYPTO
|
||||
else if (zde.Encryption == EncryptionAlgorithm.WinZipAes128 ||
|
||||
zde.Encryption == EncryptionAlgorithm.WinZipAes256)
|
||||
{
|
||||
zde._CompressedFileDataSize = zde.CompressedSize -
|
||||
(ZipEntry.GetLengthOfCryptoHeaderBytes(zde.Encryption) + 10);
|
||||
zde._LengthOfTrailer = 10;
|
||||
}
|
||||
#endif
|
||||
|
||||
// tally the trailing descriptor
|
||||
if ((zde._BitField & 0x0008) == 0x0008)
|
||||
{
|
||||
// sig, CRC, Comp and Uncomp sizes
|
||||
if (zde._InputUsesZip64)
|
||||
zde._LengthOfTrailer += 24;
|
||||
else
|
||||
zde._LengthOfTrailer += 16;
|
||||
}
|
||||
|
||||
// workitem 12744
|
||||
zde.AlternateEncoding = ((zde._BitField & 0x0800) == 0x0800)
|
||||
? System.Text.Encoding.UTF8
|
||||
:expectedEncoding;
|
||||
|
||||
zde.AlternateEncodingUsage = ZipOption.Always;
|
||||
|
||||
if (zde._commentLength > 0)
|
||||
{
|
||||
block = new byte[zde._commentLength];
|
||||
n = s.Read(block, 0, block.Length);
|
||||
bytesRead += n;
|
||||
if ((zde._BitField & 0x0800) == 0x0800)
|
||||
{
|
||||
// UTF-8 is in use
|
||||
zde._Comment = Ionic.Zip.SharedUtilities.Utf8StringFromBuffer(block);
|
||||
}
|
||||
else
|
||||
{
|
||||
zde._Comment = Ionic.Zip.SharedUtilities.StringFromBuffer(block, expectedEncoding);
|
||||
}
|
||||
}
|
||||
//zde._LengthOfDirEntry = bytesRead;
|
||||
return zde;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Returns true if the passed-in value is a valid signature for a ZipDirEntry.
|
||||
/// </summary>
|
||||
/// <param name="signature">the candidate 4-byte signature value.</param>
|
||||
/// <returns>true, if the signature is valid according to the PKWare spec.</returns>
|
||||
internal static bool IsNotValidZipDirEntrySig(int signature)
|
||||
{
|
||||
return (signature != ZipConstants.ZipDirEntrySignature);
|
||||
}
|
||||
|
||||
|
||||
private Int16 _VersionMadeBy;
|
||||
private Int16 _InternalFileAttrs;
|
||||
private Int32 _ExternalFileAttrs;
|
||||
|
||||
//private Int32 _LengthOfDirEntry;
|
||||
private Int16 _filenameLength;
|
||||
private Int16 _extraFieldLength;
|
||||
private Int16 _commentLength;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,69 +1,69 @@
|
||||
// ZipEntrySource.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-November-19 11:18:42>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum that specifies the source of the ZipEntry.
|
||||
/// </summary>
|
||||
public enum ZipEntrySource
|
||||
{
|
||||
/// <summary>
|
||||
/// Default value. Invalid on a bonafide ZipEntry.
|
||||
/// </summary>
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// The entry was instantiated by calling AddFile() or another method that
|
||||
/// added an entry from the filesystem.
|
||||
/// </summary>
|
||||
FileSystem,
|
||||
|
||||
/// <summary>
|
||||
/// The entry was instantiated via <see cref="Ionic.Zip.ZipFile.AddEntry(string,string)"/> or
|
||||
/// <see cref="Ionic.Zip.ZipFile.AddEntry(string,System.IO.Stream)"/> .
|
||||
/// </summary>
|
||||
Stream,
|
||||
|
||||
/// <summary>
|
||||
/// The ZipEntry was instantiated by reading a zipfile.
|
||||
/// </summary>
|
||||
ZipFile,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be or was provided by the WriteDelegate.
|
||||
/// </summary>
|
||||
WriteDelegate,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be obtained from the stream dispensed by the <c>OpenDelegate</c>.
|
||||
/// The entry was instantiated via <see cref="Ionic.Zip.ZipFile.AddEntry(string,OpenDelegate,CloseDelegate)"/>.
|
||||
/// </summary>
|
||||
JitStream,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be or was obtained from a <c>ZipOutputStream</c>.
|
||||
/// </summary>
|
||||
ZipOutputStream,
|
||||
}
|
||||
|
||||
// ZipEntrySource.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-November-19 11:18:42>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum that specifies the source of the ZipEntry.
|
||||
/// </summary>
|
||||
public enum ZipEntrySource
|
||||
{
|
||||
/// <summary>
|
||||
/// Default value. Invalid on a bonafide ZipEntry.
|
||||
/// </summary>
|
||||
None = 0,
|
||||
|
||||
/// <summary>
|
||||
/// The entry was instantiated by calling AddFile() or another method that
|
||||
/// added an entry from the filesystem.
|
||||
/// </summary>
|
||||
FileSystem,
|
||||
|
||||
/// <summary>
|
||||
/// The entry was instantiated via <see cref="Ionic.Zip.ZipFile.AddEntry(string,string)"/> or
|
||||
/// <see cref="Ionic.Zip.ZipFile.AddEntry(string,System.IO.Stream)"/> .
|
||||
/// </summary>
|
||||
Stream,
|
||||
|
||||
/// <summary>
|
||||
/// The ZipEntry was instantiated by reading a zipfile.
|
||||
/// </summary>
|
||||
ZipFile,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be or was provided by the WriteDelegate.
|
||||
/// </summary>
|
||||
WriteDelegate,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be obtained from the stream dispensed by the <c>OpenDelegate</c>.
|
||||
/// The entry was instantiated via <see cref="Ionic.Zip.ZipFile.AddEntry(string,OpenDelegate,CloseDelegate)"/>.
|
||||
/// </summary>
|
||||
JitStream,
|
||||
|
||||
/// <summary>
|
||||
/// The content for the ZipEntry will be or was obtained from a <c>ZipOutputStream</c>.
|
||||
/// </summary>
|
||||
ZipOutputStream,
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,97 +1,97 @@
|
||||
// ZipErrorAction.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-September-01 18:43:20>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the ZipErrorAction enum, which provides
|
||||
// an action to take when errors occur when opening or reading
|
||||
// files to be added to a zip file.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum providing the options when an error occurs during opening or reading
|
||||
/// of a file or directory that is being saved to a zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This enum describes the actions that the library can take when an error occurs
|
||||
/// opening or reading a file, as it is being saved into a Zip archive.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// In some cases an error will occur when DotNetZip tries to open a file to be
|
||||
/// added to the zip archive. In other cases, an error might occur after the
|
||||
/// file has been successfully opened, while DotNetZip is reading the file.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The first problem might occur when calling AddDirectory() on a directory
|
||||
/// that contains a Clipper .dbf file; the file is locked by Clipper and
|
||||
/// cannot be opened by another process. An example of the second problem is
|
||||
/// the ERROR_LOCK_VIOLATION that results when a file is opened by another
|
||||
/// process, but not locked, and a range lock has been taken on the file.
|
||||
/// Microsoft Outlook takes range locks on .PST files.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public enum ZipErrorAction
|
||||
{
|
||||
/// <summary>
|
||||
/// Throw an exception when an error occurs while zipping. This is the default
|
||||
/// behavior. (For COM clients, this is a 0 (zero).)
|
||||
/// </summary>
|
||||
Throw,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs during zipping, for example a file cannot be opened,
|
||||
/// skip the file causing the error, and continue zipping. (For COM clients,
|
||||
/// this is a 1.)
|
||||
/// </summary>
|
||||
Skip,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs during zipping, for example a file cannot be opened,
|
||||
/// retry the operation that caused the error. Be careful with this option. If
|
||||
/// the error is not temporary, the library will retry forever. (For COM
|
||||
/// clients, this is a 2.)
|
||||
/// </summary>
|
||||
Retry,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs, invoke the zipError event. The event type used is
|
||||
/// <see cref="ZipProgressEventType.Error_Saving"/>. A typical use of this option:
|
||||
/// a GUI application may wish to pop up a dialog to allow the user to view the
|
||||
/// error that occurred, and choose an appropriate action. After your
|
||||
/// processing in the error event, if you want to skip the file, set <see
|
||||
/// cref="ZipEntry.ZipErrorAction"/> on the
|
||||
/// <c>ZipProgressEventArgs.CurrentEntry</c> to <c>Skip</c>. If you want the
|
||||
/// exception to be thrown, set <c>ZipErrorAction</c> on the <c>CurrentEntry</c>
|
||||
/// to <c>Throw</c>. If you want to cancel the zip, set
|
||||
/// <c>ZipProgressEventArgs.Cancel</c> to true. Cancelling differs from using
|
||||
/// Skip in that a cancel will not save any further entries, if there are any.
|
||||
/// (For COM clients, the value of this enum is a 3.)
|
||||
/// </summary>
|
||||
InvokeErrorEvent,
|
||||
}
|
||||
|
||||
}
|
||||
// ZipErrorAction.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-September-01 18:43:20>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the ZipErrorAction enum, which provides
|
||||
// an action to take when errors occur when opening or reading
|
||||
// files to be added to a zip file.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
/// <summary>
|
||||
/// An enum providing the options when an error occurs during opening or reading
|
||||
/// of a file or directory that is being saved to a zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This enum describes the actions that the library can take when an error occurs
|
||||
/// opening or reading a file, as it is being saved into a Zip archive.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// In some cases an error will occur when DotNetZip tries to open a file to be
|
||||
/// added to the zip archive. In other cases, an error might occur after the
|
||||
/// file has been successfully opened, while DotNetZip is reading the file.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The first problem might occur when calling AddDirectory() on a directory
|
||||
/// that contains a Clipper .dbf file; the file is locked by Clipper and
|
||||
/// cannot be opened by another process. An example of the second problem is
|
||||
/// the ERROR_LOCK_VIOLATION that results when a file is opened by another
|
||||
/// process, but not locked, and a range lock has been taken on the file.
|
||||
/// Microsoft Outlook takes range locks on .PST files.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public enum ZipErrorAction
|
||||
{
|
||||
/// <summary>
|
||||
/// Throw an exception when an error occurs while zipping. This is the default
|
||||
/// behavior. (For COM clients, this is a 0 (zero).)
|
||||
/// </summary>
|
||||
Throw,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs during zipping, for example a file cannot be opened,
|
||||
/// skip the file causing the error, and continue zipping. (For COM clients,
|
||||
/// this is a 1.)
|
||||
/// </summary>
|
||||
Skip,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs during zipping, for example a file cannot be opened,
|
||||
/// retry the operation that caused the error. Be careful with this option. If
|
||||
/// the error is not temporary, the library will retry forever. (For COM
|
||||
/// clients, this is a 2.)
|
||||
/// </summary>
|
||||
Retry,
|
||||
|
||||
/// <summary>
|
||||
/// When an error occurs, invoke the zipError event. The event type used is
|
||||
/// <see cref="ZipProgressEventType.Error_Saving"/>. A typical use of this option:
|
||||
/// a GUI application may wish to pop up a dialog to allow the user to view the
|
||||
/// error that occurred, and choose an appropriate action. After your
|
||||
/// processing in the error event, if you want to skip the file, set <see
|
||||
/// cref="ZipEntry.ZipErrorAction"/> on the
|
||||
/// <c>ZipProgressEventArgs.CurrentEntry</c> to <c>Skip</c>. If you want the
|
||||
/// exception to be thrown, set <c>ZipErrorAction</c> on the <c>CurrentEntry</c>
|
||||
/// to <c>Throw</c>. If you want to cancel the zip, set
|
||||
/// <c>ZipProgressEventArgs.Cancel</c> to true. Cancelling differs from using
|
||||
/// Skip in that a cancel will not save any further entries, if there are any.
|
||||
/// (For COM clients, the value of this enum is a 3.)
|
||||
/// </summary>
|
||||
InvokeErrorEvent,
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,352 +1,352 @@
|
||||
// ZipFile.Check.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009-2011 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-31 14:40:50>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the methods for doing Checks on zip files.
|
||||
// These are not necessary to include in the Reduced or CF
|
||||
// version of the library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
public partial class ZipFile
|
||||
{
|
||||
/// <summary>
|
||||
/// Checks a zip file to see if its directory is consistent.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory within a zip file can get out
|
||||
/// of synch with the entries in the zip file. This method checks the
|
||||
/// given zip file and returns true if this has occurred.
|
||||
/// </para>
|
||||
///
|
||||
/// <para> This method may take a long time to run for large zip files. </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact Framework
|
||||
/// versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Developers using COM can use the <see
|
||||
/// cref="ComHelper.CheckZip(String)">ComHelper.CheckZip(String)</see>
|
||||
/// method.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
///
|
||||
/// <seealso cref="FixZipDirectory(string)"/>
|
||||
/// <seealso cref="CheckZip(string,bool,System.IO.TextWriter)"/>
|
||||
public static bool CheckZip(string zipFileName)
|
||||
{
|
||||
return CheckZip(zipFileName, false, null);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Checks a zip file to see if its directory is consistent,
|
||||
/// and optionally fixes the directory if necessary.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory within a zip file can get out of
|
||||
/// synch with the entries in the zip file. This method checks the given
|
||||
/// zip file, and returns true if this has occurred. It also optionally
|
||||
/// fixes the zipfile, saving the fixed copy in <em>Name</em>_Fixed.zip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method may take a long time to run for large zip files. It
|
||||
/// will take even longer if the file actually needs to be fixed, and if
|
||||
/// <c>fixIfNecessary</c> is true.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact
|
||||
/// Framework versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <param name="fixIfNecessary">If true, the method will fix the zip file if
|
||||
/// necessary.</param>
|
||||
///
|
||||
/// <param name="writer">
|
||||
/// a TextWriter in which messages generated while checking will be written.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>true if the named zip is OK; false if the file needs to be fixed.</returns>
|
||||
///
|
||||
/// <seealso cref="CheckZip(string)"/>
|
||||
/// <seealso cref="FixZipDirectory(string)"/>
|
||||
public static bool CheckZip(string zipFileName, bool fixIfNecessary,
|
||||
TextWriter writer)
|
||||
|
||||
{
|
||||
ZipFile zip1 = null, zip2 = null;
|
||||
bool isOk = true;
|
||||
try
|
||||
{
|
||||
zip1 = new ZipFile();
|
||||
zip1.FullScan = true;
|
||||
zip1.Initialize(zipFileName);
|
||||
|
||||
zip2 = ZipFile.Read(zipFileName);
|
||||
|
||||
foreach (var e1 in zip1)
|
||||
{
|
||||
foreach (var e2 in zip2)
|
||||
{
|
||||
if (e1.FileName == e2.FileName)
|
||||
{
|
||||
if (e1._RelativeOffsetOfLocalHeader != e2._RelativeOffsetOfLocalHeader)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in RelativeOffsetOfLocalHeader (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._RelativeOffsetOfLocalHeader,
|
||||
e2._RelativeOffsetOfLocalHeader);
|
||||
}
|
||||
if (e1._CompressedSize != e2._CompressedSize)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in CompressedSize (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._CompressedSize,
|
||||
e2._CompressedSize);
|
||||
}
|
||||
if (e1._UncompressedSize != e2._UncompressedSize)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in UncompressedSize (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._UncompressedSize,
|
||||
e2._UncompressedSize);
|
||||
}
|
||||
if (e1.CompressionMethod != e2.CompressionMethod)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in CompressionMethod (0x{1:X4} != 0x{2:X4})",
|
||||
e1.FileName, e1.CompressionMethod,
|
||||
e2.CompressionMethod);
|
||||
}
|
||||
if (e1.Crc != e2.Crc)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in Crc32 (0x{1:X4} != 0x{2:X4})",
|
||||
e1.FileName, e1.Crc,
|
||||
e2.Crc);
|
||||
}
|
||||
|
||||
// found a match, so stop the inside loop
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
zip2.Dispose();
|
||||
zip2 = null;
|
||||
|
||||
if (!isOk && fixIfNecessary)
|
||||
{
|
||||
string newFileName = Path.GetFileNameWithoutExtension(zipFileName);
|
||||
newFileName = System.String.Format("{0}_fixed.zip", newFileName);
|
||||
zip1.Save(newFileName);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (zip1 != null) zip1.Dispose();
|
||||
if (zip2 != null) zip2.Dispose();
|
||||
}
|
||||
return isOk;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Rewrite the directory within a zipfile.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory in a zip file can get out of
|
||||
/// synch with the entries in the zip file. This method attempts to fix
|
||||
/// the zip file if this has occurred.
|
||||
/// </para>
|
||||
///
|
||||
/// <para> This can take a long time for large zip files. </para>
|
||||
///
|
||||
/// <para> This won't work if the zip file uses a non-standard
|
||||
/// code page - neither IBM437 nor UTF-8. </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact Framework
|
||||
/// versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Developers using COM can use the <see
|
||||
/// cref="ComHelper.FixZipDirectory(String)">ComHelper.FixZipDirectory(String)</see>
|
||||
/// method.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to fix.</param>
|
||||
///
|
||||
/// <seealso cref="CheckZip(string)"/>
|
||||
/// <seealso cref="CheckZip(string,bool,System.IO.TextWriter)"/>
|
||||
public static void FixZipDirectory(string zipFileName)
|
||||
{
|
||||
using (var zip = new ZipFile())
|
||||
{
|
||||
zip.FullScan = true;
|
||||
zip.Initialize(zipFileName);
|
||||
zip.Save(zipFileName);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Verify the password on a zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// Keep in mind that passwords in zipfiles are applied to
|
||||
/// zip entries, not to the entire zip file. So testing a
|
||||
/// zipfile for a particular password doesn't work in the
|
||||
/// general case. On the other hand, it's often the case
|
||||
/// that a single password will be used on all entries in a
|
||||
/// zip file. This method works for that case.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// There is no way to check a password without doing the
|
||||
/// decryption. So this code decrypts and extracts the given
|
||||
/// zipfile into <see cref="System.IO.Stream.Null"/>
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to fix.</param>
|
||||
///
|
||||
/// <param name="password">The password to check.</param>
|
||||
///
|
||||
/// <returns>a bool indicating whether the password matches.</returns>
|
||||
public static bool CheckZipPassword(string zipFileName, string password)
|
||||
{
|
||||
// workitem 13664
|
||||
bool success = false;
|
||||
try
|
||||
{
|
||||
using (ZipFile zip1 = ZipFile.Read(zipFileName))
|
||||
{
|
||||
foreach (var e in zip1)
|
||||
{
|
||||
if (!e.IsDirectory && e.UsesEncryption)
|
||||
{
|
||||
e.ExtractWithPassword(System.IO.Stream.Null, password);
|
||||
}
|
||||
}
|
||||
}
|
||||
success = true;
|
||||
}
|
||||
catch(Ionic.Zip.BadPasswordException) { }
|
||||
return success;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Provides a human-readable string with information about the ZipFile.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// The information string contains 10 lines or so, about each ZipEntry,
|
||||
/// describing whether encryption is in use, the compressed and uncompressed
|
||||
/// length of the entry, the offset of the entry, and so on. As a result the
|
||||
/// information string can be very long for zip files that contain many
|
||||
/// entries.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// This information is mostly useful for diagnostic purposes.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public string Info
|
||||
{
|
||||
get
|
||||
{
|
||||
var builder = new System.Text.StringBuilder();
|
||||
builder.Append(string.Format(" ZipFile: {0}\n", this.Name));
|
||||
if (!string.IsNullOrEmpty(this._Comment))
|
||||
{
|
||||
builder.Append(string.Format(" Comment: {0}\n", this._Comment));
|
||||
}
|
||||
if (this._versionMadeBy != 0)
|
||||
{
|
||||
builder.Append(string.Format(" version made by: 0x{0:X4}\n", this._versionMadeBy));
|
||||
}
|
||||
if (this._versionNeededToExtract != 0)
|
||||
{
|
||||
builder.Append(string.Format("needed to extract: 0x{0:X4}\n", this._versionNeededToExtract));
|
||||
}
|
||||
|
||||
builder.Append(string.Format(" uses ZIP64: {0}\n", this.InputUsesZip64));
|
||||
|
||||
builder.Append(string.Format(" disk with CD: {0}\n", this._diskNumberWithCd));
|
||||
if (this._OffsetOfCentralDirectory == 0xFFFFFFFF)
|
||||
builder.Append(string.Format(" CD64 offset: 0x{0:X16}\n", this._OffsetOfCentralDirectory64));
|
||||
else
|
||||
builder.Append(string.Format(" CD offset: 0x{0:X8}\n", this._OffsetOfCentralDirectory));
|
||||
builder.Append("\n");
|
||||
foreach (ZipEntry entry in this._entries.Values)
|
||||
{
|
||||
builder.Append(entry.Info);
|
||||
}
|
||||
return builder.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
// ZipFile.Check.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009-2011 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-31 14:40:50>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the methods for doing Checks on zip files.
|
||||
// These are not necessary to include in the Reduced or CF
|
||||
// version of the library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
public partial class ZipFile
|
||||
{
|
||||
/// <summary>
|
||||
/// Checks a zip file to see if its directory is consistent.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory within a zip file can get out
|
||||
/// of synch with the entries in the zip file. This method checks the
|
||||
/// given zip file and returns true if this has occurred.
|
||||
/// </para>
|
||||
///
|
||||
/// <para> This method may take a long time to run for large zip files. </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact Framework
|
||||
/// versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Developers using COM can use the <see
|
||||
/// cref="ComHelper.CheckZip(String)">ComHelper.CheckZip(String)</see>
|
||||
/// method.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <returns>true if the named zip file checks OK. Otherwise, false. </returns>
|
||||
///
|
||||
/// <seealso cref="FixZipDirectory(string)"/>
|
||||
/// <seealso cref="CheckZip(string,bool,System.IO.TextWriter)"/>
|
||||
public static bool CheckZip(string zipFileName)
|
||||
{
|
||||
return CheckZip(zipFileName, false, null);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Checks a zip file to see if its directory is consistent,
|
||||
/// and optionally fixes the directory if necessary.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory within a zip file can get out of
|
||||
/// synch with the entries in the zip file. This method checks the given
|
||||
/// zip file, and returns true if this has occurred. It also optionally
|
||||
/// fixes the zipfile, saving the fixed copy in <em>Name</em>_Fixed.zip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method may take a long time to run for large zip files. It
|
||||
/// will take even longer if the file actually needs to be fixed, and if
|
||||
/// <c>fixIfNecessary</c> is true.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact
|
||||
/// Framework versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to check.</param>
|
||||
///
|
||||
/// <param name="fixIfNecessary">If true, the method will fix the zip file if
|
||||
/// necessary.</param>
|
||||
///
|
||||
/// <param name="writer">
|
||||
/// a TextWriter in which messages generated while checking will be written.
|
||||
/// </param>
|
||||
///
|
||||
/// <returns>true if the named zip is OK; false if the file needs to be fixed.</returns>
|
||||
///
|
||||
/// <seealso cref="CheckZip(string)"/>
|
||||
/// <seealso cref="FixZipDirectory(string)"/>
|
||||
public static bool CheckZip(string zipFileName, bool fixIfNecessary,
|
||||
TextWriter writer)
|
||||
|
||||
{
|
||||
ZipFile zip1 = null, zip2 = null;
|
||||
bool isOk = true;
|
||||
try
|
||||
{
|
||||
zip1 = new ZipFile();
|
||||
zip1.FullScan = true;
|
||||
zip1.Initialize(zipFileName);
|
||||
|
||||
zip2 = ZipFile.Read(zipFileName);
|
||||
|
||||
foreach (var e1 in zip1)
|
||||
{
|
||||
foreach (var e2 in zip2)
|
||||
{
|
||||
if (e1.FileName == e2.FileName)
|
||||
{
|
||||
if (e1._RelativeOffsetOfLocalHeader != e2._RelativeOffsetOfLocalHeader)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in RelativeOffsetOfLocalHeader (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._RelativeOffsetOfLocalHeader,
|
||||
e2._RelativeOffsetOfLocalHeader);
|
||||
}
|
||||
if (e1._CompressedSize != e2._CompressedSize)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in CompressedSize (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._CompressedSize,
|
||||
e2._CompressedSize);
|
||||
}
|
||||
if (e1._UncompressedSize != e2._UncompressedSize)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in UncompressedSize (0x{1:X16} != 0x{2:X16})",
|
||||
e1.FileName, e1._UncompressedSize,
|
||||
e2._UncompressedSize);
|
||||
}
|
||||
if (e1.CompressionMethod != e2.CompressionMethod)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in CompressionMethod (0x{1:X4} != 0x{2:X4})",
|
||||
e1.FileName, e1.CompressionMethod,
|
||||
e2.CompressionMethod);
|
||||
}
|
||||
if (e1.Crc != e2.Crc)
|
||||
{
|
||||
isOk = false;
|
||||
if (writer != null)
|
||||
writer.WriteLine("{0}: mismatch in Crc32 (0x{1:X4} != 0x{2:X4})",
|
||||
e1.FileName, e1.Crc,
|
||||
e2.Crc);
|
||||
}
|
||||
|
||||
// found a match, so stop the inside loop
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
zip2.Dispose();
|
||||
zip2 = null;
|
||||
|
||||
if (!isOk && fixIfNecessary)
|
||||
{
|
||||
string newFileName = Path.GetFileNameWithoutExtension(zipFileName);
|
||||
newFileName = System.String.Format("{0}_fixed.zip", newFileName);
|
||||
zip1.Save(newFileName);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (zip1 != null) zip1.Dispose();
|
||||
if (zip2 != null) zip2.Dispose();
|
||||
}
|
||||
return isOk;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Rewrite the directory within a zipfile.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// In cases of data error, the directory in a zip file can get out of
|
||||
/// synch with the entries in the zip file. This method attempts to fix
|
||||
/// the zip file if this has occurred.
|
||||
/// </para>
|
||||
///
|
||||
/// <para> This can take a long time for large zip files. </para>
|
||||
///
|
||||
/// <para> This won't work if the zip file uses a non-standard
|
||||
/// code page - neither IBM437 nor UTF-8. </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method is not supported in the Reduced or Compact Framework
|
||||
/// versions of DotNetZip.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Developers using COM can use the <see
|
||||
/// cref="ComHelper.FixZipDirectory(String)">ComHelper.FixZipDirectory(String)</see>
|
||||
/// method.
|
||||
/// </para>
|
||||
///
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to fix.</param>
|
||||
///
|
||||
/// <seealso cref="CheckZip(string)"/>
|
||||
/// <seealso cref="CheckZip(string,bool,System.IO.TextWriter)"/>
|
||||
public static void FixZipDirectory(string zipFileName)
|
||||
{
|
||||
using (var zip = new ZipFile())
|
||||
{
|
||||
zip.FullScan = true;
|
||||
zip.Initialize(zipFileName);
|
||||
zip.Save(zipFileName);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Verify the password on a zip file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// Keep in mind that passwords in zipfiles are applied to
|
||||
/// zip entries, not to the entire zip file. So testing a
|
||||
/// zipfile for a particular password doesn't work in the
|
||||
/// general case. On the other hand, it's often the case
|
||||
/// that a single password will be used on all entries in a
|
||||
/// zip file. This method works for that case.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// There is no way to check a password without doing the
|
||||
/// decryption. So this code decrypts and extracts the given
|
||||
/// zipfile into <see cref="System.IO.Stream.Null"/>
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <param name="zipFileName">The filename to of the zip file to fix.</param>
|
||||
///
|
||||
/// <param name="password">The password to check.</param>
|
||||
///
|
||||
/// <returns>a bool indicating whether the password matches.</returns>
|
||||
public static bool CheckZipPassword(string zipFileName, string password)
|
||||
{
|
||||
// workitem 13664
|
||||
bool success = false;
|
||||
try
|
||||
{
|
||||
using (ZipFile zip1 = ZipFile.Read(zipFileName))
|
||||
{
|
||||
foreach (var e in zip1)
|
||||
{
|
||||
if (!e.IsDirectory && e.UsesEncryption)
|
||||
{
|
||||
e.ExtractWithPassword(System.IO.Stream.Null, password);
|
||||
}
|
||||
}
|
||||
}
|
||||
success = true;
|
||||
}
|
||||
catch(Ionic.Zip.BadPasswordException) { }
|
||||
return success;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Provides a human-readable string with information about the ZipFile.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// The information string contains 10 lines or so, about each ZipEntry,
|
||||
/// describing whether encryption is in use, the compressed and uncompressed
|
||||
/// length of the entry, the offset of the entry, and so on. As a result the
|
||||
/// information string can be very long for zip files that contain many
|
||||
/// entries.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// This information is mostly useful for diagnostic purposes.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
public string Info
|
||||
{
|
||||
get
|
||||
{
|
||||
var builder = new System.Text.StringBuilder();
|
||||
builder.Append(string.Format(" ZipFile: {0}\n", this.Name));
|
||||
if (!string.IsNullOrEmpty(this._Comment))
|
||||
{
|
||||
builder.Append(string.Format(" Comment: {0}\n", this._Comment));
|
||||
}
|
||||
if (this._versionMadeBy != 0)
|
||||
{
|
||||
builder.Append(string.Format(" version made by: 0x{0:X4}\n", this._versionMadeBy));
|
||||
}
|
||||
if (this._versionNeededToExtract != 0)
|
||||
{
|
||||
builder.Append(string.Format("needed to extract: 0x{0:X4}\n", this._versionNeededToExtract));
|
||||
}
|
||||
|
||||
builder.Append(string.Format(" uses ZIP64: {0}\n", this.InputUsesZip64));
|
||||
|
||||
builder.Append(string.Format(" disk with CD: {0}\n", this._diskNumberWithCd));
|
||||
if (this._OffsetOfCentralDirectory == 0xFFFFFFFF)
|
||||
builder.Append(string.Format(" CD64 offset: 0x{0:X16}\n", this._OffsetOfCentralDirectory64));
|
||||
else
|
||||
builder.Append(string.Format(" CD offset: 0x{0:X8}\n", this._OffsetOfCentralDirectory));
|
||||
builder.Append("\n");
|
||||
foreach (ZipEntry entry in this._entries.Values)
|
||||
{
|
||||
builder.Append(entry.Info);
|
||||
}
|
||||
return builder.ToString();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,298 +1,298 @@
|
||||
// ZipFile.Extract.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-31 14:45:18>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the methods for Extract operations on zip files.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
public partial class ZipFile
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// Extracts all of the items in the zip archive, to the specified path in the
|
||||
/// filesystem. The path can be relative or fully-qualified.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This method will extract all entries in the <c>ZipFile</c> to the
|
||||
/// specified path.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// If an extraction of a file from the zip archive would overwrite an
|
||||
/// existing file in the filesystem, the action taken is dictated by the
|
||||
/// ExtractExistingFile property, which overrides any setting you may have
|
||||
/// made on individual ZipEntry instances. By default, if you have not
|
||||
/// set that property on the <c>ZipFile</c> instance, the entry will not
|
||||
/// be extracted, the existing file will not be overwritten and an
|
||||
/// exception will be thrown. To change this, set the property, or use the
|
||||
/// <see cref="ZipFile.ExtractAll(string,
|
||||
/// Ionic.Zip.ExtractExistingFileAction)" /> overload that allows you to
|
||||
/// specify an ExtractExistingFileAction parameter.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The action to take when an extract would overwrite an existing file
|
||||
/// applies to all entries. If you want to set this on a per-entry basis,
|
||||
/// then you must use one of the <see
|
||||
/// cref="ZipEntry.Extract()">ZipEntry.Extract</see> methods.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will send verbose output messages to the <see
|
||||
/// cref="StatusMessageTextWriter"/>, if it is set on the <c>ZipFile</c>
|
||||
/// instance.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// You may wish to take advantage of the <c>ExtractProgress</c> event.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// About timestamps: When extracting a file entry from a zip archive, the
|
||||
/// extracted file gets the last modified time of the entry as stored in
|
||||
/// the archive. The archive may also store extended file timestamp
|
||||
/// information, including last accessed and created times. If these are
|
||||
/// present in the <c>ZipEntry</c>, then the extracted file will also get
|
||||
/// these times.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A Directory entry is somewhat different. It will get the times as
|
||||
/// described for a file entry, but, if there are file entries in the zip
|
||||
/// archive that, when extracted, appear in the just-created directory,
|
||||
/// then when those file entries are extracted, the last modified and last
|
||||
/// accessed times of the directory will change, as a side effect. The
|
||||
/// result is that after an extraction of a directory and a number of
|
||||
/// files within the directory, the last modified and last accessed
|
||||
/// timestamps on the directory will reflect the time that the last file
|
||||
/// was extracted into the directory, rather than the time stored in the
|
||||
/// zip archive for the directory.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// To compensate, when extracting an archive with <c>ExtractAll</c>,
|
||||
/// DotNetZip will extract all the file and directory entries as described
|
||||
/// above, but it will then make a second pass on the directories, and
|
||||
/// reset the times on the directories to reflect what is stored in the
|
||||
/// zip archive.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This compensation is performed only within the context of an
|
||||
/// <c>ExtractAll</c>. If you call <c>ZipEntry.Extract</c> on a directory
|
||||
/// entry, the timestamps on directory in the filesystem will reflect the
|
||||
/// times stored in the zip. If you then call <c>ZipEntry.Extract</c> on
|
||||
/// a file entry, which is extracted into the directory, the timestamps on
|
||||
/// the directory will be updated to the current time.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example extracts all the entries in a zip archive file, to the
|
||||
/// specified target directory. The extraction will overwrite any
|
||||
/// existing files silently.
|
||||
///
|
||||
/// <code>
|
||||
/// String TargetDirectory= "unpack";
|
||||
/// using(ZipFile zip= ZipFile.Read(ZipFileToExtract))
|
||||
/// {
|
||||
/// zip.ExtractExistingFile= ExtractExistingFileAction.OverwriteSilently;
|
||||
/// zip.ExtractAll(TargetDirectory);
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim TargetDirectory As String = "unpack"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// zip.ExtractExistingFile= ExtractExistingFileAction.OverwriteSilently
|
||||
/// zip.ExtractAll(TargetDirectory)
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <seealso cref="Ionic.Zip.ZipFile.ExtractProgress"/>
|
||||
/// <seealso cref="Ionic.Zip.ZipFile.ExtractExistingFile"/>
|
||||
///
|
||||
/// <param name="path">
|
||||
/// The path to which the contents of the zipfile will be extracted.
|
||||
/// The path can be relative or fully-qualified.
|
||||
/// </param>
|
||||
///
|
||||
public void ExtractAll(string path)
|
||||
{
|
||||
_InternalExtractAll(path, true);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Extracts all of the items in the zip archive, to the specified path in the
|
||||
/// filesystem, using the specified behavior when extraction would overwrite an
|
||||
/// existing file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will extract all entries in the <c>ZipFile</c> to the specified
|
||||
/// path. For an extraction that would overwrite an existing file, the behavior
|
||||
/// is dictated by <paramref name="extractExistingFile"/>, which overrides any
|
||||
/// setting you may have made on individual ZipEntry instances.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The action to take when an extract would overwrite an existing file
|
||||
/// applies to all entries. If you want to set this on a per-entry basis,
|
||||
/// then you must use <see cref="ZipEntry.Extract(String,
|
||||
/// ExtractExistingFileAction)" /> or one of the similar methods.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Calling this method is equivalent to setting the <see
|
||||
/// cref="ExtractExistingFile"/> property and then calling <see
|
||||
/// cref="ExtractAll(String)"/>.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will send verbose output messages to the
|
||||
/// <see cref="StatusMessageTextWriter"/>, if it is set on the <c>ZipFile</c> instance.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example extracts all the entries in a zip archive file, to the
|
||||
/// specified target directory. It does not overwrite any existing files.
|
||||
/// <code>
|
||||
/// String TargetDirectory= "c:\\unpack";
|
||||
/// using(ZipFile zip= ZipFile.Read(ZipFileToExtract))
|
||||
/// {
|
||||
/// zip.ExtractAll(TargetDirectory, ExtractExistingFileAction.DontOverwrite);
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim TargetDirectory As String = "c:\unpack"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// zip.ExtractAll(TargetDirectory, ExtractExistingFileAction.DontOverwrite)
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <param name="path">
|
||||
/// The path to which the contents of the zipfile will be extracted.
|
||||
/// The path can be relative or fully-qualified.
|
||||
/// </param>
|
||||
///
|
||||
/// <param name="extractExistingFile">
|
||||
/// The action to take if extraction would overwrite an existing file.
|
||||
/// </param>
|
||||
/// <seealso cref="ExtractSelectedEntries(String,ExtractExistingFileAction)"/>
|
||||
public void ExtractAll(string path, ExtractExistingFileAction extractExistingFile)
|
||||
{
|
||||
ExtractExistingFile = extractExistingFile;
|
||||
_InternalExtractAll(path, true);
|
||||
}
|
||||
|
||||
|
||||
private void _InternalExtractAll(string path, bool overrideExtractExistingProperty)
|
||||
{
|
||||
bool header = Verbose;
|
||||
_inExtractAll = true;
|
||||
try
|
||||
{
|
||||
OnExtractAllStarted(path);
|
||||
|
||||
int n = 0;
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
{
|
||||
if (header)
|
||||
{
|
||||
StatusMessageTextWriter.WriteLine("\n{1,-22} {2,-8} {3,4} {4,-8} {0}",
|
||||
"Name", "Modified", "Size", "Ratio", "Packed");
|
||||
StatusMessageTextWriter.WriteLine(new System.String('-', 72));
|
||||
header = false;
|
||||
}
|
||||
if (Verbose)
|
||||
{
|
||||
StatusMessageTextWriter.WriteLine("{1,-22} {2,-8} {3,4:F0}% {4,-8} {0}",
|
||||
e.FileName,
|
||||
e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"),
|
||||
e.UncompressedSize,
|
||||
e.CompressionRatio,
|
||||
e.CompressedSize);
|
||||
if (!String.IsNullOrEmpty(e.Comment))
|
||||
StatusMessageTextWriter.WriteLine(" Comment: {0}", e.Comment);
|
||||
}
|
||||
e.Password = _Password; // this may be null
|
||||
OnExtractEntry(n, true, e, path);
|
||||
if (overrideExtractExistingProperty)
|
||||
e.ExtractExistingFile = this.ExtractExistingFile;
|
||||
e.Extract(path);
|
||||
n++;
|
||||
OnExtractEntry(n, false, e, path);
|
||||
if (_extractOperationCanceled)
|
||||
break;
|
||||
}
|
||||
|
||||
if (!_extractOperationCanceled)
|
||||
{
|
||||
// workitem 8264:
|
||||
// now, set times on directory entries, again.
|
||||
// The problem is, extracting a file changes the times on the parent
|
||||
// directory. So after all files have been extracted, we have to
|
||||
// run through the directories again.
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
{
|
||||
// check if it is a directory
|
||||
if ((e.IsDirectory) || (e.FileName.EndsWith("/")))
|
||||
{
|
||||
string outputFile = (e.FileName.StartsWith("/"))
|
||||
? Path.Combine(path, e.FileName.Substring(1))
|
||||
: Path.Combine(path, e.FileName);
|
||||
|
||||
e._SetTimes(outputFile, false);
|
||||
}
|
||||
}
|
||||
OnExtractAllCompleted(path);
|
||||
}
|
||||
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
||||
_inExtractAll = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
// ZipFile.Extract.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2009 Dino Chiesa.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2011-July-31 14:45:18>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines the methods for Extract operations on zip files.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
public partial class ZipFile
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// Extracts all of the items in the zip archive, to the specified path in the
|
||||
/// filesystem. The path can be relative or fully-qualified.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// <para>
|
||||
/// This method will extract all entries in the <c>ZipFile</c> to the
|
||||
/// specified path.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// If an extraction of a file from the zip archive would overwrite an
|
||||
/// existing file in the filesystem, the action taken is dictated by the
|
||||
/// ExtractExistingFile property, which overrides any setting you may have
|
||||
/// made on individual ZipEntry instances. By default, if you have not
|
||||
/// set that property on the <c>ZipFile</c> instance, the entry will not
|
||||
/// be extracted, the existing file will not be overwritten and an
|
||||
/// exception will be thrown. To change this, set the property, or use the
|
||||
/// <see cref="ZipFile.ExtractAll(string,
|
||||
/// Ionic.Zip.ExtractExistingFileAction)" /> overload that allows you to
|
||||
/// specify an ExtractExistingFileAction parameter.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The action to take when an extract would overwrite an existing file
|
||||
/// applies to all entries. If you want to set this on a per-entry basis,
|
||||
/// then you must use one of the <see
|
||||
/// cref="ZipEntry.Extract()">ZipEntry.Extract</see> methods.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will send verbose output messages to the <see
|
||||
/// cref="StatusMessageTextWriter"/>, if it is set on the <c>ZipFile</c>
|
||||
/// instance.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// You may wish to take advantage of the <c>ExtractProgress</c> event.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// About timestamps: When extracting a file entry from a zip archive, the
|
||||
/// extracted file gets the last modified time of the entry as stored in
|
||||
/// the archive. The archive may also store extended file timestamp
|
||||
/// information, including last accessed and created times. If these are
|
||||
/// present in the <c>ZipEntry</c>, then the extracted file will also get
|
||||
/// these times.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// A Directory entry is somewhat different. It will get the times as
|
||||
/// described for a file entry, but, if there are file entries in the zip
|
||||
/// archive that, when extracted, appear in the just-created directory,
|
||||
/// then when those file entries are extracted, the last modified and last
|
||||
/// accessed times of the directory will change, as a side effect. The
|
||||
/// result is that after an extraction of a directory and a number of
|
||||
/// files within the directory, the last modified and last accessed
|
||||
/// timestamps on the directory will reflect the time that the last file
|
||||
/// was extracted into the directory, rather than the time stored in the
|
||||
/// zip archive for the directory.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// To compensate, when extracting an archive with <c>ExtractAll</c>,
|
||||
/// DotNetZip will extract all the file and directory entries as described
|
||||
/// above, but it will then make a second pass on the directories, and
|
||||
/// reset the times on the directories to reflect what is stored in the
|
||||
/// zip archive.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This compensation is performed only within the context of an
|
||||
/// <c>ExtractAll</c>. If you call <c>ZipEntry.Extract</c> on a directory
|
||||
/// entry, the timestamps on directory in the filesystem will reflect the
|
||||
/// times stored in the zip. If you then call <c>ZipEntry.Extract</c> on
|
||||
/// a file entry, which is extracted into the directory, the timestamps on
|
||||
/// the directory will be updated to the current time.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example extracts all the entries in a zip archive file, to the
|
||||
/// specified target directory. The extraction will overwrite any
|
||||
/// existing files silently.
|
||||
///
|
||||
/// <code>
|
||||
/// String TargetDirectory= "unpack";
|
||||
/// using(ZipFile zip= ZipFile.Read(ZipFileToExtract))
|
||||
/// {
|
||||
/// zip.ExtractExistingFile= ExtractExistingFileAction.OverwriteSilently;
|
||||
/// zip.ExtractAll(TargetDirectory);
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim TargetDirectory As String = "unpack"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// zip.ExtractExistingFile= ExtractExistingFileAction.OverwriteSilently
|
||||
/// zip.ExtractAll(TargetDirectory)
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <seealso cref="Ionic.Zip.ZipFile.ExtractProgress"/>
|
||||
/// <seealso cref="Ionic.Zip.ZipFile.ExtractExistingFile"/>
|
||||
///
|
||||
/// <param name="path">
|
||||
/// The path to which the contents of the zipfile will be extracted.
|
||||
/// The path can be relative or fully-qualified.
|
||||
/// </param>
|
||||
///
|
||||
public void ExtractAll(string path)
|
||||
{
|
||||
_InternalExtractAll(path, true);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Extracts all of the items in the zip archive, to the specified path in the
|
||||
/// filesystem, using the specified behavior when extraction would overwrite an
|
||||
/// existing file.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will extract all entries in the <c>ZipFile</c> to the specified
|
||||
/// path. For an extraction that would overwrite an existing file, the behavior
|
||||
/// is dictated by <paramref name="extractExistingFile"/>, which overrides any
|
||||
/// setting you may have made on individual ZipEntry instances.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// The action to take when an extract would overwrite an existing file
|
||||
/// applies to all entries. If you want to set this on a per-entry basis,
|
||||
/// then you must use <see cref="ZipEntry.Extract(String,
|
||||
/// ExtractExistingFileAction)" /> or one of the similar methods.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// Calling this method is equivalent to setting the <see
|
||||
/// cref="ExtractExistingFile"/> property and then calling <see
|
||||
/// cref="ExtractAll(String)"/>.
|
||||
/// </para>
|
||||
///
|
||||
/// <para>
|
||||
/// This method will send verbose output messages to the
|
||||
/// <see cref="StatusMessageTextWriter"/>, if it is set on the <c>ZipFile</c> instance.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example extracts all the entries in a zip archive file, to the
|
||||
/// specified target directory. It does not overwrite any existing files.
|
||||
/// <code>
|
||||
/// String TargetDirectory= "c:\\unpack";
|
||||
/// using(ZipFile zip= ZipFile.Read(ZipFileToExtract))
|
||||
/// {
|
||||
/// zip.ExtractAll(TargetDirectory, ExtractExistingFileAction.DontOverwrite);
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim TargetDirectory As String = "c:\unpack"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// zip.ExtractAll(TargetDirectory, ExtractExistingFileAction.DontOverwrite)
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <param name="path">
|
||||
/// The path to which the contents of the zipfile will be extracted.
|
||||
/// The path can be relative or fully-qualified.
|
||||
/// </param>
|
||||
///
|
||||
/// <param name="extractExistingFile">
|
||||
/// The action to take if extraction would overwrite an existing file.
|
||||
/// </param>
|
||||
/// <seealso cref="ExtractSelectedEntries(String,ExtractExistingFileAction)"/>
|
||||
public void ExtractAll(string path, ExtractExistingFileAction extractExistingFile)
|
||||
{
|
||||
ExtractExistingFile = extractExistingFile;
|
||||
_InternalExtractAll(path, true);
|
||||
}
|
||||
|
||||
|
||||
private void _InternalExtractAll(string path, bool overrideExtractExistingProperty)
|
||||
{
|
||||
bool header = Verbose;
|
||||
_inExtractAll = true;
|
||||
try
|
||||
{
|
||||
OnExtractAllStarted(path);
|
||||
|
||||
int n = 0;
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
{
|
||||
if (header)
|
||||
{
|
||||
StatusMessageTextWriter.WriteLine("\n{1,-22} {2,-8} {3,4} {4,-8} {0}",
|
||||
"Name", "Modified", "Size", "Ratio", "Packed");
|
||||
StatusMessageTextWriter.WriteLine(new System.String('-', 72));
|
||||
header = false;
|
||||
}
|
||||
if (Verbose)
|
||||
{
|
||||
StatusMessageTextWriter.WriteLine("{1,-22} {2,-8} {3,4:F0}% {4,-8} {0}",
|
||||
e.FileName,
|
||||
e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"),
|
||||
e.UncompressedSize,
|
||||
e.CompressionRatio,
|
||||
e.CompressedSize);
|
||||
if (!String.IsNullOrEmpty(e.Comment))
|
||||
StatusMessageTextWriter.WriteLine(" Comment: {0}", e.Comment);
|
||||
}
|
||||
e.Password = _Password; // this may be null
|
||||
OnExtractEntry(n, true, e, path);
|
||||
if (overrideExtractExistingProperty)
|
||||
e.ExtractExistingFile = this.ExtractExistingFile;
|
||||
e.Extract(path);
|
||||
n++;
|
||||
OnExtractEntry(n, false, e, path);
|
||||
if (_extractOperationCanceled)
|
||||
break;
|
||||
}
|
||||
|
||||
if (!_extractOperationCanceled)
|
||||
{
|
||||
// workitem 8264:
|
||||
// now, set times on directory entries, again.
|
||||
// The problem is, extracting a file changes the times on the parent
|
||||
// directory. So after all files have been extracted, we have to
|
||||
// run through the directories again.
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
{
|
||||
// check if it is a directory
|
||||
if ((e.IsDirectory) || (e.FileName.EndsWith("/")))
|
||||
{
|
||||
string outputFile = (e.FileName.StartsWith("/"))
|
||||
? Path.Combine(path, e.FileName.Substring(1))
|
||||
: Path.Combine(path, e.FileName);
|
||||
|
||||
e._SetTimes(outputFile, false);
|
||||
}
|
||||
}
|
||||
OnExtractAllCompleted(path);
|
||||
}
|
||||
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
||||
_inExtractAll = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,154 +1,154 @@
|
||||
// ZipFile.x-IEnumerable.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006, 2007, 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-December-26 15:13:26>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines smoe methods for IEnumerable support. It is
|
||||
// particularly important for COM to have these things in a separate module.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
// For some weird reason, the method with the DispId(-4) attribute, which is used as
|
||||
// the _NewEnum() method, and which is required to get enumeration to work from COM
|
||||
// environments like VBScript and Javascript (etc) must be the LAST MEMBER in the
|
||||
// source. In the event of Partial classes, it needs to be the last member defined
|
||||
// in the last source module. The source modules are ordered alphabetically by
|
||||
// filename. Not sure why this is true. In any case, we put the enumeration stuff
|
||||
// here in this oddly-named module, for this reason.
|
||||
//
|
||||
|
||||
|
||||
|
||||
public partial class ZipFile
|
||||
{
|
||||
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Generic IEnumerator support, for use of a ZipFile in an enumeration.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// You probably do not want to call <c>GetEnumerator</c> explicitly. Instead
|
||||
/// it is implicitly called when you use a <see langword="foreach"/> loop in C#, or a
|
||||
/// <c>For Each</c> loop in VB.NET.
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example reads a zipfile of a given name, then enumerates the
|
||||
/// entries in that zip file, and displays the information about each
|
||||
/// entry on the Console.
|
||||
/// <code>
|
||||
/// using (ZipFile zip = ZipFile.Read(zipfile))
|
||||
/// {
|
||||
/// bool header = true;
|
||||
/// foreach (ZipEntry e in zip)
|
||||
/// {
|
||||
/// if (header)
|
||||
/// {
|
||||
/// System.Console.WriteLine("Zipfile: {0}", zip.Name);
|
||||
/// System.Console.WriteLine("Version Needed: 0x{0:X2}", e.VersionNeeded);
|
||||
/// System.Console.WriteLine("BitField: 0x{0:X2}", e.BitField);
|
||||
/// System.Console.WriteLine("Compression Method: 0x{0:X2}", e.CompressionMethod);
|
||||
/// System.Console.WriteLine("\n{1,-22} {2,-6} {3,4} {4,-8} {0}",
|
||||
/// "Filename", "Modified", "Size", "Ratio", "Packed");
|
||||
/// System.Console.WriteLine(new System.String('-', 72));
|
||||
/// header = false;
|
||||
/// }
|
||||
///
|
||||
/// System.Console.WriteLine("{1,-22} {2,-6} {3,4:F0}% {4,-8} {0}",
|
||||
/// e.FileName,
|
||||
/// e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"),
|
||||
/// e.UncompressedSize,
|
||||
/// e.CompressionRatio,
|
||||
/// e.CompressedSize);
|
||||
///
|
||||
/// e.Extract();
|
||||
/// }
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim ZipFileToExtract As String = "c:\foo.zip"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// Dim header As Boolean = True
|
||||
/// Dim e As ZipEntry
|
||||
/// For Each e In zip
|
||||
/// If header Then
|
||||
/// Console.WriteLine("Zipfile: {0}", zip.Name)
|
||||
/// Console.WriteLine("Version Needed: 0x{0:X2}", e.VersionNeeded)
|
||||
/// Console.WriteLine("BitField: 0x{0:X2}", e.BitField)
|
||||
/// Console.WriteLine("Compression Method: 0x{0:X2}", e.CompressionMethod)
|
||||
/// Console.WriteLine(ChrW(10) & "{1,-22} {2,-6} {3,4} {4,-8} {0}", _
|
||||
/// "Filename", "Modified", "Size", "Ratio", "Packed" )
|
||||
/// Console.WriteLine(New String("-"c, 72))
|
||||
/// header = False
|
||||
/// End If
|
||||
/// Console.WriteLine("{1,-22} {2,-6} {3,4:F0}% {4,-8} {0}", _
|
||||
/// e.FileName, _
|
||||
/// e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"), _
|
||||
/// e.UncompressedSize, _
|
||||
/// e.CompressionRatio, _
|
||||
/// e.CompressedSize )
|
||||
/// e.Extract
|
||||
/// Next
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <returns>A generic enumerator suitable for use within a foreach loop.</returns>
|
||||
public System.Collections.Generic.IEnumerator<ZipEntry> GetEnumerator()
|
||||
{
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
yield return e;
|
||||
}
|
||||
|
||||
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
|
||||
{
|
||||
return GetEnumerator();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// An IEnumerator, for use of a ZipFile in a foreach construct.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// This method is included for COM support. An application generally does not call
|
||||
/// this method directly. It is called implicitly by COM clients when enumerating
|
||||
/// the entries in the ZipFile instance. In VBScript, this is done with a <c>For Each</c>
|
||||
/// statement. In Javascript, this is done with <c>new Enumerator(zipfile)</c>.
|
||||
/// </remarks>
|
||||
///
|
||||
/// <returns>
|
||||
/// The IEnumerator over the entries in the ZipFile.
|
||||
/// </returns>
|
||||
[System.Runtime.InteropServices.DispId(-4)]
|
||||
public System.Collections.IEnumerator GetNewEnum() // the name of this method is not significant
|
||||
{
|
||||
return GetEnumerator();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
// ZipFile.x-IEnumerable.cs
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// Copyright (c) 2006, 2007, 2008, 2009 Dino Chiesa and Microsoft Corporation.
|
||||
// All rights reserved.
|
||||
//
|
||||
// This code module is part of DotNetZip, a zipfile class library.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This code is licensed under the Microsoft Public License.
|
||||
// See the file License.txt for the license details.
|
||||
// More info on: http://dotnetzip.codeplex.com
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// last saved (in emacs):
|
||||
// Time-stamp: <2009-December-26 15:13:26>
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
//
|
||||
// This module defines smoe methods for IEnumerable support. It is
|
||||
// particularly important for COM to have these things in a separate module.
|
||||
//
|
||||
// ------------------------------------------------------------------
|
||||
|
||||
|
||||
namespace Ionic.Zip
|
||||
{
|
||||
|
||||
// For some weird reason, the method with the DispId(-4) attribute, which is used as
|
||||
// the _NewEnum() method, and which is required to get enumeration to work from COM
|
||||
// environments like VBScript and Javascript (etc) must be the LAST MEMBER in the
|
||||
// source. In the event of Partial classes, it needs to be the last member defined
|
||||
// in the last source module. The source modules are ordered alphabetically by
|
||||
// filename. Not sure why this is true. In any case, we put the enumeration stuff
|
||||
// here in this oddly-named module, for this reason.
|
||||
//
|
||||
|
||||
|
||||
|
||||
public partial class ZipFile
|
||||
{
|
||||
|
||||
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Generic IEnumerator support, for use of a ZipFile in an enumeration.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// You probably do not want to call <c>GetEnumerator</c> explicitly. Instead
|
||||
/// it is implicitly called when you use a <see langword="foreach"/> loop in C#, or a
|
||||
/// <c>For Each</c> loop in VB.NET.
|
||||
/// </remarks>
|
||||
///
|
||||
/// <example>
|
||||
/// This example reads a zipfile of a given name, then enumerates the
|
||||
/// entries in that zip file, and displays the information about each
|
||||
/// entry on the Console.
|
||||
/// <code>
|
||||
/// using (ZipFile zip = ZipFile.Read(zipfile))
|
||||
/// {
|
||||
/// bool header = true;
|
||||
/// foreach (ZipEntry e in zip)
|
||||
/// {
|
||||
/// if (header)
|
||||
/// {
|
||||
/// System.Console.WriteLine("Zipfile: {0}", zip.Name);
|
||||
/// System.Console.WriteLine("Version Needed: 0x{0:X2}", e.VersionNeeded);
|
||||
/// System.Console.WriteLine("BitField: 0x{0:X2}", e.BitField);
|
||||
/// System.Console.WriteLine("Compression Method: 0x{0:X2}", e.CompressionMethod);
|
||||
/// System.Console.WriteLine("\n{1,-22} {2,-6} {3,4} {4,-8} {0}",
|
||||
/// "Filename", "Modified", "Size", "Ratio", "Packed");
|
||||
/// System.Console.WriteLine(new System.String('-', 72));
|
||||
/// header = false;
|
||||
/// }
|
||||
///
|
||||
/// System.Console.WriteLine("{1,-22} {2,-6} {3,4:F0}% {4,-8} {0}",
|
||||
/// e.FileName,
|
||||
/// e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"),
|
||||
/// e.UncompressedSize,
|
||||
/// e.CompressionRatio,
|
||||
/// e.CompressedSize);
|
||||
///
|
||||
/// e.Extract();
|
||||
/// }
|
||||
/// }
|
||||
/// </code>
|
||||
///
|
||||
/// <code lang="VB">
|
||||
/// Dim ZipFileToExtract As String = "c:\foo.zip"
|
||||
/// Using zip As ZipFile = ZipFile.Read(ZipFileToExtract)
|
||||
/// Dim header As Boolean = True
|
||||
/// Dim e As ZipEntry
|
||||
/// For Each e In zip
|
||||
/// If header Then
|
||||
/// Console.WriteLine("Zipfile: {0}", zip.Name)
|
||||
/// Console.WriteLine("Version Needed: 0x{0:X2}", e.VersionNeeded)
|
||||
/// Console.WriteLine("BitField: 0x{0:X2}", e.BitField)
|
||||
/// Console.WriteLine("Compression Method: 0x{0:X2}", e.CompressionMethod)
|
||||
/// Console.WriteLine(ChrW(10) & "{1,-22} {2,-6} {3,4} {4,-8} {0}", _
|
||||
/// "Filename", "Modified", "Size", "Ratio", "Packed" )
|
||||
/// Console.WriteLine(New String("-"c, 72))
|
||||
/// header = False
|
||||
/// End If
|
||||
/// Console.WriteLine("{1,-22} {2,-6} {3,4:F0}% {4,-8} {0}", _
|
||||
/// e.FileName, _
|
||||
/// e.LastModified.ToString("yyyy-MM-dd HH:mm:ss"), _
|
||||
/// e.UncompressedSize, _
|
||||
/// e.CompressionRatio, _
|
||||
/// e.CompressedSize )
|
||||
/// e.Extract
|
||||
/// Next
|
||||
/// End Using
|
||||
/// </code>
|
||||
/// </example>
|
||||
///
|
||||
/// <returns>A generic enumerator suitable for use within a foreach loop.</returns>
|
||||
public System.Collections.Generic.IEnumerator<ZipEntry> GetEnumerator()
|
||||
{
|
||||
foreach (ZipEntry e in _entries.Values)
|
||||
yield return e;
|
||||
}
|
||||
|
||||
System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()
|
||||
{
|
||||
return GetEnumerator();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// An IEnumerator, for use of a ZipFile in a foreach construct.
|
||||
/// </summary>
|
||||
///
|
||||
/// <remarks>
|
||||
/// This method is included for COM support. An application generally does not call
|
||||
/// this method directly. It is called implicitly by COM clients when enumerating
|
||||
/// the entries in the ZipFile instance. In VBScript, this is done with a <c>For Each</c>
|
||||
/// statement. In Javascript, this is done with <c>new Enumerator(zipfile)</c>.
|
||||
/// </remarks>
|
||||
///
|
||||
/// <returns>
|
||||
/// The IEnumerator over the entries in the ZipFile.
|
||||
/// </returns>
|
||||
[System.Runtime.InteropServices.DispId(-4)]
|
||||
public System.Collections.IEnumerator GetNewEnum() // the name of this method is not significant
|
||||
{
|
||||
return GetEnumerator();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user