feat(format): read unlimited and printf-style VDS mappings like libhdf5

Unlimited VDS mappings were refused, and printf-style source names
("f-%b.h5") were not expanded, so those regions read as fill (read-matrix
case 0470: 29 of 30 values wrong). All 7 virtual datasets in the libhdf5
test set use such mappings.

Implement H5Dvirtual.c's semantics in the vds module:
- %b is the block number, %% a literal %, other specifiers are an error;
  block j of the virtual selection comes from the source named with j,
  probing from 0 to the first missing source (printf gap 0);
- unlimited source/virtual selections are clipped to what the source's
  current extent fills (H5S_hyper_get_clip_extent_match, partial last
  block included);
- the extent is recomputed as H5Dget_space does (view "last available":
  the largest clip, never below what limited mappings need), exposed as
  vds::virtual_dataset_extent and used by Dataset::shape();
- a source in the other byte order is byte-swapped; other conversions stay
  an error.

Tests: vds_interop::vds_printf_source_names,
vds_unlimited_mappings_follow_source_extents (h5py low-level API, earliest
and latest format) and vds_libhdf5_test_files (vds-eiger, 4_vds and
vds-percival-unlim-maxmin from HDF5's tools/test/testfiles/vds, committed
as fixtures) all compare shape and values with h5py; unit tests for the
clip arithmetic, name parsing and mapping rules.

Co-Authored-By: Claude Opus 5.5 (1M context) <[email protected]>
This commit is contained in:
osobh
2026-09-25 22:10:09 -05:00
co-authored by Claude Opus 5.5
parent e94a52a88b
commit b4a44a2e66
18 changed files with 889 additions and 84 deletions
+7 -1
View File
@@ -72,7 +72,13 @@ fill-value item that did is fixed).
- ~~**Wrong data:** unmapped regions read as 0 instead of the fill value.~~
Fixed 2026-09-25: unmapped elements and missing sources read as the
virtual dataset's fill value.
- `%b` printf-style source names are not expanded.
- ~~`%b` printf-style source names are not expanded.~~ Fixed 2026-09-25:
printf-style and unlimited mappings are read, and the extent is
recomputed from the sources as libhdf5 does. Still open: the
"first missing" view and a printf gap other than 0 (libhdf5 access
properties we always read at their defaults), source-to-virtual type
conversion other than a byte swap, nested virtual sources, and source
files outside the virtual file's directory (refused with an error).
- ~~Hyperslab selection versions 1 and 2 are refused.~~ Fixed 2026-09-25:
versions 1-3 and irregular hyperslabs are decoded.
- ~~The version-1 mapping list written with a 2.0 low bound (flags byte,