Release date: 2026-11-08.
Patch release: reliable releases and a clearer GUI. There are no library API or archive-format changes; the package remains compatible with 1.9.0.
- Folder pickers no longer surface Avalonia's
Directory must existexception as an application error when the selected folder was deleted (or became inaccessible) while the native dialog was open. The GUI now explains that the path is not an existing folder and suggests choosing another folder or typing the path directly. - Picker and browse failures now marshal their log messages to the UI thread, so
a handled picker error can no longer trigger a second
InvalidOperationExceptionfromDataContextaccess on a thread-pool thread. - Removed the now-redundant nested picker-failure guards and added regression coverage for the Avalonia exception contract.
- Tag pushes reliably create the GitHub release again;
workflow_dispatchdry runs still build and smoke-test the bundles without publishing. - The release SBOM tool is pinned to
Microsoft.Sbom.DotNetTool4.1.13. - Docker base images are pinned by digest, and GHCR write permission is scoped to the Docker build job.
- Packaging manifests are generated from GitHub REST API release digests (including the refreshed 1.9.0 manifests), and the Homebrew cask uses the current macOS dependency form.
- Full suite: 2315 passed / 1 opt-in skip on
net10.0(three new GUI folder-picker regression tests); 2239 passed / 1 opt-in skip onnet8.0/net9.0.
Release date: 2026-11-08.
The most advanced XISO management release. 1.9.0 combines the reviewed
public-API cleanup (FAC-01), the beyond-reference feature pass
(BRF-01…BRF-13), the distribution and shell-integration track
(DST-01…DST-05) and a full documentation refresh. net8.0, net9.0 and
net10.0 remain supported.
- Removed
XISOSharp.GodHeader,XISOSharp.StfsHeader,XISOSharp.StfsPackage,XISOSharp.BlockDevice.GodBlockDeviceand the matchingXISOSharp.Modelsrecords/enums (GodTitleInfo,GodVolumeInfo,StfsEntry,StfsPackageInfo,StfsPackageKind,StfsTitleInfo,StfsValidationIssue,StfsValidationReport). Consumers useStfsSharptypes directly. - Kept
XisoChecksum.ComputeStfsChecksum/ComputeStfsChecksumHexas StfsSharp-backed helpers. The internalGodVolumeBlockDeviceadapter keepsXisoImageSource/OpenRead/OpenBlockDeviceworking for GOD/SVOD inputs. - Package validation now compares against 1.8.0; the reviewed CP0001 suppressions cover exactly the facade type removals.
- Downstream consumers migrated to the hybrid split: SimpleXisoDrive uses
XISOSharpfor mounting/XDVDFS andStfsSharpdirectly for GOD/SVOD resolution; XISO Studio usesXISOSharpfor reads,StfsSharpdirectly for GOD metadata andCCISharpdirectly for CCI validation (XRP-04).
- Parallel collection verbs (
BRF-06):--jobs 1..64now also runs multi-imagechecksum,hash,-V/audit and--batchextract/list/tree/rewrite over images in parallel. Per-image output is captured and replayed in input order, JSON arrays stay ordered, and scopedLoggercounters keep each image's summary exact. - Redump DAT verification (
BRF-09):XisoDat.Parse/Verifyandverify-dat <dat> <image>... [--json]match whole images against a Redump-style XML DAT (game/romsize + MD5/SHA-1/CRC32) and report verified, ambiguous, not-in-DAT and missing entries. No DAT source is bundled. - Disc-layout inspector (
BRF-01):XisoDiscInfo.Readanddisc-info/--disc-inforeport XGD type/subtype and wave, video L0/L1 and game-partition byte/sector ranges, PFI presence and layer break, embedded orsectors.txtsecurity-sector ranges, Redump-size matching and consistency warnings. Containers report the game-partition view and mark video fields unavailable. - Skeleton overlay (
BRF-02):XisoSkeleton.Applyandapply-skeleton/--apply-skeletonrestore file data into a--petrifyskeleton, verifying the optional.hash; Petrify→Apply reproduces the original image byte-for-byte. Skeleton creation now preserves the system preamble and 0xFF file-tail padding. - Per-file hash sidecars (
BRF-05):XisoReader.ComputeFileHashSidecarandfile-hashesgenerate SHA-1 (default), SHA-256 or MD5 sidecars for ISO/split/CISO/CCI/GOD/STFS/ZAR;verify-hashesdetects all three digest lengths and accepts the same containers. - Redump/XGD size helper:
XisoDiscInfo.IsKnownRedumpSize.
- Embedded
default.xexmetadata (BRF-03): GOD headers and XBLA/XBLIG STFS packages merge XDBF/XSRC publisher, developer, genre, description and thumbnail presence intotitle-info/TitleInfo, in text and--json. - Thumbnail export (
BRF-04):xex-image --type thumbnailwrites the XDBF0x8000PNG payload (image or loose.xexinput). - Loose executables (
BRF-08):--xex-info,--xbe-infoand--xbe-imageaccept a single.xex/.xbefile with the same parser and JSON shape as the image-plus-path form. - ZAR level (
BRF-07):--zar-level 1..22for--zar,--compressandconvert --format zar; level 6 remains byte-identical.
- Create-time link policy (
BRF-12):--symlink-mode follow|skip|rejectfor-c,--pack,build-imageandapply-skeleton.followis the historical behavior (file links pack their target, directory reparse points are skipped);skipomits both;rejectfails with the link path. Cyclic directory links always terminate. - Actionable host-I/O diagnostics (
BRF-13):HostIoDiagnosticsnames the path, operation and likely fix for permission-denied, long-path, sharing, existing-destination, illegal-name and full-disk failures. Extraction exceptions and CLI modes use the same detail, so rawPermission deniedorInvalid argumentno longer reaches the user alone. - Xbox filename rules (
BRF-10):XisoNameRulesexposes the 42-character component limit and Latin-1 contract.--strict-namesfails before writing; the default warns. Supported for create,--pack,--copy-in,build-imageandApply;+,!, spaces and Latin-1 names round-trip. - Deterministic packing (
BRF-11):--deterministicis an alias for--file-time 0and is accepted for create,--pack, rewrite andbuild-image; repeated packs are byte-identical. Rewrites now accept an explicitfileTimeso--deterministic -rwrites FILETIME 0 instead of preserving the source timestamp.
- winget, Scoop and Homebrew manifests (
DST-03): the release assets are described by generated manifests underpackaging/. The repository root is also a Scoop bucket (bucket/xisosharp.json), andscripts/update-packaging.ps1 -Version <version>refreshes every manifest and SHA-256 value from a published GitHub release. - Shell completions and man page (
DST-04): PowerShell, bash, zsh and fish completions live indocs/completions/, andxisosharp(1)indocs/man/. CI parses each script, checks that every CLI flag is completable, and renders/lints the man page. - Container image (
DST-05):Dockerfilebuilds a framework-dependent CLI image.docker.ymlsmoke-tests-v, create/list/extract and publishesghcr.io/purelogiccode/xisosharp:<version>plus:lateston tag pushes. - Optional signing (
DST-01/DST-02): NuGet author signing runs when the signing secrets exist; Windows bundles can be Authenticode-signed and verified, and macOS bundles codesigned/notarized, behind repository variables. Unsigned builds remain the default. - CI validation:
packaging-smoke(completions/man page),packaging-windows(winget/Scoop validation) andpackage-install-smoke(winget, Scoop and Homebrew installs).
- Deterministic rewrites now write the fixed FILETIME again
(
DecodeXiso/Rewritegained additivefileTimeoverloads). - Redump DAT parsing skips size-only entries that can never be content-verified,
and duplicate detection no longer depends on a
|-joined key. - Host-I/O diagnostics map the Unix
EWOULDBLOCKsharing error in addition toEBUSYandEEXIST.
New suites cover the disc inspector, skeleton overlay, embedded XEX metadata,
thumbnail export, hash sidecars across containers, ZAR levels, loose
executables, name rules, deterministic packing, parallel collection verbs,
Redump DAT verification, symlink modes and host-I/O diagnostics. The full suite
is 2312 passed / 1 opt-in skip on net10.0 and 2239 passed / 1 opt-in
skip on net8.0/net9.0.
Release date: 2026-11-07.
Hardening and Xbox 360 GUI release. No existing public API is removed and
all read/write behavior is unchanged; the package validates against 1.7.0.
- Source-filesystem packing (LIB-01):
ISourceFilesystemis the read-side counterpart toIFilesystem.MemoryFilesystemimplements both, andXisoWriter.CreateXiso/PackFromDirectory(sync and async) gain overloads that pack a custom store without host source paths. The output is byte-identical to the host-directory path and remains CWD-free under concurrent creates. - Per-call logging (LIB-02):
IXisoLogger,XisoLogOptionsandXisoLogScoperoute one operation's log output to an isolated sink.UnpackOptions.Logapplies the same to extraction. Scopes areAsyncLocal-based, so concurrent operations can log to separate sinks; the staticLoggerfacade is unchanged when no scope is active. - Sparse outputs (LIB-03): pre-sized writer and extraction outputs are
marked sparse on NTFS (
FSCTL_SET_SPARSE) and rely on file-system holes on Unix. CISO/CCI decompression and ZAR extraction skip all-zero chunks; every path keeps the dense fallback when sparse files are unavailable. - Property-style round-trips (LIB-04): deterministic seeded coverage for pack/extract, split/join, CISO, CCI and ISO/ZAR at empty, one-byte, sector-boundary and compression-threshold sizes.
- Benchmarks (LIB-05/LIB-06): the end-to-end suite adds extract, CCI
compress/decompress and 64 MiB random-read cases;
docs/benchmarks.mdrecords the methodology and an extract-xiso/xdvdfs/XboxKit comparison with a reproducible script. - Support policy (LIB-07):
net8.0/net9.0stay supported compatibility targets in 2.x (owner decision 2026-11-07);net10.0is the primary target. - Package validation (LIB-08): the baseline moved from
1.4.4to1.7.0; the 1.4.4-era suppressions were retired.
XISOSharp now references CCISharp 1.1.0:
- CCI compression levels
10..12select the managed LZ4-HC encoder (level 12 is the highest effort); levels0..9keep the existing fast encoder and byte output. - Single-file
compress --format cci --jobs 1..64compresses sectors on a bounded worker pool. Output is byte-identical to--jobs 1. - CCI readers accept multi-digit parts such as
game.10.cciwhen the contiguous set starts atgame.1.cci; the writer still emits.1.cci….9.cci. XisoCci.CompressToCcigains ajobsoverload; the existing overload is unchanged and defaults to sequential compression.- Documentation, CLI help and the public-API baseline are updated. Existing
level
0..9CCI output and all read verbs are unchanged.
- DocFX link gate (DOC-01): the Pages site and API reference already
publish from the library XML docs; a CI
docs-linksjob now fails on broken local Markdown/HTML links. - Public synthetic corpus (DOC-02):
XISOSharp.TestDataGenerator --corpusdeterministically generates XISO, split ISO, CISO, CCI, ZAR, GOD/SVOD, XBLA/XBLIG STFS, XBE/XEX and corrupt fixtures plus a SHA-256 manifest. No game data is included, andPublicCorpusTests/BattleTests consume it. - Docs refresh (DOC-03): feature matrices, known limitations, library/CLI docs and READMEs updated for the hardening APIs and the Xbox 360 GUI.
- Xbox 360 tab (GUI-01/GUI-02): open GOD/SVOD headers or
.datafolders, XBLA/XBLIG STFS packages and images; list/tree/extract/unpack/audit, with the same CLI verbs and byte-identical output as the command line. Drag/drop routes GOD/STFS inputs to the tab. - Title panel (GUI-03): parses
title-info --jsonfor XBE/XEX/GOD/STFS and shows title name, ID, region, disc and publisher/developer/genre fields. - XBE preview (GUI-04): renders logo,
$$XTIMAGEtitle and$$XSIMAGEsave assets through the sameXbeAssetsdecoder as--xbe-image; missing or unsupported assets produce a clean message. - Parallel controls (GUI-05): extraction and CISO/CCI compression expose
--jobs 1..64, and CCI levels10..12are selectable.
Full suite green on all three targets: 2144 passed / 1 opt-in skip on
net8.0/net9.0 and 2217 passed / 1 opt-in skip on net10.0. Package
validation against 1.7.0, dotnet format, InspectCode, AOT, fuzz and
battle-interop are green on the release commit.
Release date: 2026-11-07.
StfsSharp extraction. The GOD/SVOD and single-file XBLA/XBLIG STFS
readers now live in the standalone MIT package
StfsSharp 1.0.0. XISOSharp
consumes it as a NuGet dependency and keeps its historical public types as
thin facades, so no read verb changes behavior:
GodHeader,StfsHeaderandStfsPackagemap the StfsSharp models to the existing XISOSharp records.GodBlockDeviceis anIBlockDeviceadapter overStfsSharp.GodVolume.XisoChecksum.ComputeStfsChecksumand the CLI/GUI paths are unchanged.- The facades were removed in XISOSharp 1.9.0; consumers use
StfsSharpdirectly.
StfsSharp adds a standalone public surface for the moved readers:
GodVolume/GodVolumeStream, StfsPackage.Open/ReadFileChunks, extraction
progress (StfsProgress), safe-name policies, and deep hash-tree validation.
Its suite covers synthetic packages, a deterministic mutation fuzzer,
BenchmarkDotNet cases and optional real-corpus checks (XBLA, XBLIG and
GOD/SVOD). No on-disk format behavior changed.
Full suite green on all three targets: 2101 passed / 1 opt-in skip (2102) on
net8.0/net9.0 and 2165 passed / 1 opt-in skip (2166) on net10.0;
InspectCode 0 warnings, dotnet format clean, package validation passes.
Release date: 2026-11-06
Phase 10 Tier A + read-only Tier B slice. This release adds Xbox 360
XDBF/XSRC title metadata, XBE logo/title/save image extraction, the FATX split
cap, batch --delete-source, GOD/STFS title naming, read-only GOD/SVOD sector
input, XBLA/XBLIG STFS package listing/extraction and SHA-1 hash-tree
validation, parallel CISO compression/extraction, the safe-extract name policy,
and CWD-free writer/reader concurrency. The standalone StfsSharp package
extraction is planned for 1.7.0; CCISharp 1.1 (LZ4-HC and parallel CCI
compression) remains a separate track.
Full suite green on all three targets: 2098 passed / 1 opt-in skip (2099) on net8.0/net9.0 and 2162 passed / 1 opt-in skip (2163) on net10.0.
- Concurrent creation and extraction:
XisoWriter.CreateXiso/PackFromDirectoryresolve the source to absolute host paths, keep byte/file progress in per-operation state and take no process-wide lock. Concurrent creates run independently and never change the process working directory; output is byte-identical. A caller-suppliedinRootwithoutHostPathis resolved once against the caller's CWD.XisoReader.Extract/UnpackImageextract through a rootedLocalFilesysteminstead ofDirectory.SetCurrentDirectory, so concurrent extracts are independent too;UnpackImage(..., IFilesystem)still accepts any custom destination. - FATX-safe split default:
Constants.FatxMaxFileSize(0xFF000000, 4 GiB − 16 MiB) is now the default maximum part size for plain-ISO splits. An explicit--sizeabove it is still honoured with a warning. CISO/CCI keep their0xffbf6000xdvdfs-compatible compression default. - Parallel CISO compression:
CisoWriter.CompressToCso/CompressStreamgainjobsoverloads (1..64) that compress sector batches on a bounded worker pool and write payloads in sector order, so output is byte-identical to the sequential writer and progress stays ordered.MaxParallelismis the shared ceiling; CCI remains single-threaded until CCISharp 1.1. - Parallel extraction:
UnpackOptions.MaxDegreeOfParallelism(1..64, default1) queues independent files during the sequential tree walk and copies them on a bounded pool. Output is byte-identical to a sequential run; per-fileFileAddedprogress and completion logs stay in traversal order, andSkipExisting/ContinueOnErrorkeep their semantics. Plain ISO sources are read positionally throughRandomAccess; CISO/CCI/GOD/split and in-memory sources serialize reads, and destination filesystem calls are serialized soMemoryFilesystemand other non-thread-safe stores stay safe.UnpackOptions.MaxParallelismis the shared64ceiling. - GOD read-only sector input:
GodBlockDevicemaps a GOD/SVOD header plus itsDataNNNNfragments into the decompressed sector view, so every read verb (list, tree, extract, checksum, hash, validate, sector-layout, ranges) accepts a GOD container.GodHeader.TryReadVolume/GodVolumeInfoexpose the SVOD mapping, andXisoImageSourcedetects both a header file and its.datafolder. In-place repair/copy-in/set-filetime/rewrite refuse GOD and ask for a decompress first. - GOD title metadata:
GodHeader/GodTitleInforead the plaintextXContentheader of a GOD/SVOD container (title name, title ID, disc number/count) without mounting it. Names are sanitised for FATX and fall back to the hex title ID when empty. - XBLA/XBLIG header metadata:
StfsHeader/StfsTitleInforead the same XContent fields from single-file Xbox 360 STFS packages (XBLA0x000D0000, XBLIG0x00000002), which have no.datadirectory. - XBLA/XBLIG package listing and extraction:
StfsPackagereads the STFS file table, follows contiguous and hash-chain block lists through the level-0/level-1/level-2 hash interleave, and exposesEntries,Find,ReadAllBytes,CopyToandExtractTo.StfsPackageInforeports theXContenttitle fields and the volume layout.XisoChecksum.ComputeStfsChecksumuses the same sorted-path SHA3-256 tree hash as ISO and ZAR, so equivalent trees compare equal. Read-only: STFS writing/rebuilding stays out of scope. - STFS hash-tree validation:
StfsPackage.Validatehashes every logical data block and compares it with its level-0 hash entry, walks each file's block chain for truncation/cycles, verifies every level-0 table against its level-1 parent (and level-1 tables against level 2), and checks the top hash and header hash in the volume descriptor.StfsValidationReportcarries the counts and every mismatch as aStfsValidationIssue. Read-only: package signatures are not verified, and STFS writing/rebuilding remains out of scope. - Xbox 360 title metadata:
XexDbdfreads the plaintext XDBF/XSTR/XSRC resources from the XEX header-section table.XexTitleInfocarries title name, publisher, developer, genre, description and optional thumbnail;GetXexTitleInfoexposes it directly.TitleInfogains additiveKind(Xbe/Xex) andXexproperties, andGetTitleInforesolvesdefault.xbe→default.xex→default_mp.xbe. - XBE image assets:
XbeAssetsreads the logo bitmap and the$$XTIMAGE/$$XSIMAGEsections. DXT1/3/5, BGR24/BGRA32 and XPR0 payloads are decoded to PNG by the new BCL-onlyDxtDecoder/PngWriter; DDS is passed through or generated.XbeInfogainsHasLogoBitmap,HasTitleImageandHasSaveImageinit properties. - Safe-extract name policy:
ExtractNamePolicy(Rejectdefault,Sanitize,Skip) andUnpackOptions.NamePolicychoose how hostile entry names are handled.Sanitizereplaces unsafe characters with_and adds~Non collisions;Skipomits the entry (and a skipped directory's subtree).StfsPackage.ExtractToandXisoZarchive.ExtractZargained matchingExtractNamePolicyoverloads. The existing overloads keep the fail-fast default.
- GOD input: every read verb accepts a GOD header or its
.datafolder;decompresswrites a plain ISO (named after the header title) andconvertaccepts GOD →.iso/.cci/.cso. Redump modes and in-place write verbs refuse GOD with a "decompress first" message. - XBLA/XBLIG STFS packages:
-l,-t,-x,--unpack,checksumand-l/--jsonaccept a single-file XBLA/XBLIG STFS package and read its file table directly. Extraction honours-dand--skip-existing;checksumuses the ISO/ZAR-compatible tree hash.compress,decompress,convert, rewrite and the raw redump modes refuse STFS with an "extract first" message.-V/audit verifies the package's SHA-1 hash tree (per-block hashes, level tables, top hash and header hash) and reportsFiles checked/Blocks checked/Hash tables/Result. title-infoaccepts a GOD header or its.datafolder, a single-file XBLA/XBLIG STFS package, or an XISO image'sdefault.xbe/default.xex/default_mp.xbeand reports the available title name, title ID, disc and version fields in text and--jsonform. Xbox 360 titles also report publisher, developer, genre, description and thumbnail presence.--xbe-image <image> <path> --type logo|title|save -o out.png|out.ddsextracts XBE artwork.--xbe-info --jsonaddshasLogoBitmap,hasTitleImageandhasSaveImage;--xex-infoprints the XDBF title name, publisher, developer, genre and description when present.--delete-sourceon batchcompress,decompress,convertandsplit: deletes each source only after a successful conversion, requires-y/--yes(refused with-n/--no), removes every part of a split set, and reports the deleted count in the batch summary.--jobson CISO compression:compress/cso --jobs 1..64compresses sectors on a bounded worker pool (default1); output is byte-identical to the sequential writer. With--batch,--jobsstill selects concurrent conversions; single-file CCI compression is single-threaded.--jobson extraction:-xand--unpackaccept--jobs 1..64(default1) to copy independent files in parallel. Output is byte-identical, per-fileFileAddedprogress stays in traversal order, and--skip-existing/--continue-on-errorwork unchanged. ZAR/STFS unpacking and non-extract modes reject the flag with a clear message.--name-policy reject|sanitize|skipon-x/--unpack: choose fail-fast rejection (default), collision-safe sanitized names, or skipping hostile entries during ISO/CISO/CCI/GOD/ZAR/STFS extraction.splitwarns when an explicit--sizeexceeds the conservative FATX cap.
CCISharp1.0.1: the CCI reader now rejects oversized or hostile indexes withInvalidIndexinstead of allocating a buffer sized by the part file. No API change.
- The CLI is no longer published as a NuGet dotnet tool (
XISOSharp.Tool).XISOSharp(the library) remains the only NuGet package; get the CLI from the GitHub release bundles (release_<version>_<rid>.zip) or build it from source withpublish-cli.ps1.
World-class library release. This merges the 1.5.0 development work
(CCI, split ISO, ZAR input, traversal hardening, batch
conversion, JSON, preallocation and explicit layout packing) with the Phase 9
productization work: an open-once XisoImage facade, full-image
CRC32/MD5/SHA-1/SHA-256/SHA3-256, .hash verification, title metadata,
Windows long-path/reserved-name hardening, ZAR extraction caps, mutation
fuzzing, AOT smoke, 3-OS tests, a dotnet tool, SBOM and provenance.
Full suite green on all three targets: 1979 passed / 1 opt-in skip (1980) on net8.0/net9.0 and 2043 passed / 1 opt-in skip (2044) on net10.0.
XisoImage(XISOSharp):Open/OpenAsync,List/ListFlat,ReadFile/OpenReadStream,Extract/ExtractAsync,Validate,GetTitleInfo,ComputeImageHash,IDisposable/IAsyncDisposable.- Full-image hashes:
XisoImageHash.Computestreams CRC32, MD5, SHA-1, SHA-256 and SHA3-256 in one pass through the decompressed view. verify-hashes: verifies a--petrify/XboxKit.hashsidecar for ISO, CISO, CCI, split ISO and ZAR inputs.- Title metadata:
title-info/XisoReader.GetTitleInfofinddefault.xbeand report title name, ID, region, disc and version. - Hardening: Windows
longPathAwaremanifests, reserved device-name rejection/sanitization, ZAR extraction byte/entry caps, CISO malformed-index and alignment validation (found by the new mutation fuzzer). - Quality gates: 3-OS test matrix,
dotnet formatgate, AOT publish smoke, mutation fuzz job, 70% line / 60% branch coverage floors, package validation against 1.4.4 with a reviewed suppression baseline. - Packaging:
XISOSharp.Tooldotnet tool, SBOM + build provenance on releases, community files and a console sample.
Sector-layout packing release, plus the TOC
hardening follow-up. Images can now be repacked at
an explicit layout: XisoLayoutSpec accepts the JSON emitted by
--sector-layout --json (or a compact path=sector text spec), fixes the sectors of
matching files and directory tables, and allocates every other entry first-fit around
the reserved extents. -c, --pack <dir> and build-image gain --layout <file>.
The audit, sector-range, repair, salvage and ZAR walks now use the same explicit
in-order table traversal as extract/list/rewrite, so MaxTocDepth bounds real
subdirectory nesting only. The raw-sector redump modes also reject compressed
and split containers up front, and the GUI ZAR tab converts a .zar back to a
plain ISO. ZAR extraction is now depth-bounded, pre-sized and exact-length, and
CISO compression reads split/container sources through the decompressed view
instead of a joined temporary ISO.
Full suite green on all three targets: 1979 passed / 1 opt-in skip (1980) on net8.0/net9.0 and 2043 passed / 1 opt-in skip (2044) on net10.0.
XisoLayoutSpec/XisoLayoutEntry(XISOSharp.Models):FromSectorLayout,Load(JSON/text auto-detect),Parse,ParseJsonandParseText. JSON accepts the full--sector-layoutpayload, a bareentriesarray, camelCase or PascalCase names, andstartSector/sectoraliases; the text form supports#/;comments,total-sectors=Nand0xhex sectors.XisoWriterlayout packing:CreateXiso,CreateXisoAsync,PackFromDirectory,PackFromDirectoryAsyncandRemapFilesystem.BuildImageaccept an optionallayout. A two-pass planner validates every fixed extent (overlap, reserved system area, bounds, too-small extents), assigns the requested sectors, then seedsSectorAllocatorso unplaced entries fill gaps first-fit.- Layout fidelity: a JSON layout round-trips an unchanged source tree
byte-for-byte;
TotalSectorsis preserved (subject to the writer's final 64 KiB alignment); partition-relative sectors stay correct underprependSectors. - Strict/lenient paths: the compact text form rejects paths missing from the source tree; JSON extra entries are reserved (with a warning) so a subset repack cannot reuse their bytes.
XisoReader.AuditWalk,XisoRanges.GetValidSectorsCore/CollectFileEntries,XisoRepairer.CollectWalk,XisoSalvager.SalvageWalkandXisoZarchive.ParseNodenow walk each directory table with an explicit in-order stack (left subtree, entry, right siblings) instead of recursing on the left child.MaxTocDepth(64) bounds real subdirectory nesting only.- A 4,096-entry left-skewed table now audits, maps (
--ranges,GetFileEntries), repairs a reserved-attribute bit on its deepest entry, salvages into a fresh image and packs to ZAR; cycles and out-of-table pointers still hit the existing named errors or report/drop gates. - The visited-offset set and
MaxTocEntriesPerTable/MaxTocStackFramesbackstops are unchanged; a shared (DAG) subtree now reports the same cycle error the reader has always raised.
XisoValidator.ValidateConversionaccepts a ZArchive (.zar) on either side: the tree comes fromXisoZarchive.ListZar, and--validate-checksumshashes each name-tree entry through the newXisoZarchive.ComputeFileHash(no extraction to disk). ISO↔ZAR conversions can now be verified directly.- The CLI
validateverb accepts.zar(including--jsonand--validate-report), matching the-l/-t/-x/checksumZAR input support. - A
.zarhanded to a sector-only verb (-i,--ls,-V,--filetime,--sector-layout,--ranges,--repair,--copy-in/--copy-out, …) now reports a cleanError:naming the archive verbs instead of an unhandledNotSupportedExceptionstack trace.
XisoZarchive.ExtractZarnow bounds directory nesting atConstants.MaxTocDepth, matchingListZarandComputeZarChecksum; a malicious or corrupt archive fails with a namedInvalidDataExceptioninstead of recursing until the stack overflows.- Each extracted destination is pre-sized from the name tree and copied with
XisoFileCopier.CopyExact, so a truncated entry throwsTruncatedCopyExceptioninstead of silently producing a short file. Failed or canceled entries delete their partial output (Windows-safe: the handle is closed first).
CisoWriter.CompressToCsoreads split ISO, CISO and CCI sources through the seekable decompressed view fromXisoImageSourceinstead of writing a joined temporary ISO first. Split output still goes throughCisoSplitOutput.- The split-output collision guard now compares every source part (not just the entry path), so recompressing a split CISO/ISO set cannot truncate one of its own parts.
--layout <file>on-c <dir>,--pack <dir>andbuild-image; rejected for rewrite/extract/list modes and for--pack <iso>.- Help text and the misplaced-flag guard cover
--layout. --sector-layout --json game.iso > layout.jsonfollowed by-c game_dir out.iso --layout layout.jsonreproduces the source layout.- The raw-sector redump modes (
--video,--random,--seed,--wipe,--trim,--petrify,--update,--zar) refuse.cso/.cci, split ISO and.zarinputs with a clear "decompress/convert/join first" message instead of parsing container bytes as an XISO. - Expected overwrite refusals (
-n, redirected stdin) stay in the local log and no longer reach the bug-report API. - CCI split sets opened through any numbered part (
.2.cci….9.cci) name outputs after the game: extraction createsgame/, rewrite writesgame.iso, andcompressderivesgame.cciinstead of refusing the source as its own output. Plain ISO/CISO sets still strip only.1, andarchive.1.zarkeeps its number.
- The ZAR tab is bidirectional: a
.zarsource runsconvertand writes a plain ISO (output auto-derived next to the archive); an image source keeps the existing pack + overwrite/skip/auto-rename behavior. The output picker and labels follow the detected direction, and the self-test covers the new argv.
LayoutPackingTests(41): JSON/text parsing and validation,FromSectorLayout, byte-identical JSON round-trips, fixed-extent placement, first-fit gaps, reserved unmatched JSON extents, total-sector preservation, prepended partitions, case- insensitive paths, empty files/directories,build-image, and CLI-c/--pack/build-imageend-to-end plus usage errors.SectorAllocatorTests(+7SeedUsedRangescases): one-pass bulk seeding sorts/coalesces, rejects overlaps and out-of-bounds ranges, refuses to seed after allocations, handles null and zero-count ranges.PathologicalTocTests(+5): the 4,096-entry left spine audits and maps, repairs its deepest entry, salvages to a passing image, and packs to a valid ZAR.ZarValidateTests(10): ZAR↔ISO/CCI tree comparison, per-entry SHA-256/MD5 hashing (case-insensitive paths, missing/directory paths), missing-file and checksum-mismatch detection, CLIvalidate --json/--validate-report, and a clean sector-only rejection for.zarinputs.ZarInputTests(+1): a 65-level name tree is rejected by bothListZarandExtractZarwith the depth message; the existing list/extract/checksum/ convert tests still pass with pre-sized, exact-length extraction.CisoTests(+1): recompressing a CISO throughCompressToCsonow reads the decompressed view directly and round-trips to the same ISO hash.RedumpInputGuardTests(11): every redump mode refuses.cci/.cso, split ISO and.zarinputs with the documented message, while a plain ISO still runs.CliCommandsTests.Convert,MainViewModelTestsand the GUI self-test cover the ZAR→ISO direction/argv;OverwritePromptExtraTestsasserts expected refusals carryNoBugReport.CisoAutoDetectTests.ReaderVerbs_CsoMatchIsoand the split-ISO reader test now compare--rangesand sector-layout output.XisoImageSourceTests(+7 part-suffix cases),CciAutoDetectTests.SecondCciPart_NamesOutputsAfterGameStemandXisoRepairerRefusalTests.Salvage_DefaultOutputPath_Namingcover numbered CCI part naming: extraction, rewrite, recompress and salvage from.2.cciall use the game stem;.10.cci/.0.ccistay ordinary names, and.1.zarkeeps its number.- net8.0/net9.0 - 1980 tests (1979 passed, 1 opt-in skip); net10.0 - 2044 tests (2043 passed, 1 opt-in skip, adds the GUI tests).
Machine-readable-output and I/O-efficiency release. Read-only verbs gain a
stable --json schema (source-generated, trim/AOT-safe) with human logs moved
to stderr, and extraction/creation now pre-size known-length destinations and
use sequential-scan hints. -v/--version also reports the CCISharp,
ZArchiveSharp, runtime and commit metadata.
Full suite green on all three targets: 1860 passed / 1 opt-in skip (1861) on net8.0/net9.0 and 1922 passed / 1 opt-in skip (1923) on net10.0.
- Preallocation / sequential I/O: new additive
IFilesystem.CreateFile(string path, long? expectedLength)default member.LocalFilesystemopens withFileOptions.SequentialScanand appliesSetLengthbefore the first write;MemoryFilesystempreallocates its buffer; custom stores keep the old behavior through the default member.XisoReader.ExtractFile/CopyOutFilepass each entry's size, and plain-ISO sources open withSequentialScan. XisoWriterpre-sizing: after the sector layout is computed, the output is sized once to the exact post-layout extent (plus any prepended partition) before the data phase. The final 64 KiB alignment padding and image bytes are unchanged.- Offset-aware read helpers: new overloads
GetVolumeInfo(string, int?),GetVolumeInfo(Stream, string, int?),ListDirectory(string, string, int?),ListDirectory(Stream, string, string, int?)andGetSectorLayout(string, int?)probe the XISO header at an explicit Redump/XGD partition offset instead of the automatic candidates. - Container-aware ranges:
XisoRanges.GetXisoRanges/GetFileEntriesgainedStreamoverloads and open throughXisoImageSource, so--rangesand range-based archival helpers read split ISO, CISO and CCI inputs. Logger.RouteInfoToError: optional switch that sendsLog/LogLine/FlushtoError, keeping stdout free for machine-readable output.
--jsonon-i,-l,-t,--checksum/checksum,--sector-layout,--ranges,--filetime,--xex-info,--xbe-info,validateand-v/--version. Every document carries"schemaVersion": 1and acommand; list/tree wrap results in animagesarray (one document for multiple inputs), checksum returns achecksumsarray. JSON goes to stdout; banners/progress/warnings/errors go to stderr.- Serialization uses the source-generated
JsonOutputContext(camelCase, nulls omitted), so the trimmed single-file CLI has no reflection fallback. --jsonis rejected for mutating modes (extract, rewrite, create, compress/decompress, redump) with a clear error.- Version enrichment:
-vkeeps its historical first line, then prints XISOSharp, CCISharp, ZArchiveSharp, runtime, OS, architecture and the MinVer commit.-v --jsonemits the same data as a JSON document. - Help text documents
--json,--version, and the new read-only schema.
CliJsonTests(12): every JSON payload parses, stdout/stderr are separated, multi-image list output stays one document, CCI input matches the ISO tree, checksum matches the library digest,validatereports summaries, version metadata is populated, and--jsonrejects extract mode.XbeInfoTests/XexInfoTests: JSON payloads for--xbe-info/--xex-info(plus the existing end-to-end text checks).PreallocationTests(5):LocalFilesystempre-sizing, empty default,MemoryFilesystemcapacity behavior, the default interface-member fallback, and extraction passing each entry size to a customIFilesystem.CliHelpFlagTestsnow asserts the enriched version output while keeping the first-line banner contract.- net8.0/net9.0 - 1861 tests (1860 passed, 1 opt-in skip); net10.0 - 1923 tests (1922 passed, 1 opt-in skip, adds the GUI tests).
Container-input, traversal-hardening and batch-conversion release. XISOSharp now
reads CCI/CCIM images (via the new CCISharp 1.0.0 dependency), split
plain-ISO sets (game.1.iso …), and ZArchive (.zar) inputs, and exposes
one unified detection/open layer (XisoImageSource) for every sector-based
format. The CLI gains compress --format cci, --cci-level/--cci-split,
cci/uncci aliases, convert for ZAR ↔ ISO, ZAR-aware
list/extract/checksum, and --batch conversion on compress, decompress,
convert and split; the GUI gains a CISO/CCI format selector and routes
.cci/.zar drops to the matching tab. The reader's directory walk is now an
explicit in-order stack, so a pathological left-skewed table can no longer
exhaust the process stack or trip the subdirectory depth cap.
Full suite green on all three targets: 1841 passed / 1 opt-in skip (1842) on net8.0/net9.0 and 1903 passed / 1 opt-in skip (1904) on net10.0.
XisoImageSource(XisoImageFormat,XisoImageSourceInfo): extension-led detection with aCISO/CCIMmagic sniff fallback;OpenRead/OpenBlockDevicereturn the decompressed/concatenated view for ISO, split ISO, CISO, CCI and their split variants. Plain files remain ISO candidates.- CCI/CCIM:
XisoCci(CompressToCci,DecompressToIso,DeriveDefaultCciPath,DeriveDefaultIsoPath),CciBlockDevice, andCciNaming; backed by CCISharp 1.0.0 (MIT, pure managed, LZ4). Single-part and.1.cci….9.ccisets are supported. - Split ISO input:
SplitIsoFile/SplitIsoStreamconcatenate<base>.1.iso,.2.iso, … (multi-digit indices included); a missing middle part raisesInvalidDataExceptioninstead of silently truncating. - ZAR input:
XisoZarchive.ListZar,ExtractZar,ConvertZarToIso;XisoChecksum.ComputeZarChecksum/ComputeZarChecksumHexproduce the same SHA3-256 tree hash as the equivalent ISO. Unsafe entry names are rejected. - Unified readers:
XisoReader.OpenImageStreamnow routes CCI and split ISO through the factory;XisoChecksumopens every format throughOpenBlockDevice. Output naming strips.cso/.cci/.1.*suffixes. - In-place guards:
Repair,CopyIntoImageandSetFileTimerefuse CISO and CCI containers with a clear "decompress first" error, even when the file is missing or corrupt. - Recompression:
CisoWriter.CompressToCsoandXisoCci.CompressToCciaccept split ISO/CISO/CCI sources by materializing the decompressed image to a temporary ISO; directory sources still pack then compress. StreamBlockDeviceexposes any seekable stream as anIBlockDevice.- Pathological TOC traversal:
TraverseXisonow walks each directory table with an explicit in-order stack instead of left-subtree recursion.MaxTocDepthbounds subdirectory nesting only; intra-table depth is bounded byMaxTocEntriesPerTableandConstants.MaxTocStackFrames(100k). A 4,096-entry left-skewed chain lists/trees/extracts/rewrites, and the rewrite checksum matches the balanced form.ContinueOnErrorstill skips just the corrupt subtree. - Runtime dependencies are now
ZArchiveSharp1.4.0 andCCISharp1.0.0.
compress --format cso|cci(defaultcso),--cci-level 0..9,--cci-split <bytes>;-l/--leveland--splitremain format-neutral.ccialias forcompress --format cci;unccijoinsdecompress.- Format-specific flag validation:
--ciso-*is rejected for CCI output and--cci-*for CISO output. decompressauto-detects CISO vs CCI (extension plus magic sniff).convert <src.zar|src.iso> <out.iso|out.zar>;-l,-t,-x,--unpackandchecksumaccept.zardirectly.- Batch conversion:
--batch <dir>/--batch-recursiveoncompress,decompress,convertandsplit;--skip-existingresumes,--continue-on-errorkeeps going after a failed file (partial outputs are removed),--jobs 1..64converts in parallel, and--output-namesupports{name}/{ext}/{format}. Duplicate outputs and outputs that would clobber another input are refused before any write.convert --batch --format iso|zarcovers both directions. - Help text and the GUI self-test cover the new flags.
- Compress tab: Format selector (CISO/CCI); output/save dialog and split placeholder follow the selected format.
- Picker filters and drop routing include
.cci/.1.cci; a dropped.zaropens the Extract tab for list/extract/checksum, and compressed drops route to Decompress. - Decompress picker accepts CISO and CCI; collision guards use the matching default output naming.
XisoImageSourceTests: detection table for ISO/XISO/IMG/CISO/split CISO/ CCI/split CCI/split ISO, CCI round-trip, cross-part seeks, magic sniffing, suffix stripping and missing files.CciAutoDetectTests: list/tree/extract/unpack/rewrite/checksum parity, default output naming, CCI decompression and the in-place refusal contracts.SplitIsoAutoDetectTests: extract/list/checksum parity, split CISO/CCI recompression, defaultgame/naming and missing-middle-part errors.CliCciTests: CCI compress/decompress, split sets, aliases, list and format-specific flag rejection.ZarInputTests: ZAR listing/extraction/checksum/convert and CLI wiring.PathologicalTocTests: 4,096-entry left-skewed, right-skewed, alternating and balanced tables; list/tree/extract/rewrite parity, a left self-cycle, and continue-on-error subtree skipping.CliBatchConvertTests: CISO/CCI batch compress, batch decompress, ISO to ZAR convert, batch split, recursive discovery, naming templates (including subdirectories), duplicate-output refusal,--skip-existingresume,--continue-on-errorpartial-output cleanup, and parallel--jobs.- net8.0/net9.0 - 1842 tests (1841 passed, 1 opt-in skip); net10.0 - 1904 tests (1903 passed, 1 opt-in skip, adds the GUI tests).
Extraction-cleanup and static-analysis release. A failed or cancelled extraction no
longer leaves a truncated destination file behind: ExtractFile/CopyOutFile
delete the partial output through the new IFilesystem.DeleteFile member, which
custom destination stores can override (the default keeps the previous no-op
behavior). The solution is clean under JetBrains InspectCode - 0 errors and 0
warnings across every project - and dead members found by the inspection were
removed from the Tester. Full suite green on all three targets: 1760 passed / 1
opt-in skip (1761) on net8.0/net9.0, 1821 passed / 1 opt-in skip (1822) on net10.0.
- Partial-destination cleanup: a copy that throws, reports truncation, or is cancelled removes the destination it wrote, so callers (drag-and-drop prep, batch extraction, resume runs) can never mistake a partial file for a complete one. Cleanup is best-effort and never masks the extraction error.
IFilesystem.DeleteFile: new member with a default no-op implementation - existing custom stores still compile and keep their partial content if they cannot delete.LocalFilesystemdeletes from disk (a missing file is a no-op);MemoryFilesystemremoves the stored snapshot.- Static-analysis cleanup across the library, CLI, GUI, Tester, benchmarks and
tests: redundant default arguments, redundant casts and assignments, dead null
guards, unused fields/properties, and simplified nullability in
Logger.Out/Logger.Error(assigningnullnow storesTextWriter.Null, so the getters never returnnull). No output or format changes.
ExtractRobustnessTests: a truncated copy and a mid-write failure both leave no destination file, including through a customIFilesystem.XisoFilesystemTests:LocalFilesystem.DeleteFileremoves files and treats a missing path as a no-op.- Suite: net8.0/net9.0 - 1761 tests (1760 passed, 1 opt-in skip); net10.0 - 1822 tests (1821 passed, 1 opt-in skip, adds the GUI tests).
Split CISO part sets honor the caller-chosen FileShare when opening images.
CisoSplitFile.OpenParts was hardcoded to FileShare.Read, so
XisoReader.OpenImageStream(path, FileShare.ReadWrite) and
XisoExplorerOptions.Share reached plain ISOs and single-file .cso containers
but not the individual *.1.cso part files - a split set held open by a writer
(sync client, in-progress copy, antivirus) still failed with a sharing violation
on Windows. The share mode now threads to every part. Defaults are unchanged
(FileShare.Read). Full suite green on all three targets: 1758 passed / 1
opt-in skip (1759) on net8.0/net9.0, 1819 passed / 1 opt-in skip (1820) on
net10.0.
- Split CISO share mode:
CisoSplitFile.OpenParts(firstPart, share)accepts a share mode, andCisoBlockDevicethreads the caller'sFileSharethrough to every part file.XisoExplorerOptions.Sharenow covers plain ISOs, single.csocontainers, and split*.1.csopart sets alike.
CisoOpenParts_HonorsCallerShareModepins the share plumbing, including that the default stays read-shared;SplitCso_ExplorerWithReadWriteShare_ CoexistsWithWriterHoldingPartcovers the end-to-endXisoExplorerflow with a writer holding the first part.
Deep-review hardening and GUI experience release. An 80-item review of the whole
repository (path escapes, patch-layout collisions, CWD leaks, partial artifacts,
CLI contract mismatches, vacuous tests, doc drift) is resolved, together with
the follow-up regressions found while re-reviewing those fixes and a final pass
over the fix commits. The desktop app gains Donate/About/Exit header actions, F8
window screenshots, and a startup update prompt backed by the same UpdateCore
- 24-hour cache the CLI uses. Namespace note:
UnpackOptions,ProcessRunResult,ExplorerNode, andXisoExplorerOptionsmoved fromXISOSharptoXISOSharp.Models— addusing XISOSharp.Models;when upgrading from 1.4.1. Targets remainnet8.0/net9.0/net10.0; full suite green on all three (1818 tests on net10.0: 1817 passed, 1 opt-in skip; 1757 on net8.0/net9.0: 1756 passed, 1 opt-in skip). The suite runs fully sequentially (assembly-wideDisableTestParallelization) because create/extract mutate the process CWD.
- Path safety: crafted image names (separators, Windows drive-relative colons, any trailing dot/space) are rejected at extract on Windows or sanitized by repair/salvage; listing, tree, rewrite, and ZAR packing accept every structurally valid name on every host, matching the reference tool (the colon stays valid on Unix where the writer/patcher accept it).
- Patching: the allocator reserves the optimized tag (sector 15), the
ECMA-119 descriptor pair (16-17), and the layout-tool signature sector — also
for header-only volumes; sector counts use 64-bit math; the root table size
is recorded even when the table stays in place; a child offset that would
encode the
0xFFFFempty-child sentinel fails instead of truncating. - Walkers: all child offsets are bounded by the recorded table size, the
all-zero empty-table sentinel is honored,
./..records are skipped consistently, truncated names fail instead of truncating the walk (includingCollectFileEntries), and zero-size directory entries list as empty. - Writing/containers: CWD is restored on every path; a cwd source
(
-c ./-c ..) defaults its output next to the source instead of aborting on the same-leaf guard; relative-dresolves against the caller CWD; failed/cancelled runs delete partial.iso/.cso/.zaroutput (including thebuild-imageremap writer, and closing split-part handles first on Windows) but never a pre-existing file the call did not create; CISO headers/indexes are validated; split part naming handles dotted bases;Latin1Encodingrange checks are overflow-safe. - Repair/audit: a missing optimized tag is written at the disc offset for prepended images; path and device audits agree on trailing magic, empty-image tag probing, and an oversized root table (audit now matches extraction).
XisoPathsresolves both sides of an input==output check against one CWD snapshot;XisoExplorer.Disposeserializes with keep-open reads.
--silentis order-independent in every position, including with-v/--help, and still requires--checksum;--file-time/--preserve-attrs/--jobs/--policyare rejected outside their modes, and--jobsis rejected with--compressor a multi-mode redump run where it cannot take effect;--wipe/--trimhonor-o;--is-optimizedhonors--skip-sectors;--ciso-splitrefuses a source named like its own first part.-Ddeletes.oldonly after a fully successful (validated) rewrite, and a failed file no longer suppresses a later file's success or keeps its backup.- Help shows
-o <output>for the redump modes instead of a positional second file (which is parsed as another input). - stdout/stderr are always UTF-8 instead of the host console code page, so
Latin-1 filenames (
café.txt) render and pipe identically on every platform (matching xdvdfs's UTF-8 output); the battle harness now decodes each tool with its real encoding (extract-xiso Latin-1; xdvdfs, xboxkit, and the CLI UTF-8) so non-ASCII names compare equal instead of collapsing toU+FFFD.
- Donate/About/Exit header actions with an About dialog; F8 screenshots; startup update prompt (subscribed before probing so a fast show cannot hang it); tooltips.
- Drag-and-drop routing fixed (only
*.isofolders go to Batch;.zardrops go to Rebuild in single- and multi-item drops); Wipe/Trim pass-obefore the image;CliStatusupdates on the UI thread; settings persist again; screenshot environment warnings stay local and the fallback folder is tried for security exceptions.
- Shared Serilog pipeline; expected operational warnings are tagged
NoBugReport; the shared API key is double-Base64 encoded (ApiKeyStore); the dedupe map is bounded;ProcessRunnerfalls back to a stable working directory when the inherited CWD was deleted.
- List comparison parses the real
\name (N bytes)format and decodes extract-xiso's Latin-1 output; two empty parses fail instead of passing; remaining dead wrappers (RunQuietAsync) removed.
- Drift fixed (test counts,
--help, Release packing, battle default, coverage OS/figures, Tester CI, sequential-suite description, missing scripts,ConversionPlan.md, namespace samples); publish scripts stage into%TEMP%and merge instead of deleting the protectedpublish*/trees, andpublish-cli.ps1 -Ziprequires an exact tag or-Version <x.y.z>so a pre-release run cannot overwrite a shippedrelease_*.zip;docs/serves Pages (Docsify_sidebar.md) and syncs to the wiki (Home.md+_Sidebar.md) via.github/workflows/wiki.yml.
Dependency and legal maintenance release. ZArchiveSharp moves 1.3.0 → 1.4.0
(drop-in: upstream rewrote its pipeline layer as original MIT work with no
public-surface, wire-format, or CLI changes), and the ZArchiveSharp notice is
refreshed — the library, including the ZArchiveSharp.Pipeline pack/extract
layer XISOSharp uses, is fully MIT. No XISOSharp API or CLI behavior changes;
targets remain net8.0 / net9.0 / net10.0; full suite green on all three
(1427 tests: 1426 passed, 1 opt-in skip, 0 failed).
ZArchiveSharp1.3.0 → 1.4.0. Upstream highlights: original MIT pipeline layer (ZarPipeline,ZarPackEngine,ProcessRunner), stricter per-item batch isolation, and a robust stderr drain that no longer stalls on an inherited pipe. The public surface is unchanged, so ZAR output, CLI semantics, and exit codes are untouched.
LICENSEitem 4 records ZArchiveSharp as fully MIT as of v1.4.0 (Copyright (c) 2026 PureLogicCode.com; lead developer Peterson Fernandes), includingZArchiveSharp.Pipeline.- The packaged library license (
XISOSharp/LICENSE) is synced with the rootLICENSE, so the NuGet package now carries the full third-party notices (extract-xiso BSD-4-clause, xdvdfs, XboxKit, ZArchiveSharp).
- Root
README.mdanddocs/building.mddependency references updated 1.3.0 → 1.4.0.
Integrity-audit release. The CLI's -V audit no longer fails a structurally
sound image just because the optimized tag is missing: it reports the tag
(Optimized: yes/no) and passes raw/unconverted dumps, while structural damage
still fails. Audits now accept .cso images (previously compressed bytes were
read as sectors), the library gains a requireOptimizedTag overload plus the
AuditResult.IsOptimized property, and empty (zero-root) images report tag
presence instead of always false. Targets remain net8.0 / net9.0 /
net10.0; full suite green on all three (1427 tests: 1426 passed, 1 opt-in
skip, 0 failed).
- New overloads
AuditXiso(string isoPath, bool requireOptimizedTag)andAuditXiso(IBlockDevice dev, string isoName, bool requireOptimizedTag). WithrequireOptimizedTag: falsea missing tag is not an audit issue, so raw (unconverted) images audit as valid; the 1-arg overloads keep the original strict behavior (true). - New
AuditResult.IsOptimizedproperty reports whether the tag was found. The empty/zero-root early-return paths previously skipped the tag probe, so an image whose root fields are zero but whose tag is intact reportedfalse; both the path and block-device overloads now probe and report it. AuditXiso(string)now opens throughOpenImageStream(CISO-aware) instead of a plainFileStream, matchingGetVolumeInfo. A.csoinput used to be audited as compressed bytes, producing bogus tree/bounds issues.
-Vis an integrity audit: it printsOptimized: yes/no, a missing tag no longer fails the run, and raw/unconverted images exit 0. Use--is-optimizedfor the strict tag-only probe or--repairto write a missing tag. Help text updated.
- 1427 tests across
net8.0/net9.0/net10.0: 1426 passed, 1 opt-in skip (XISO_UPDATE_FIXTURE=1fixture validator), 0 failed. - New:
CliAuditTests(3 end-to-end-Vruns: optimized, raw passing withOptimized: no, corrupt tree failing),AuditXisoTestsintegrity/tag/CISO cases (4, incl. plain-vs-CISO parity), and device empty-root tag coverage.
coverlet.collector10.0.1 → 10.1.0 (Tests). No library dependency changes.
README.md,XISOSharp/README.md,XISOSharp.Cli/README.md,docs/cli.md, anddocs/api-xisoreader.mddocument the integrity audit, therequireOptimizedTagoverload, andIsOptimized;docs/troubleshooting.mdanddocs/getting-started.mdrefreshed; suite counts updated.- Release bundles now include
WhatsNew.mdnext toREADME.mdandLICENSE.
Correctness and maintenance release. The rewrite -o output name is now
honored for real — including rooted/absolute paths — and a rewrite that fails
to write reports an error instead of exiting 0. Wrapped exceptions carry their
cause, the reference-binary interop tests resolve the current References/
drop again, and the bug-report wire format is locked by tests. Targets remain
net8.0 / net9.0 / net10.0; full suite green on all three (1419 tests:
1418 passed, 1 opt-in skip, 0 failed).
XisoWriter.CreateXisoignoredinNamein rewrite mode, soXisoReader.Rewrite(..., outputName:)(CLI-o) had no effect on the output filename. The name is now used verbatim: relative names resolve against the-ddirectory, and rooted names are kept intact. The Windows drive-letter strip used for legacy names no longer applies to a rooted-o, which turnedC:\out\game.isointo:\out\game.isoand failed with a path-syntax error.XisoReader.DecodeXiso(and thereforeRewrite) now returns the writer's non-zero result when the output cannot be written. Previously the writer logged the failure but the rewrite still reported success and returned 0.- Regression tests:
Rewrite_WithAbsoluteOutputName_UsesProvidedName,Rewrite_UnwritableOutput_ReturnsError.
- Wrapped rethrows embed the caught exception as
InnerException(Meziantou MA0054):ProcessRunnertimeout →TimeoutException,XisoReadertruncated file copy →IOException, GUIMainViewModeloutput-verification failures →InvalidOperationException. Message text is unchanged, so existing diagnostics and exception filters keep working.
- Rewrite (
-r) now checks the decode result: a failed rewrite exits 1 and does not printsuccessfully rewritten(the input stays at<name>.old, exactly as before the fix). -oaccepts relative and rooted paths and uses them as-is.
UpdateCheckerdebug-logs every previously silent catch (offline checks and API/cache failures stay belowWarning, so they never file bug reports); GUICliLocator.ProductVersiondebug-logs unreadable CLI metadata.BugReporterextractsComposeReportand exposesBuildExceptionBlockto tests; newBugReportFormatTests(5) lock the Environment / Error / Exception sections required by the bug-report service.
- 1419 tests across
net8.0/net9.0/net10.0: 1418 passed, 1 opt-in skip (XISO_UPDATE_FIXTURE=1fixture validator), 0 failed. TestConditionsresolves the compiledextract-xiso.exefrom the currentReferences/drop (canonicalReferences/extract-xiso.exe, dated drop root, or in-tree CMake build) instead of the removed202505152050artifact path; the legacyllCompatinterop tests run and pass again.RegenerateFixtureIso_WhenRequestedrenamed toValidateFixtureIso_WhenRequested(it validates only; regeneration stays manual) —docs/testing.mdupdated.
Meziantou.Analyzer3.0.257 → 3.0.290 (all projects),Avalonia12.1.2 → 12.1.3 (GUI),QuestPDF2026.8.0 → 2026.9.1 (Tester),Microsoft.NET.Test.Sdk18.10.0 → 18.10.1 (Tests). No library dependency changes.
- Badge rows (CI, NuGet version/downloads, release, .NET, platform/RIDs,
license, docs site, per-project) added to the root, library, CLI, Tests,
Tester, and docs READMEs; suite counts refreshed;
-orooted-path behavior documented in the CLI reference.
Additive release for VFS-consumer parity (SimpleXisoDrive/Dokan): the probe and
read stack now accepts the rebuilt "sector-0" XISO layout (volume descriptor at
the very start of the image instead of partition sector 32), and the in-place
patcher, sector ranges, and ZAR packing understand it end-to-end. Targets remain
net8.0 / net9.0 / net10.0; full suite green on all three (1412 tests:
1408 passed, 4 pre-existing skips, 0 failed).
VerifyXiso(stream and block-device overloads),GetVolumeInfo,GetFileTimeRaw/SetFileTime(both overloads), andOffsetBlockDevice.Probedetect a volume descriptor at absolute offset 0. Such images reportDiscLseek = 0andDescriptorSector = 0; sector numbers stay partition-relative, soXisoExplorer, directory listing, and bounded file reads work unchanged on them.XisoReader.TryFindHeaderBaseresolves the descriptor base for callers that take a partition offset (standard sector-32 candidate first, then sector-0).GetSectorLayoutmarks the detected descriptor sector as used instead of hardcoding partition sector 32, soSectorAllocator.FromLayoutcan no longer hand out the live header to the in-place patcher.PatchVolumeHeaderRootwrites the relocated root pointer to the active header base (DiscLseek + DescriptorSector * 2048), fixing a silent-corruption path whereCopyInon a sector-0 image overwrote the descriptor or left the header pointing at the old root table.XisoRanges.GetXisoRanges/GetFileEntriesandXisoZarchive.CreateZarresolve the descriptor with the same helper; invalid images keep the historical fallback base and failure behavior.XisoRedump.RebuildRedumprejects sector-0 inputs with an explicit error (repack to the standard sector-32 layout first) because a verbatim embed would place the descriptor at partition sector 0;HasXisoMagicrecognizes sector-0 images so they keep working as.zarsidecar inputs.
- The brute-force seed search now checks the cancellation token inside each worker's candidate chunk. A canceled search stops promptly instead of grinding through the rest of the chunk — removing the coverage-instrumented stall that tripped CI's 15-minute blame-hang watchdog on the net8.0 test host.
- New
XisoRebuiltSector0Tests(12 tests): probe/verify/volume-info parity, explorer listing +OpenReadStream, filetime read/write, block-device probe, sector layout used/free ranges, in-place add/replace/root-table-move, andGetXisoRanges/CreateZarround-trips on sector-0 images.
docs/xiso-format.mddocuments the rebuilt sector-0 variant; theapi-xisoreader.mdprobe table,DescriptorSectorcontract, and the library/CLI READMEs cover the accepted layout and the Redump rebuild restriction.
- Test runs always publish a
.trxartifact for post-mortems and skip hang-dump collection (--blame-hang-dump-type none); the instrumented seed-search stall that aborted the net8.0 job is gone (windows tests dropped from ~15 min to ~1.5 min per TFM).
Additive release for VFS-consumer parity (SimpleXisoDrive/Dokan): the public API
gains bounded in-place file reads, a keep-open explorer mode, descriptor
creation-time/sector surfacing, FileShare control, and Windows attribute
mapping — no behavior change to existing APIs. Targets remain net8.0 /
net9.0 / net10.0; full suite green on all three (1400 tests: 1396 passed,
4 pre-existing skips, 0 failed).
XisoExplorer.OpenReadStream(string)/OpenReadStream(ExplorerNode)return a read-only, seekableStreamover a file's data extent inside the image. Reads are clamped to the entry'sFileSize(not the image length), so a corrupt TOC cannot leak the next file's sectors; seeking at/past the end reads 0 bytes perStreamconventions; CISO/split-CISO images work transparently through the decompressed block device. No copy is made, so 4 GB files stream in place.XisoReader.ReadFileBytes(isoPath, internalPath, Span<byte>, fileOffset)and the stream overload are one-shot conveniences over the same bounds; the stream overload leaves the caller's stream open, and missing paths/directories throwInvalidDataException.- A stateless explorer's read stream owns the image handle (dispose it); a keep-open explorer's read streams stay valid until the explorer is disposed.
- New
XisoExplorerOptions { KeepOpen, Share }andXisoExplorer(string, XisoExplorerOptions):KeepOpenholds one image stream for the explorer's lifetime (metadata calls use the held stream), serializes operations with an internal lock, andDispose()closes the stream — the mount/VFS shape that avoids re-opening the image for every lookup.KeepOpen: falsestays byte-for-byte identical to 1.0.2.
XisoReader.OpenImageStream(path, FileShare)andXisoExplorerOptions.Share: plain-ISO streams pass the share mode through (defaultFileShare.Read, unchanged), and CISO inputs thread it to the container file.FileShare.ReadWritelets a mounted image coexist with AV scanners or sync clients that open the.isofor write.
VolumeInfogainsCreationTime(DateTimeOffset?,nullwhen invalid; raw 0 maps to 1601-01-01),FileTimeRaw, andDescriptorSector(partition-relative sector32for every supported layout — the partition shift isDiscLseek; −1 when invalid) — all populated by the same probeGetVolumeInfoalready performs, so no second open is needed.GetVolumeInfoagrees withGetFileTimefor the same image.
- New
XisoAttributes.ToWindowsFileAttributes(byte): pure bit math mapping the raw XDVDFS attribute byte toSystem.IO.FileAttributes(ReadOnlyalways set;Directory/Hidden/System/ArchiveOR'd in;Normalwhen nothing else applies; reserved bits masked), matching SimpleXisoDrive's locked expectations.
- Modern dark theme: left navigation rail with an accent pill, card layout, green accent palette, rounded inputs and log console, and a dark native title bar on Windows.
- New ZAR tab: packs an ISO/XISO/Redump image into a
.zar(ZArchive/zstd, loadable in Xenia canary) with overwrite/skip/auto-rename collision policies; drop routing and tab-order shortcuts account for the new tab.
XisoExplorer.OpenReadStream(string)and the keep-open constructor no longer leak the image handle when a lookup or probe throws.BoundedSubStreamrejects seeks before the window start withIOException(perStreamconventions) instead of reading preceding image bytes.ReadFileBytesvalidates the path even when the buffer is empty.GetVolumeInfoskips probe candidates past EOF instead of aborting, so a trimmed XGD3 image (smaller than the global candidate offset) is detected.
- Library/Getting-Started quick samples for the VFS use case, and the Utilities
page documents explorer options, the read-bounds contract, and
XisoAttributes.
ZArchiveSharpNuGet dependency updated 1.0.2 → 1.3.0 (mount-friendly reader API, specific open-failure reasons; additive, no wire-format changes).
Release tag 1.0.2.
Targets remain net8.0 / net9.0 / net10.0; full suite green on all three
(1338 tests: 1334 passed, 4 pre-existing skips, 0 failed).
-v (and the usage header) now prints
XISOSharp v<version> for <win|linux|macos|cross-platform> - https://github.com/purelogiccode/XISOSharp
instead of the extract-xiso compatibility line. The version is the MinVer
build stamp with +build metadata trimmed, so it matches the package/assembly
version. Constants.ExisoVersion is kept for provenance and the on-disk
optimized tag (in!xiso!2.7.1 (01.11.14)) is unchanged, so image compatibility
is unaffected. The extract-xiso BSD-4-clause acknowledgement remains in the
shipped LICENSE.
Every interactive launch compares the running version against the latest
GitHub release — at most one request per 24 hours, cached at
%LocalAppData%/XISOSharp/update-check.json. A newer release prints an
[UPDATE] notice with the release page and the matching
release_<version>_<rid>.zip asset, and on an interactive console you are
offered to open the release page in your browser. The check is skipped for
-q/-Q/-v runs and test hosts, never fails the run, and can be disabled
with XISO_NO_UPDATE_CHECK=1.
--sector-layout (volume summary, per-file extents, used/free ranges),
--ranges (system/bone vs file sector ranges), and --is-optimized
(optimized-tag probe, --skip-sectors aware).
Double-clicking XISOSharp.exe with no arguments prints usage and waits for a
keypress instead of closing the console window. Scripts, pipes, test hosts, and
XISO_NO_PAUSE=1 are never blocked.
The shared Serilog pipeline in the CLI, GUI, and Tester forwards
Warning-and-above events to the bug-report API with environment, error, and
exception sections; opt out with XISO_DISABLE_BUGREPORT=1.
- CLI discovery fix for single-file bundles:
ToolLocatornow also probes the directory of the real executable (Environment.ProcessPath) afterAppContext.BaseDirectory, since self-extracting bundles run from%TEMP%\.net\.... This resolves the "CLI not found" state when the GUI runs from a published bundle. - The legacy
XISOSharp.Clifile-name fallback was removed; resolution isXISOSharp(.exe)only. - Status bar and log show a branded product label (
XISOSharp <version>) read from the CLI binary's version metadata instead of echoing the-vbanner. - The app icon is embedded in both the executable and the window.
- Framework-dependent publish builds and stages the CLI beside the GUI
automatically (previous attempts failed with
NETSDK1151).
ToolLocatoris now the shared resolver/probe used by the GUI, Tester, and BattleTests: explicit override → app directory → process directory →PATH, with a bounded, tree-killed-vprobe viaProcessRunner, plus a newToolLocatorTestssuite.Constants.Bannerreports the XISOSharp product version; the extract-xiso baseline constant is retained for provenance.
- GitHub Pages publishes the Docsify documentation, and a workflow syncs the wiki (sidebar included).
LICENSEnow carries the full third-party notices (extract-xiso BSD-4-clause, xdvdfs, XboxKit, ZArchiveSharp); distributed bundles includeLICENSEandREADME.md.- Docs and readmes refreshed for the branded banner, the new inspection verbs, update checks, the GUI bundle layout, and the shared tool locator.
No library dependency changes: ZArchiveSharp stays at 1.0.2, analyzer/Roslynator
versions are unchanged from 1.0.1.
Release tag 1.0.1.
Targets remain net8.0 / net9.0 / net10.0; full suite green on all three
(1290 tests: 1286 passed, 4 pre-existing skips, 0 failed).
Optimizing (-r / Rewrite) an image containing a zero-size directory entry —
seen in the wild in e.g. Marvel vs Capcom 2 — used to write that entry back as a
file (ARC attribute, file data) instead of a directory, breaking the game.
Cause: XisoReader.TraverseXiso in GenerateAvl mode only recursed into
subdirectories with fileSize > 0 and left AvlNode.Subdirectory as null for
zero-size ones; the writer treats null as "file". The fix assigns
AvlNode.EmptySubdirectory, matching upstream extract-xiso build
202609111233, which fixed the same bug in traverse_xiso() (subdirectory left
NULL instead of EMPTY_SUBDIRECTORY). See Rewrite mode
and XISO Format.
XisoChecksum.ComputeImageChecksum used only the BCL
IncrementalHash SHA3-256, which throws PlatformNotSupportedException on OSes
without a SHA3 provider (Windows 10 CNG, OpenSSL 1.x) — all checksum tests
failed there. New pure-managed FIPS 202 SHA3-256 (XISOSharp/Sha3.cs, no new
dependencies, trim/AOT-safe) is now used as a fallback whenever
SHA3_256.IsSupported is false; digests are identical either way (verified
against OpenSSL 3.0, including rate-boundary sizes). See
Checksums.
ZArchiveSharp1.0.1 → 1.0.2, now consumed purely as a NuGet package — the sibling-checkoutProjectReferencefallback was removed, so no side-by-sideCSharp_ZArchiveSharpclone is needed to build. See Building.Meziantou.Analyzer3.0.235 → 3.0.236 (all projects),Avalonia.Diagnostics11.3.21 → 11.3.22 (GUI, Debug-only). Dev-only, no runtime impact.
- Checksum docs (xdvdfs Compat, XisoReader, Utilities) describe the BCL/managed-fallback behavior.
- Rewrite docs (XisoWriter) and the format reference (XISO Format) document the zero-size-directory handling and upstream parity.
- Reference/build docs updated for the NuGet-only ZArchiveSharp consumption and
the
extract-xiso-build-202609111233reference drop. - Library README intro no longer pins a single extract-xiso version number.
Solution-wide Roslynator formatting cleanup (line wrapping, Fill(0) →
Clear(), internal Sha3_256 → Sha3256 rename).
Initial NuGet release: pure-C# port of extract-xiso v2.7.1 (byte-identical
output) extended with XboxKit archival workflows and xdvdfs packing
(build-image remapping, CISO, SHA3-256 checksums). See the
README for the full feature list.