Fix bug in hashing algorithm

As per .NET guidelines and implementation details, can't use
string.GetHashCode() to persist string hash code values on disk.

--HG--
branch : 1.x
This commit is contained in:
Renaud Paquay
2011-05-29 13:08:38 -07:00
parent a281658f9a
commit 234375704a
2 changed files with 36 additions and 5 deletions

View File

@@ -87,14 +87,14 @@ namespace Orchard.Environment.Extensions {
private string GetExtensionHash(ExtensionLoadingContext context, DependencyDescriptor dependencyDescriptor) {
var hash = new Hash();
hash.AddString(dependencyDescriptor.Name);
hash.AddStringInvariant(dependencyDescriptor.Name);
foreach (var virtualpathDependency in context.ProcessedExtensions[dependencyDescriptor.Name].VirtualPathDependencies) {
hash.AddDateTime(GetVirtualPathModificationTimeUtc(context.VirtualPathModficationDates, virtualpathDependency));
}
foreach (var reference in dependencyDescriptor.References) {
hash.AddString(reference.Name);
hash.AddStringInvariant(reference.Name);
hash.AddString(reference.LoaderName);
hash.AddDateTime(GetVirtualPathModificationTimeUtc(context.VirtualPathModficationDates, reference.VirtualPath));
}

View File

@@ -10,12 +10,28 @@ namespace Orchard.Utility {
public class Hash {
private long _hash;
public string Value { get { return _hash.ToString("x", CultureInfo.InvariantCulture); } }
public string Value {
get {
return _hash.ToString("x", CultureInfo.InvariantCulture);
}
}
public override string ToString() {
return Value;
}
public void AddString(string value) {
if (string.IsNullOrEmpty(value))
return;
_hash += value.GetHashCode();
_hash += GetStringHashCode(value);
}
public void AddStringInvariant(string value) {
if (string.IsNullOrEmpty(value))
return;
AddString(value.ToLowerInvariant());
}
public void AddTypeReference(Type type) {
@@ -24,7 +40,22 @@ namespace Orchard.Utility {
}
public void AddDateTime(DateTime dateTime) {
_hash += dateTime.ToUniversalTime().ToBinary();
_hash += dateTime.ToBinary();
}
/// <summary>
/// We need a custom string hash code function, because .NET string.GetHashCode()
/// function is not guaranteed to be constant across multiple executions.
/// </summary>
private static long GetStringHashCode(string s) {
unchecked {
long result = 352654597L;
foreach (var ch in s) {
long h = ch.GetHashCode();
result = result + (h << 27) + h;
}
return result;
}
}
}
}