diff --git a/Library/DiscUtils.Core/Archives/TarFileBuilder.cs b/Library/DiscUtils.Core/Archives/TarFileBuilder.cs
index c5eed3bfc..cfab95504 100644
--- a/Library/DiscUtils.Core/Archives/TarFileBuilder.cs
+++ b/Library/DiscUtils.Core/Archives/TarFileBuilder.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -24,6 +24,7 @@
using DiscUtils.Streams;
using System;
using System.Collections.Generic;
+using System.Collections.ObjectModel;
using System.IO;
namespace DiscUtils.Archives;
@@ -74,6 +75,11 @@ public long TotalSize
public int FileCount => _files.Count;
+ protected virtual void AddFile(UnixBuildFileRecord file)
+ {
+ _files.Add(file);
+ }
+
///
/// Add a directory to the tar archive.
///
@@ -114,7 +120,7 @@ public void AddDirectory(
/// The file data.
public void AddFile(string name, byte[] buffer)
{
- _files.Add(new UnixBuildFileRecord(name, buffer));
+ AddFile(new UnixBuildFileRecord(name, buffer));
}
///
@@ -124,7 +130,7 @@ public void AddFile(string name, byte[] buffer)
/// The file to add.
public void AddFile(string name, string sourcefile)
{
- _files.Add(new UnixBuildFileRecord(name, File.ReadAllBytes(sourcefile)));
+ AddFile(new UnixBuildFileRecord(name, File.ReadAllBytes(sourcefile)));
}
///
@@ -139,7 +145,7 @@ public void AddFile(string name, string sourcefile)
public void AddFile(
string name, byte[] buffer, int ownerId, int groupId, UnixFilePermissions fileMode, DateTime modificationTime)
{
- _files.Add(new UnixBuildFileRecord(name, buffer, fileMode, ownerId, groupId, modificationTime));
+ AddFile(new UnixBuildFileRecord(name, buffer, fileMode, ownerId, groupId, modificationTime));
}
///
@@ -154,7 +160,7 @@ public void AddFile(
public void AddFile(
string name, string sourcefile, int ownerId, int groupId, UnixFilePermissions fileMode, DateTime modificationTime)
{
- _files.Add(new UnixBuildFileRecord(name, File.ReadAllBytes(sourcefile), fileMode, ownerId, groupId, modificationTime));
+ AddFile(new UnixBuildFileRecord(name, File.ReadAllBytes(sourcefile), fileMode, ownerId, groupId, modificationTime));
}
///
@@ -164,7 +170,7 @@ public void AddFile(
/// The file data.
public void AddFile(string name, Stream stream)
{
- _files.Add(new UnixBuildFileRecord(name, stream));
+ AddFile(new UnixBuildFileRecord(name, stream));
}
///
@@ -179,7 +185,7 @@ public void AddFile(string name, Stream stream)
public void AddFile(
string name, Stream stream, int ownerId, int groupId, UnixFilePermissions fileMode, DateTime modificationTime)
{
- _files.Add(new UnixBuildFileRecord(name, stream, fileMode, ownerId, groupId, modificationTime));
+ AddFile(new UnixBuildFileRecord(name, stream, fileMode, ownerId, groupId, modificationTime));
}
protected override List FixExtents(out long totalLength)
diff --git a/Library/DiscUtils.Core/Archives/UnixBuildFileRecord.cs b/Library/DiscUtils.Core/Archives/UnixBuildFileRecord.cs
index c9622f921..dafb70468 100644
--- a/Library/DiscUtils.Core/Archives/UnixBuildFileRecord.cs
+++ b/Library/DiscUtils.Core/Archives/UnixBuildFileRecord.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -26,7 +26,8 @@
using System.IO;
namespace DiscUtils.Archives;
-internal sealed class UnixBuildFileRecord
+
+public sealed class UnixBuildFileRecord
{
private string _name;
private UnixFilePermissions _fileMode;
diff --git a/Library/DiscUtils.Core/IFileSystemBuilder.cs b/Library/DiscUtils.Core/IFileSystemBuilder.cs
index dd805a4da..fbf148fb8 100644
--- a/Library/DiscUtils.Core/IFileSystemBuilder.cs
+++ b/Library/DiscUtils.Core/IFileSystemBuilder.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -33,6 +33,8 @@ public interface IFileSystemBuilder
string VolumeIdentifier { get; set; }
+ event EventHandler ProgressChanged;
+
void AddDirectory(string name);
void AddDirectory(string name, DateTime creationTime, DateTime writtenTime, DateTime accessedTime, FileAttributes attributes);
diff --git a/Library/DiscUtils.Core/ProgressEventArgs.cs b/Library/DiscUtils.Core/ProgressEventArgs.cs
new file mode 100644
index 000000000..33de31a82
--- /dev/null
+++ b/Library/DiscUtils.Core/ProgressEventArgs.cs
@@ -0,0 +1,32 @@
+//
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
+//
+// Permission is hereby granted, free of charge, to any person obtaining a
+// copy of this software and associated documentation files (the "Software"),
+// to deal in the Software without restriction, including without limitation
+// the rights to use, copy, modify, merge, publish, distribute, sublicense,
+// and/or sell copies of the Software, and to permit persons to whom the
+// Software is furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
+// DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+
+namespace DiscUtils;
+
+// EventArgs class for progress reporting
+public class ProgressEventArgs : EventArgs
+{
+ public long TotalFiles { get; set; }
+ public long TotalItems { get; set; }
+}
diff --git a/Library/DiscUtils.Iso9660/BuildDirectoryInfo.cs b/Library/DiscUtils.Iso9660/BuildDirectoryInfo.cs
index 42de7863c..44902ed88 100644
--- a/Library/DiscUtils.Iso9660/BuildDirectoryInfo.cs
+++ b/Library/DiscUtils.Iso9660/BuildDirectoryInfo.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -41,9 +41,9 @@ public sealed class BuildDirectoryInfo : BuildDirectoryMember
private List _sortedMembers;
internal BuildDirectoryInfo(string name, BuildDirectoryInfo parent)
- : base(name, MakeShortDirName(name, parent))
+ : base(name, MakeShortDirName(name))
{
- _parent = parent == null ? this : parent;
+ _parent = parent ?? this;
HierarchyDepth = parent == null ? 0 : parent.HierarchyDepth + 1;
_members = new(StringComparer.OrdinalIgnoreCase, entry => entry.Name);
}
@@ -147,7 +147,7 @@ private static int WriteMember(BuildDirectoryMember m, string nameOverride, Enco
return dr.WriteTo(buffer, nameEnc);
}
- private static string MakeShortDirName(string longName, BuildDirectoryInfo dir)
+ private static string MakeShortDirName(string longName)
{
if (IsoUtilities.IsValidDirectoryName(longName))
{
diff --git a/Library/DiscUtils.Iso9660/CDBuilder.cs b/Library/DiscUtils.Iso9660/CDBuilder.cs
index 3f45e0adb..de4094995 100644
--- a/Library/DiscUtils.Iso9660/CDBuilder.cs
+++ b/Library/DiscUtils.Iso9660/CDBuilder.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -56,6 +56,23 @@ public sealed class CDBuilder : StreamBuilder, IFileSystemBuilder
private readonly List _files;
private readonly BuildDirectoryInfo _rootDirectory;
+ // Progress reporting event
+ public event EventHandler ProgressChanged;
+
+ private ProgressEventArgs progressEventArgs;
+
+ // Method for updating progress
+ private void UpdateProgress()
+ {
+ if (ProgressChanged is not null)
+ {
+ progressEventArgs ??= new();
+ progressEventArgs.TotalFiles = _files.Count;
+ progressEventArgs.TotalItems = _files.Count + _dirs.Count;
+ ProgressChanged(this, progressEventArgs);
+ }
+ }
+
///
/// Initializes a new instance of the CDBuilder class.
///
@@ -180,6 +197,8 @@ public BuildDirectoryInfo AddDirectory(string name)
private void AddFile(BuildFileInfo fi)
{
_files.Add(fi);
+
+ UpdateProgress();
}
///
@@ -311,7 +330,7 @@ protected override List FixExtents(out long totalLength)
_bootEntry.WriteTo(bootCatalog, 0x20);
fixedRegions.Add(new BuilderBufferExtent(bootCatalogPos, bootCatalog));
-
+
// Don't add to focus, we already skipped the length of the bootCatalog
}
@@ -628,11 +647,11 @@ void IFileSystemBuilder.AddFile(string name, byte[] content, DateTime creationTi
void IFileSystemBuilder.AddFile(string name, Stream source, DateTime creationTime, DateTime writtenTime, DateTime accessedTime, FileAttributes attributes) =>
AddFile(name, source).CreationTime = writtenTime;
-
+
void IFileSystemBuilder.AddFile(string name, string sourcePath, DateTime creationTime, DateTime writtenTime, DateTime accessedTime, FileAttributes attributes) =>
AddFile(name, sourcePath).CreationTime = writtenTime;
bool IFileSystemBuilder.Exists(string path) => GetFile(path) != null;
public IFileSystem GenerateFileSystem() => new CDReader(Build(), UseJoliet);
-}
\ No newline at end of file
+}
diff --git a/Library/DiscUtils.SquashFs/BuilderDirectory.cs b/Library/DiscUtils.SquashFs/BuilderDirectory.cs
index a73ea7017..ec98e115a 100644
--- a/Library/DiscUtils.SquashFs/BuilderDirectory.cs
+++ b/Library/DiscUtils.SquashFs/BuilderDirectory.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2011, Kenneth Bell
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -43,7 +43,7 @@ public BuilderDirectory()
public void AddChild(string name, BuilderNode node)
{
- if (name.Contains(@"\\"))
+ if (name.IndexOfAny(Utilities.PathSeparators) >= 0)
{
throw new ArgumentException("Single level of path must be provided", nameof(name));
}
diff --git a/Library/DiscUtils.SquashFs/SquashFileSystemBuilder.cs b/Library/DiscUtils.SquashFs/SquashFileSystemBuilder.cs
index 82b9c7540..a65c28418 100644
--- a/Library/DiscUtils.SquashFs/SquashFileSystemBuilder.cs
+++ b/Library/DiscUtils.SquashFs/SquashFileSystemBuilder.cs
@@ -1,5 +1,5 @@
//
-// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist
+// Copyright (c) 2008-2024, Kenneth Bell, Olof Lagerkvist and contributors
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the "Software"),
@@ -45,6 +45,23 @@ public sealed class SquashFileSystemBuilder : StreamBuilder, IFileSystemBuilder
private BuilderDirectory _rootDir;
+ // Progress reporting event
+ public event EventHandler ProgressChanged;
+
+ private ProgressEventArgs progressEventArgs;
+
+ // Method for updating progress
+ private void AddProgress(int newFiles, int newItems)
+ {
+ if (ProgressChanged is not null)
+ {
+ progressEventArgs ??= new();
+ progressEventArgs.TotalFiles += newFiles;
+ progressEventArgs.TotalItems += newItems;
+ ProgressChanged(this, progressEventArgs);
+ }
+ }
+
///
/// Initializes a new instance of the SquashFileSystemBuilder class.
///
@@ -155,7 +172,10 @@ public void AddFile(string path, Stream content, int user, int group, UnixFilePe
user,
group,
DefaultDirectoryPermissions);
+
dirNode.AddChild(Utilities.GetFileFromPath(path), file);
+
+ AddProgress(newFiles: 1, newItems: 1);
}
///
@@ -187,7 +207,10 @@ public void AddFile(string path, byte[] content, int user, int group, UnixFilePe
user,
group,
DefaultDirectoryPermissions);
+
dirNode.AddChild(Utilities.GetFileFromPath(path), file);
+
+ AddProgress(newFiles: 1, newItems: 1);
}
///
@@ -219,7 +242,10 @@ public void AddFile(string path, string contentPath, int user, int group, UnixFi
user,
group,
DefaultDirectoryPermissions);
+
dirNode.AddChild(Utilities.GetFileFromPath(path), file);
+
+ AddProgress(newFiles: 1, newItems: 1);
}
///
@@ -266,6 +292,7 @@ public void AddDirectory(string path, int user, int group, UnixFilePermissions p
user,
group,
permissions);
+
parentDir.AddChild(Utilities.GetFileFromPath(path), dir);
}
@@ -535,6 +562,8 @@ private BuilderDirectory CreateDirectory(string path, int user, int group, UnixF
};
currentDir.AddChild(elems[i], nextDir);
+
+ AddProgress(newFiles: 0, newItems: 1);
}
else if (nextDir == null)
{
diff --git a/Library/DiscUtils.VirtualFileSystem/TarFileSystemBuilder.cs b/Library/DiscUtils.VirtualFileSystem/TarFileSystemBuilder.cs
index 94af2c905..5ad13aa49 100644
--- a/Library/DiscUtils.VirtualFileSystem/TarFileSystemBuilder.cs
+++ b/Library/DiscUtils.VirtualFileSystem/TarFileSystemBuilder.cs
@@ -4,10 +4,31 @@
using DiscUtils.Archives;
using DiscUtils.Internal;
using System.IO;
+using System.Collections.Specialized;
+using System.Linq;
+using LTRData.Extensions.Buffers;
namespace DiscUtils.VirtualFileSystem;
public class TarFileSystemBuilder : TarFileBuilder, IFileSystemBuilder
{
+ // Progress reporting event
+ public event EventHandler ProgressChanged;
+
+ private ProgressEventArgs progressEventArgs;
+
+ protected override void AddFile(UnixBuildFileRecord file)
+ {
+ base.AddFile(file);
+
+ if (ProgressChanged is not null)
+ {
+ progressEventArgs ??= new();
+ progressEventArgs.TotalFiles += file.Name.EndsWith('/') ? 0 : 1;
+ progressEventArgs.TotalItems = FileCount;
+ ProgressChanged(this, progressEventArgs);
+ }
+ }
+
public string VolumeIdentifier { get; set; }
public IFileSystem GenerateFileSystem() => new TarFileSystem(Build(), VolumeIdentifier, ownsStream: true);
diff --git a/Library/DiscUtils.VirtualFileSystem/VirtualFileSystem.cs b/Library/DiscUtils.VirtualFileSystem/VirtualFileSystem.cs
index 2bd9efff5..f29fec53d 100644
--- a/Library/DiscUtils.VirtualFileSystem/VirtualFileSystem.cs
+++ b/Library/DiscUtils.VirtualFileSystem/VirtualFileSystem.cs
@@ -12,6 +12,23 @@ public partial class VirtualFileSystem : DiscFileSystem, IWindowsFileSystem, IUn
{
public delegate Stream FileOpenDelegate(FileMode mode, FileAccess access);
+ // Progress reporting event
+ public event EventHandler ProgressChanged;
+
+ private ProgressEventArgs progressEventArgs;
+
+ // Method for updating progress
+ internal void AddProgress(int newFiles, int newItems)
+ {
+ if (ProgressChanged is not null)
+ {
+ progressEventArgs ??= new();
+ progressEventArgs.TotalFiles += newFiles;
+ progressEventArgs.TotalItems += newItems;
+ ProgressChanged(this, progressEventArgs);
+ }
+ }
+
public static string GetPathDirectoryName(string path)
{
if (string.IsNullOrEmpty(path))
diff --git a/Library/DiscUtils.VirtualFileSystem/VirtualFileSystemDirectoryEntry.cs b/Library/DiscUtils.VirtualFileSystem/VirtualFileSystemDirectoryEntry.cs
index a480ed82a..47ec0f1e4 100644
--- a/Library/DiscUtils.VirtualFileSystem/VirtualFileSystemDirectoryEntry.cs
+++ b/Library/DiscUtils.VirtualFileSystem/VirtualFileSystemDirectoryEntry.cs
@@ -43,8 +43,11 @@ internal VirtualFileSystemDirectoryEntry(VirtualFileSystem fileSystem)
internal VirtualFileSystemDirectoryEntry(VirtualFileSystemDirectory parent, string name)
{
- Parent = parent ?? throw new ArgumentNullException(nameof(parent));
- FileSystem = parent.FileSystem ?? throw new ArgumentException("FileSystem property is null", nameof(parent));
+ Parent = parent
+ ?? throw new ArgumentNullException(nameof(parent));
+
+ FileSystem = parent.FileSystem
+ ?? throw new ArgumentException("FileSystem property is null", nameof(parent));
if (string.IsNullOrEmpty(name))
{
@@ -52,6 +55,8 @@ internal VirtualFileSystemDirectoryEntry(VirtualFileSystemDirectory parent, stri
}
parent.AddEntry(name, this);
+
+ FileSystem.AddProgress(newFiles: (this is VirtualFileSystemFile) ? 1 : 0, newItems: 1);
}
public WindowsFileInformation GetStandardInformation() => new()