Skip to content

Commit 2dc7487

Browse files
committed
VCST-345: check bitwise for unmanaged dlls (#2756)
1 parent e2cc478 commit 2dc7487

File tree

1 file changed

+67
-2
lines changed

1 file changed

+67
-2
lines changed

src/VirtoCommerce.Platform.Modules/Local/LocalStorageModuleCatalog.cs

+67-2
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
using System.Diagnostics;
44
using System.IO;
55
using System.Linq;
6+
using System.Reflection;
67
using Microsoft.Extensions.Logging;
78
using Microsoft.Extensions.Options;
89
using VirtoCommerce.Platform.Core.Common;
@@ -151,7 +152,7 @@ public override void Validate()
151152
.ToArray();
152153
if (installedIncompatibilities.Any())
153154
{
154-
module.Errors.Add($"{ module } is incompatible with installed { string.Join(", ", installedIncompatibilities.Select(x => x.ToString())) }. You should uninstall these modules first.");
155+
module.Errors.Add($"{module} is incompatible with installed {string.Join(", ", installedIncompatibilities.Select(x => x.ToString()))}. You should uninstall these modules first.");
155156
}
156157
}
157158

@@ -284,7 +285,12 @@ private void CopyFile(string sourceFilePath, string targetFilePath)
284285
}
285286

286287
var versionsAreSameButLaterDate = (sourceVersion == targetVersion && targetFileInfo.Exists && sourceFileInfo.Exists && targetFileInfo.LastWriteTimeUtc < sourceFileInfo.LastWriteTimeUtc);
287-
if (!targetFileInfo.Exists || sourceVersion > targetVersion || versionsAreSameButLaterDate)
288+
289+
var replaceBitwiseReason = targetFileInfo.Exists
290+
&& sourceVersion.Equals(targetVersion)
291+
&& ReplaceBitwiseReason(sourceFilePath, targetFilePath);
292+
293+
if (!targetFileInfo.Exists || sourceVersion > targetVersion || versionsAreSameButLaterDate || replaceBitwiseReason)
288294
{
289295
var targetDirectoryPath = Path.GetDirectoryName(targetFilePath);
290296
Directory.CreateDirectory(targetDirectoryPath);
@@ -309,6 +315,65 @@ private void CopyFile(string sourceFilePath, string targetFilePath)
309315
}
310316
}
311317

318+
private bool ReplaceBitwiseReason(string sourceFilePath, string targetFilePath)
319+
{
320+
if (IsManagedLibrary(targetFilePath) || !sourceFilePath.EndsWith(".dll", StringComparison.InvariantCultureIgnoreCase))
321+
{
322+
return false;
323+
}
324+
325+
var currentIs64 = Environment.Is64BitProcess;
326+
var targetIs64 = !Is32Bitwise(targetFilePath);
327+
328+
if (currentIs64 == targetIs64)
329+
{
330+
return false;
331+
}
332+
333+
var sourceIs64 = !Is32Bitwise(sourceFilePath);
334+
if (currentIs64 == sourceIs64)
335+
{
336+
return true;
337+
}
338+
339+
return false;
340+
}
341+
342+
private bool IsManagedLibrary(string pathToDll)
343+
{
344+
try
345+
{
346+
AssemblyName.GetAssemblyName(pathToDll);
347+
return true;
348+
}
349+
catch
350+
{
351+
// file is unmanaged
352+
}
353+
354+
return false;
355+
}
356+
357+
private bool Is32Bitwise(string dllPath)
358+
{
359+
try
360+
{
361+
using var fs = new FileStream(dllPath, FileMode.Open, FileAccess.Read);
362+
using var br = new BinaryReader(fs);
363+
fs.Seek(0x3c, SeekOrigin.Begin);
364+
var peOffset = br.ReadInt32();
365+
366+
fs.Seek(peOffset, SeekOrigin.Begin);
367+
var peHead = br.ReadUInt32();
368+
369+
return peHead == 0x00004550 && br.ReadUInt16() == 0x14c;
370+
}
371+
catch (EndOfStreamException exception)
372+
{
373+
throw new PlatformException($"Failed to read file '{dllPath}'.", exception);
374+
}
375+
}
376+
312377
private bool IsAssemblyRelatedFile(string path)
313378
{
314379
return _options.AssemblyFileExtensions.Union(_options.AssemblyServiceFileExtensions).Any(x => path.EndsWith(x, StringComparison.OrdinalIgnoreCase));

0 commit comments

Comments
 (0)