[SYCL][Bindless][UR] Add support for sRGB image formats#22257
[SYCL][Bindless][UR] Add support for sRGB image formats#22257juanchuletas wants to merge 3 commits into
Conversation
8e6a729 to
15fc9ae
Compare
Update,I tested the changes using: 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
left a comment
There was a problem hiding this comment.
L0 adapter side LGTM, 2 nitpicks.
0x12CC
left a comment
There was a problem hiding this comment.
Thanks, @juanchuletas. Please add relevant tests.
There was a problem hiding this comment.
These changes need corresponding changes in sycl/doc/extensions/experimental/sycl_ext_oneapi_bindless_images.asciidoc to ensure the implementation and specification remain consistent.
7d07faf to
26ae9ea
Compare
|
I was thinking about the current implementation and some scenarios came out. The current implementation exposes Nothing stops the user from doing the following: 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::rgx;We can prohibit that kind of usage from the verify() method if (channel_order.has_value()) {
if (channel_order.value() != image_channel_order::ext_oneapi_srgba) {
throw sycl::exception(
sycl::errc::invalid,
"channel_order only supports ext_oneapi_srgba");
}
if (num_channels != 4) {
throw sycl::exception(
sycl::errc::invalid,
"ext_oneapi_srgba channel order requires num_channels == 4");
}
if (channel_type != image_channel_type::unorm_int8) {
throw sycl::exception(
sycl::errc::invalid,
"ext_oneapi_srgba channel order requires unorm_int8 channel type");
}
}but it feels weird to expose desc.channel_order and only allowing srgb. Other approach is to Make channel_order fully general: validate channel count consistency in verify() for any value set. |
dyniols
left a comment
There was a problem hiding this comment.
This PR is ABI breaking because of changes in image_descriptor struct layout.
I wonder if we could re-work image_descriptor back to support channel_order since it was replaced with num_channels due to lack of support in CUDA.
Here is PR when this change was introduced: #13745
I believe that Level Zero, OpenCL backend should support channel order.
Please add tests exercising the new sRGB path with sampled, unsampled and using pitched memory allocation, through pitched_alloc_device.
There was a problem hiding this comment.
nit: re-align the include comments and add // for std::optional.
Given that restoring channel_order as a primary field would also be an ABI break, and that CUDA does not support channel order natively, what is the preferred approach?
I am open to work on any of the approaches |
I don't think the ABI break is avoidable here. Naturally, a change like this should land with the next major release. In the meantime, we can leverage
I lean towards replacement of |
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_descriptoronly 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.hppAdded an
std::optional<image_channel_order>channel order field toimage_descriptor. This defaults tostd::nulloptto preserve full backward compatibility. Added a validation check inverify()to ensure that whenchannel_orderis set toext_oneapi_srgba, the configuration must use 4 channels and theunorm_int8type, as these are the only values accepted by the Level Zero driver for sRGB images.sycl/source/detail/bindless_images.cppModified
populate_ur_structsto use the provided channel order viachannel_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.cppUpdated
ur2zeImageDescto mapUR_IMAGE_CHANNEL_ORDER_SRGBAto theZE_IMAGE_FORMAT_LAYOUT_8_8_8_8memory layout. Configured the hardware channel assignment forSRGBAto maintain a 1-to-1 mapping, identical to the standardRGBAconfiguration.Modified
urBindlessImagesImageAllocateExpto appendze_srgb_ext_desc_t(withsRGB = true) to theZeImageBindlessDesc.pNextchain whenUR_IMAGE_CHANNEL_ORDER_SRGBAis specified. This forces the hardware to enable the sRGB-to-Linear conversion path during image fetches.Modified
bindlessImagesCreateImplto chainze_srgb_ext_desc_tcorrectly for both sampled and unsampled image paths, ensuring the existingpNextchain order is respected:ZeImageDesc->BindlessDesc->ZeSrgbDesc->ZeSamplerDesc.Proposed Usage