wabbajack/Wabbajack.Common/Paths/FileCompaction.cs

83 lines
2.5 KiB
C#
Raw Normal View History

2020-09-17 14:08:30 +00:00
using System.Linq;
using System.Threading.Tasks;
2020-08-05 22:01:45 +00:00
using Wabbajack.Common.IO;
namespace Wabbajack.Common
{
public static class FileCompaction
{
private static AbsolutePath _compactExecutable;
private static bool? _haveCompact = null;
private static AbsolutePath? GetCompactPath()
{
if (_haveCompact != null && _haveCompact.Value) return _compactExecutable;
if (_haveCompact != null) return null;
2021-06-12 09:36:51 +00:00
var x86Path = KnownFolders.SystemX86.Path;
if (x86Path == null)
return null;
_compactExecutable = ((AbsolutePath)x86Path).Combine("compact.exe");
2020-08-05 22:01:45 +00:00
if (!_compactExecutable.Exists) return null;
_haveCompact = true;
return _compactExecutable;
}
public enum Algorithm
{
XPRESS4K,
XPRESS8K,
XPRESS16K,
LZX
}
public static async Task<bool> Compact(this AbsolutePath path, Algorithm algorithm)
{
if (!path.Exists) return false;
var exe = GetCompactPath();
if (exe == null) return false;
if (path.IsFile)
{
var proc = new ProcessHelper
{
Path = exe.Value,
Arguments = new object[] {"/C", "/EXE:" + algorithm, path},
ThrowOnNonZeroExitCode = false
};
return await proc.Start() == 0;
}
else
{
var proc = new ProcessHelper
{
Path = exe.Value,
Arguments = new object[] {"/C", "/S", "/EXE:" + algorithm, path},
ThrowOnNonZeroExitCode = false
};
return await proc.Start() == 0;
}
}
2020-09-08 22:15:33 +00:00
public static async Task CompactFolder(this AbsolutePath folder, WorkQueue queue, Algorithm algorithm)
{
var driveInfo = folder.DriveInfo().DiskSpaceInfo;
var clusterSize = driveInfo.SectorsPerCluster * driveInfo.BytesPerSector;
2020-09-17 14:08:30 +00:00
await folder
.EnumerateFiles(true)
.Where(f => f.Size > clusterSize)
2020-09-08 22:15:33 +00:00
.PMap(queue, async path =>
{
2020-09-17 14:08:30 +00:00
Utils.Status($"Compacting {path.FileName}");
await path.Compact(algorithm);
2020-09-08 22:15:33 +00:00
});
}
2020-08-05 22:01:45 +00:00
}
}