Removed the redundant byte-array-to-string method from the MD5 module, and added a using directive.

Added some additional logging to better diagnose issues with VSS/LVM snapshots.
This commit is contained in:
Kenneth Skovhede
2018-05-09 10:44:32 +02:00
parent eb6fdc71c1
commit 2b54bb9415
9 changed files with 81 additions and 54 deletions
+13
View File
@@ -214,6 +214,19 @@ namespace Duplicati.Library.Logging
WriteMessage(LogMessageType.Verbose, tag, id, null, message, arguments);
}
/// <summary>
/// Writes a verbose message to the current log destination
/// </summary>
/// <param name="message">The message to write</param>
/// <param name="tag">The tag-type for this message</param>
/// <param name="id">The message id</param>
/// <param name="ex">The exception to log</param>
/// <param name="arguments">The message format arguments</param>
public static void WriteVerboseMessage(string tag, string id, Exception ex, string message, params object[] arguments)
{
WriteMessage(LogMessageType.Verbose, tag, id, ex, message, arguments);
}
/// <summary>
/// Writes a profiling message to the current log destination
/// </summary>
@@ -82,7 +82,8 @@ namespace Duplicati.Library.Main.Operation.Backup
}
else
{
bool AttributeFilter(string root, string path, FileAttributes attr) => AttributeFilterAsync(root, path, attr, snapshot, sourcefilter, hardlinkPolicy, symlinkPolicy, hardlinkmap, attributeFilter, enumeratefilter, ignorenames, mixinqueue).WaitForTask().Result;
Library.Utility.Utility.EnumerationFilterDelegate AttributeFilter = (root, path, attr) =>
AttributeFilterAsync(root, path, attr, snapshot, sourcefilter, hardlinkPolicy, symlinkPolicy, hardlinkmap, attributeFilter, enumeratefilter, ignorenames, mixinqueue).WaitForTask().Result;
if (journalService != null)
{
@@ -90,9 +91,9 @@ namespace Duplicati.Library.Main.Operation.Backup
sources = journalService.GetModifiedSources(AttributeFilter);
}
worklist = snapshot.EnumerateFilesAndFolders(sources, AttributeFilter, (rootpath, path, ex) =>
worklist = snapshot.EnumerateFilesAndFolders(sources, AttributeFilter, (rootpath, errorpath, ex) =>
{
Logging.Log.WriteWarningMessage(FILTER_LOGTAG, "FileAccessError", ex, "Error reported while accessing file: {0}", path);
Logging.Log.WriteWarningMessage(FILTER_LOGTAG, "FileAccessError", ex, "Error reported while accessing file: {0}", errorpath);
});
}
+11 -9
View File
@@ -34,6 +34,14 @@ namespace Duplicati.Library.Snapshots
/// </summary>
public sealed class LinuxSnapshot : SnapshotBase
{
/// <summary>
/// The tag used for logging messages
/// </summary>
public static readonly string LOGTAG = Logging.Log.LogTagFromType<WindowsSnapshot>();
/// <summary>
/// Helper to have access to the System.IO calls without the interface layer
/// </summary>
private static SystemIOLinux SYS_IO = new SystemIOLinux();
/// <summary>
@@ -85,9 +93,9 @@ namespace Duplicati.Library.Snapshots
{
Dispose();
}
catch
catch (Exception ex)
{
// ignored
Logging.Log.WriteVerboseMessage(LOGTAG, "SnapshotCleanupError", ex, "Failed to clean up after error");
}
throw;
@@ -97,8 +105,6 @@ namespace Duplicati.Library.Snapshots
/// <inheritdoc />
protected override void Dispose(bool disposing)
{
Exception exs = null;
if (m_snapShots != null)
{
if (disposing)
@@ -107,7 +113,7 @@ namespace Duplicati.Library.Snapshots
foreach(var s in m_snapShots)
{
try { s.Dispose(); }
catch (Exception ex) { exs = ex; }
catch (Exception ex) { Logging.Log.WriteVerboseMessage(LOGTAG, "SnapshotCloseError", ex, "Failed to close a snapshot"); }
}
}
@@ -116,10 +122,6 @@ namespace Duplicati.Library.Snapshots
}
base.Dispose(disposing);
// Report errors, if any
if (exs != null)
throw exs;
}
/// <summary>
@@ -547,6 +547,7 @@ namespace Duplicati.Library.Snapshots
}
}
[Serializable]
public class UsnJournalSoftFailureException : Exception
{
public UsnJournalSoftFailureException()
@@ -64,7 +64,7 @@ namespace Duplicati.Library.Snapshots
// get filter identifying current source filter / sources configuration
// ReSharper disable once PossibleMultipleEnumeration
var configHash = emitFilter.GetFilterHash() + MD5HashHelper.GetHashString(MD5HashHelper.GetHash(m_sources));
var configHash = emitFilter.GetFilterHash() + Utility.Utility.ByteArrayAsHexString(MD5HashHelper.GetHash(m_sources));
// create lookup for journal data
var journalDataDict = prevJournalData.ToDictionary(data => data.Volume);
+33 -28
View File
@@ -37,6 +37,11 @@ namespace Duplicati.Library.Snapshots
/// </summary>
public sealed class WindowsSnapshot : SnapshotBase
{
/// <summary>
/// The tag used for logging messages
/// </summary>
public static readonly string LOGTAG = Logging.Log.LogTagFromType<WindowsSnapshot>();
/// <summary>
/// The main reference to the backup controller
/// </summary>
@@ -161,9 +166,9 @@ namespace Duplicati.Library.Snapshots
m_mappedDrives.Add(d = new DefineDosDevice(m_volumeMap[k]));
m_volumeMap[k] = Utility.Utility.AppendDirSeparator(d.Drive);
}
catch
catch(Exception ex)
{
// ignored
Logging.Log.WriteVerboseMessage(LOGTAG, "SubstMappingfailed", ex, "Failed to map VSS path {0} to drive", k);
}
}
}
@@ -175,9 +180,9 @@ namespace Duplicati.Library.Snapshots
{
Dispose();
}
catch
catch(Exception ex)
{
// ignored
Logging.Log.WriteVerboseMessage(LOGTAG, "VSSCleanupOnError", ex, "Failed during VSS error cleanup");
}
throw;
@@ -387,7 +392,7 @@ namespace Duplicati.Library.Snapshots
foreach (var kvp in m_volumeReverseMap)
{
if (snapshotPath.StartsWith(kvp.Key))
if (snapshotPath.StartsWith(kvp.Key, Utility.Utility.ClientFilenameStringComparision))
return Path.Combine(kvp.Value, snapshotPath.Substring(kvp.Key.Length));
}
@@ -442,40 +447,40 @@ namespace Duplicati.Library.Snapshots
m_mappedDrives = null;
}
}
catch
catch (Exception ex)
{
// ignored
}
try
{
m_backup?.BackupComplete();
}
catch
{
// ignored
}
Logging.Log.WriteVerboseMessage(LOGTAG, "MappedDriveCleanupError", ex, "Failed during VSS mapped drive unmapping");
}
try
{
m_backup?.BackupComplete();
}
catch (Exception ex)
{
Logging.Log.WriteVerboseMessage(LOGTAG, "VSSTerminateError", ex, "Failed to signal VSS completion");
}
try
{
if (m_backup != null)
{
foreach (var g in m_volumes.Values)
{
try
{
m_backup.DeleteSnapshot(g, false);
}
catch
{
// ignored
}
{
try
{
m_backup.DeleteSnapshot(g, false);
}
catch (Exception ex)
{
Logging.Log.WriteVerboseMessage(LOGTAG, "VSSSnapShotDeleteError", ex, "Failed to close VSS snapshot");
}
}
}
}
catch
catch (Exception ex)
{
// ignored
Logging.Log.WriteVerboseMessage(LOGTAG, "VSSSnapShotDeleteCleanError", ex, "Failed during VSS esnapshot closing");
}
if (m_backup != null)
@@ -352,7 +352,7 @@ namespace Duplicati.Library.Utility
public string GetFilterHash()
{
var hash = MD5HashHelper.GetHash(m_filters.Select(x => x.Filter));
return MD5HashHelper.GetHashString(hash);
return Utility.ByteArrayAsHexString(hash);
}
/// <summary>
@@ -41,7 +41,7 @@ namespace Duplicati.Library.Utility
public string GetFilterHash()
{
var hash = MD5HashHelper.GetHash(new[] {First.GetFilterHash(), Second.GetFilterHash()});
return MD5HashHelper.GetHashString(hash);
return Utility.ByteArrayAsHexString(hash);
}
public bool Empty { get { return First.Empty && Second.Empty; } }
+16 -11
View File
@@ -18,20 +18,34 @@
//
#endregion
using System;
using System.Collections.Generic;
using System.Security.Cryptography;
using System.Text;
namespace Duplicati.Library.Utility
{
/// <summary>
/// Helper class to compute MD5 hashes
/// </summary>
public static class MD5HashHelper
{
/// <summary>
/// Computes the MD5 hash of the input string
/// </summary>
/// <returns>The MD5 hash.</returns>
/// <param name="inputString">The input string.</param>
public static byte[] GetHash(string inputString)
{
HashAlgorithm algorithm = MD5.Create(); //or use SHA256.Create();
return algorithm.ComputeHash(Encoding.UTF8.GetBytes(inputString));
using(var algorithm = MD5.Create()) //or use SHA256.Create();
return algorithm.ComputeHash(Encoding.UTF8.GetBytes(inputString));
}
/// <summary>
/// Computes the MD5 hash of the input strings
/// </summary>
/// <returns>The MD5 hash.</returns>
/// <param name="inputStrings">The input strings.</param>
public static byte[] GetHash(IEnumerable<string> inputStrings)
{
using (var md5 = MD5.Create())
@@ -46,14 +60,5 @@ namespace Duplicati.Library.Utility
return md5.Hash;
}
}
public static string GetHashString(byte[] hash)
{
var sb = new StringBuilder();
foreach (var b in hash)
sb.Append(b.ToString("X2"));
return sb.ToString();
}
}
}