v0.9.0-beta.10#
This software is in beta version, which means it is still undergoing testing and development before its official release. It may contain bugs, errors, or incomplete features that could affect its performance and functionality. By using this software, you agree to accept the risks and limitations associated with beta software. We appreciate your feedback and suggestions to help us improve this software, but we do not guarantee that we will implement them or that the software will meet your expectations. Please use this software at your own discretion and responsibility.
Key Features and Enhancements#
Added
device_idparameter toImage.cuda()method, allowing explicit selection of the target GPU device when copying host images to device memory. When called on an image already in device memory with a differentdevice_id, a direct device-to-device (peer-to-peer) copy is performed without going through host memory.Added
cuda_streamparameter toImage.cuda()method, allowing the caller to specify the CUDA stream for the data transfer.Added read-only
device_idproperty toDecoder,Encoder, andImageclasses.Added read-only
cuda_streamproperty toImageclass.Added keyword-only
precisionparameter tonvimgcodec.as_imageandnvimgcodec.as_images. Use it to describe lower-precision data stored in a wider container, e.g. 12-bit values held in auint16buffer:nvimgcodec.as_image(arr, precision=12). Accepted values are0(orNone, both meaning “use the full bitdepth of the sample data type”) and any integer in1..bitdepth(dtype). For floating-point dtypes only0/Noneor the dtype’s full bitdepth (e.g.32forfloat32) is accepted. Defaults toNone.nvJPEG 2000 encoder now honors custom precision: a value set via
as_image(arr, precision=N)is written into the JPEG 2000 SIZ marker and survives the bitstream round-trip.Other built-in encoders log a warning when given a custom precision and continue encoding at the full type bitdepth.
Added keyword-only
sample_formatparameter toDecodeParamsfor driving the decoder’s output layout and channel order. Must be*_AUTO_COMPONENTS(a.k.a.*_UNCHANGED) or compatible withcolor_spec, otherwise aValueErroris raised. Defaults toI_AUTO_COMPONENTS.Added
SampleFormat.I_AUTO_COMPONENTSandSampleFormat.P_AUTO_COMPONENTSas the preferred names for the case where the caller wants to pin only the channel interleaving (I_/P_) and letcolor_specchoose the components. They are exact aliases ofI_UNCHANGED/P_UNCHANGED(identical values and behaviour); the older*_UNCHANGEDnames remain valid.nvimgcodec.as_image/as_imagesaccept planar (CHW) inputs: pass a concreteP_*format with a(C, H, W)array whose leading axis is at least the format’s arity (single-channelP_Yalso accepts a 2-D(H, W)shape), orP_AUTO_COMPONENTS(P_UNCHANGED) as a layout hint with no arity constraint. Concrete interleaved formats (I_*) are similarly arity-checked against the input’s last axis.Decoder.decode(..., image=)accepts multi-plane externally-managed reuse targets. Cross-layout reuse (e.g. a contiguous HWC buffer used as a CHW decode target) is allowed when the buffer is row- and plane-contiguous; layout mismatches with a padded buffer raiseValueError.Added read-only
num_channelsproperty toImage, returning the total number of channels across all planes. Mirrors the existingCodeStream.num_channelsproperty.Updated CUDA 13 Docker images used to produce release binaries from CUDA Toolkit 13.0 to CUDA Toolkit 13.3.
Breaking change: When
chroma_subsamplingis not specified inEncodeParams, the default for images with at least 3 channels is now codec-dependent: JPEG usesCSS_420(previouslyCSS_444), while other codecs continue to useCSS_444. Images with fewer than 3 channels still default toCSS_GRAY. The 4:2:0 JPEG default is broadly compatible and is the only mode the nvJPEG hardware encoder accepts. Pass an explicitchroma_subsamplingto override - e.g.ChromaSubsampling.CSS_444to keep full-resolution chroma for JPEG.Breaking change:
Image.precisionandCodeStream.precisionnow return the full bitdepth of the sample data type (e.g.8foruint8,16foruint16) when no explicit precision is set, instead of the previous0. Explicit precision values supplied viaas_imageare returned unchanged.Breaking change: TIFF
CodeStreamInfo::sizeand PythonCodeStream.sizenow report the backing stream/file size, rather than an exact per-IFD compressed payload size. The size reported by the previous library version can be computed by using the generic TIFF metadata APIs to query the TIFF tile/strip size tags directly.Breaking change: TIFF pagination and IFD selection model has been reworked:
limit_imageshas been removed.bitstream_offsetandimage_idxnow select a single IFD rather than a parse-start position, reportingnum_images=1.The
next_bitstream_offsetproperty was renamed tonext_ifd_offset; it now exists alongsideifd_offsetwhich reports the current offset of a selected IFD.The TIFF parser keeps a cache of parsed IFDs to avoid repeated work and supports incremental parsing of the root IFD chain which is useful for very large images. See the advanced multi-image example for more details.
Added Torch DataLoader integration example notebook, demonstrating how to plug nvImageCodec into
torch.utils.data.DataLoaderfor GPU-accelerated image decoding.Improved nvJPEG hardware-decoder throughput on multi-engine GPUs for concurrent single-image decoding and batches with mixed chroma subsampling, including Python workloads using one
Decoderper thread.Breaking change: Python decoder is now using
fancy_upsamplingby default for JPEG (C decoder was already using it). Decoded images will now be upsampled using interpolation instead of nearest neighbor, which should improve the quality of the decoded images and make decoded images more similar to those produced by other libraries, but it may reduce the decode speed (especially for HW decoder). By default fancy upsampling with ROI decode is not enabled with nvJPEG version older than 13.2 (available in CTK 13.3) due to decode bug in nvJPEG, to enable it, pass:enable_roi_fancy_upsampling=1option when creating decoder.Updated Docker images to use the newest released nvTIFF, nvCOMP and nvJPEG2000.
Fixed Issues#
Pinned the
nvidia-libnvcomp-cuXXdependency in thenvtiffandallextras to>=5,<6.Fixed
device_idnot being propagated correctly when creating aDecoderorEncoderwith a non-default device.Fixed wrong copy direction in the strided device-to-host path of
Image.cpu()that usedcudaMemcpyHostToDeviceinstead ofcudaMemcpyDeviceToHost.Fixed
DeviceGuardleaking a device switch when constructed in a thread or process with no current driver context.Fixed coordinate-system mismatch for ROI decoding of EXIF-rotated images. When
DecodeParams.apply_exif_orientationis set,nvimgcodecRegion_tis now consistently interpreted in display (post-orientation) coordinates instead of raw codestream coordinates. Previously, ROIs that fit within the display image but exceeded the raw codestream’s smaller axis (for EXIF orientations 5-8, which transpose width and height) were rejected withROI_UNSUPPORTED.Fixed a race in
EncoderandDecoderwhere back-to-back submits on the same instance with different params (e.g. JPEGquality_value,apply_exif_orientation) could cause the first submission’s still-running worker threads to read the second submission’s params, silently producing output that did not match the requested params. Each submission now carries its own per-sample params snapshot, written only after the previous submission’s workers have drained.Fixed
CodeStreamreuse (passing an existingCodeStreamascode_stream_s=toEncoder.encode) when the existingCodeStreamwas created from a file or bytes. Previously the output buffer was left uninitialized in those cases, causing segfaults on the subsequent encode.Fixed CUDA device handling for multi-GPU decode, encode, and image transfer paths. Internal worker threads, generic codec processing, metadata extraction, and device/pinned buffer allocation and release now establish the requested CUDA device before issuing CUDA work or invoking user allocators. Previously, work submitted for a non-current GPU could run with a different current device, causing hangs, allocations on the wrong GPU, or custom allocator/deleter calls on the wrong device.
Reorganized the native install layout so CUDA-major variants can coexist on the same system. The default layout is now:
Linux, with prefix
/usr: runtime libraries in/usr/<libdir>/libnvimgcodec/<cuda_major>, extension modules in/usr/<libdir>/libnvimgcodec/<cuda_major>/extensions, runtime tools in/usr/bin/nvimgcodec/<cuda_major>, public headers in/usr/include, CMake package files in/usr/<libdir>/libnvimgcodec/<cuda_major>/cmake/nvimgcodec, package docs in/usr/share/doc/libnvimgcodec, and the loader drop-in at/etc/ld.so.conf.d/nvimgcodec-<cuda_major>.conf.Windows, with prefix
C:\Program Files\NVIDIA nvImageCodec: runtime DLLs and tools inbin\<cuda_major>, extension DLLs inbin\<cuda_major>\extensions, import/static libraries inlib\libnvimgcodec\<cuda_major>andlib\libnvimgcodec\<cuda_major>\extensions, headers ininclude, CMake package files inlib\libnvimgcodec\<cuda_major>\cmake\nvimgcodec, and docs inshare\doc\libnvimgcodec.
Fixed CPU TIFF decoding of JPEG-compressed images that use YCbCr photometric interpretation in the
libtiffextension.Fixed several planar (CHW) host-device transfer and codec round-trip paths that produced truncated or misaligned planes when the buffer carried per-plane row padding
Hardened TIFF and JPEG 2000 parsers against malformed metadata that previously caused process-fatal
SIGFPE/SIGSEGVcrashes. The TIFF parser now rejects files whoseImageWidthorImageLengthis zero. The JPEG 2000 parser now rejects files whose component sub-sampling factors (XRSiz/YRSiz) are zero, and files whose JP2ihdrimage-header dimensions disagree with the codestreamSIZmarker. The last case previously slipped through to the OpenCV fallback decoder and crashed insidelibopencv_ext(opj_jp2_read_header).Fixed silent zero-fill /
Bad jpegfailures when decoding JPEG Lossless (SOF3) streams on nvJPEG older than 13.0.2, where a payload marker such asCOMMENTorDHTprecedesSOF3(common in DICOM). Contributed by @bluna301 in nvImageCodec#51.Hardened the OpenCV extension’s planar-to-
cv::Matconversion path to reject images with more channels than nvImageCodec supports.Fixed a TIFF batched ROI performance bug for extremely large images with small tiles.
Fixed a crash (
SIGSEGV) when a batch-only decoder (e.g. nvJPEG lossless) was reached through the single-sample fallback after a failed batch decode.
Deprecated and removed features#
Removed the dedicated WSL2 Ubuntu installer package. On WSL2, install the standard Linux (Ubuntu) package instead.
Removed support for nvTIFF versions older than 0.8.0.
Reworked the TIFF code-stream-view model from pagination to IFD selection:
limit_imageshas been removedbitstream_offsetnow selects a single IFD rather than a parse-start positionthe
next_bitstream_offsetproperty was renamed tonext_ifd_offset.