Skip to content

[SYCL][Bindless][UR] Add support for sRGB image formats#22257

Open
juanchuletas wants to merge 2 commits into
intel:syclfrom
juanchuletas:sycl-bindless-srgb-support
Open

[SYCL][Bindless][UR] Add support for sRGB image formats#22257
juanchuletas wants to merge 2 commits into
intel:syclfrom
juanchuletas:sycl-bindless-srgb-support

Conversation

@juanchuletas

@juanchuletas juanchuletas commented Jun 9, 2026

Copy link
Copy Markdown

Summary

This PR adds native sRGB decode support for bindless images through the full DPC++ stack: SYCL API, Unified Runtime, and the Level Zero adapter.

Description

The hardware sampler on Intel Arc GPUs supports native sRGB decode via ze_srgb_ext_desc_t, confirmed by direct Level Zero testing against driver 26.18.38308.1. The driver correctly applies the IEC 61966-2-1 piecewise formula on fetch, returning linear values to the kernel. This capability was not exposed anywhere in the DPC++ or UR stack.

The SYCL bindless image API had no way to request sRGB color space decoding. The image_descriptor only accepted num_channels and channel_type, with the channel order always derived internally. This made it impossible to distinguish between a linear RGBA texture and an sRGB-encoded RGBA texture, forcing applications to manually decode sRGB values on the CPU before upload at a significant memory cost.

Proposed Changes

sycl/include/sycl/ext/oneapi/bindless_images_descriptor.hpp

Added an std::optional<image_channel_order> channel order field to image_descriptor. This defaults to std::nullopt to preserve full backward compatibility. Added a validation check in verify() to ensure that when channel_order is set to ext_oneapi_srgba, the configuration must use 4 channels and the unorm_int8 type, as these are the only values accepted by the Level Zero driver for sRGB images.

sycl/source/detail/bindless_images.cpp

Modified populate_ur_structs to use the provided channel order via channel_order.value_or(get_image_default_channel_order(num_channels)). When the channel order is not set, the behavior remains identical to previous versions. When set, the explicit value is passed to the Unified Runtime.

unified-runtime/source/adapters/level_zero/image_common.cpp

Updated ur2zeImageDesc to map UR_IMAGE_CHANNEL_ORDER_SRGBA to the ZE_IMAGE_FORMAT_LAYOUT_8_8_8_8 memory layout. Configured the hardware channel assignment for SRGBA to maintain a 1-to-1 mapping, identical to the standard RGBA configuration.

Modified urBindlessImagesImageAllocateExp to append ze_srgb_ext_desc_t (with sRGB = true) to the ZeImageBindlessDesc.pNext chain when UR_IMAGE_CHANNEL_ORDER_SRGBA is specified. This forces the hardware to enable the sRGB-to-Linear conversion path during image fetches.

Modified bindlessImagesCreateImpl to chain ze_srgb_ext_desc_t correctly for both sampled and unsampled image paths, ensuring the existing pNext chain order is respected: ZeImageDesc -> BindlessDesc -> ZeSrgbDesc -> ZeSamplerDesc.

Proposed Usage

sycl::ext::oneapi::experimental::image_descriptor desc(
    sycl::range<2>(width, height),
    4,
    sycl::image_channel_type::unorm_int8
);
desc.channel_order = sycl::image_channel_order::ext_oneapi_srgba;

sycl::ext::oneapi::experimental::image_mem imgMem(desc, q);

@juanchuletas juanchuletas requested review from a team as code owners June 9, 2026 01:41
@juanchuletas juanchuletas requested a review from 0x12CC June 9, 2026 01:41
@juanchuletas juanchuletas force-pushed the sycl-bindless-srgb-support branch from 8e6a729 to 15fc9ae Compare June 9, 2026 07:00
@juanchuletas

juanchuletas commented Jun 9, 2026

Copy link
Copy Markdown
Author

Update,

I tested the changes using:

srgb_vs_rgb.cpp

and I got:

Device: Intel(R) Arc(TM) Graphics

Input raw pixel value:            186 (0xba)
Input normalized (unorm_int8):    0.729412
Expected linear :  0.491021

RGBA  result (no decode):  R=0.729412 G=0.729412 B=0.729412 A=1
sRGBA result (hardware decoded): R=0.490745 G=0.490745 B=0.490745 A=1

Difference in R channel:   0.238666

PASS: RGBA returns raw unorm, sRGBA returns decoded linear


@kswiecicki kswiecicki left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

L0 adapter side LGTM, 2 nitpicks.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: You can stack this case with UR_IMAGE_CHANNEL_ORDER_RGBA as they look identical.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: else if (pImageFormat->channelOrder == UR_IMAGE_CHANNEL_ORDER_SRGBA) {

@0x12CC 0x12CC left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks, @juanchuletas. Please add relevant tests.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These changes need corresponding changes in sycl/doc/extensions/experimental/sycl_ext_oneapi_bindless_images.asciidoc to ensure the implementation and specification remain consistent.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants