From 1681dd142fb445d007d5cdf164a2803765b209f3 Mon Sep 17 00:00:00 2001
From: foreman
Date: Tue, 22 Jul 2014 17:42:44 -0400
Subject: [PATCH] P4 to Git Change 1058007 by rili@rili_opencl_stg_01 on
2014/07/22 17:28:41
EPR #399808 - Fixed wrong conversion of sRGBA when using host copy instead of blit kernel transfer
Affected files ...
... //depot/stg/opencl/drivers/opencl/api/opencl/amdocl/cl_memobj.cpp#68 edit
... //depot/stg/opencl/drivers/opencl/runtime/device/blit.cpp#3 edit
... //depot/stg/opencl/drivers/opencl/runtime/device/blit.hpp#2 edit
... //depot/stg/opencl/drivers/opencl/runtime/device/gpu/gpublit.cpp#107 edit
---
rocclr/runtime/device/blit.cpp | 40 ++++++++++++++++++++++++++-
rocclr/runtime/device/blit.hpp | 2 ++
rocclr/runtime/device/gpu/gpublit.cpp | 16 +++++++++--
3 files changed, 54 insertions(+), 4 deletions(-)
diff --git a/rocclr/runtime/device/blit.cpp b/rocclr/runtime/device/blit.cpp
index e7ae0a13e3..b2fb94c278 100644
--- a/rocclr/runtime/device/blit.cpp
+++ b/rocclr/runtime/device/blit.cpp
@@ -683,6 +683,20 @@ HostBlitManager::fillImage(
// rowPitch and slicePitch in bytes
size_t devRowPitch;
size_t devSlicePitch;
+
+ void *newpattern = const_cast(pattern);
+ cl_float4 fFillColor;
+
+ // Converting a linear RGB floating-point color value to a normalized 8-bit unsigned integer sRGB value so that the cpu path can treat sRGB as RGB for host transfer.
+ if (memory.owner()->asImage()->getImageFormat().image_channel_order == CL_sRGBA) {
+ float *fColor = static_cast(newpattern);
+ fFillColor.s[0] = sRGBmap(fColor[0]) / 255.0f;
+ fFillColor.s[1] = sRGBmap(fColor[1]) / 255.0f;
+ fFillColor.s[2] = sRGBmap(fColor[2]) / 255.0f;
+ fFillColor.s[3] = fColor[3];
+ newpattern = static_cast(&fFillColor);
+ }
+
// Map memory
void* fillMem = memory.cpuMap(vDev_, (entire) ? Memory::CpuWriteOnly : 0,
startLayer, numLayers, &devRowPitch, &devSlicePitch);
@@ -693,7 +707,7 @@ HostBlitManager::fillImage(
float fillValue[4];
memset(fillValue, 0, sizeof(fillValue));
- memory.owner()->asImage()->getImageFormat().formatColor(pattern, fillValue);
+ memory.owner()->asImage()->getImageFormat().formatColor(newpattern, fillValue);
size_t elementSize = memory.owner()->asImage()->getImageFormat().getElementSize();
size_t offset = origin[0] * elementSize;
@@ -734,4 +748,28 @@ HostBlitManager::fillImage(
return true;
}
+cl_uint
+HostBlitManager::sRGBmap(float fc) const
+{
+ double c = (double)fc;
+
+#ifdef ATI_OS_LINUX
+ if (isnan(c))
+ c = 0.0;
+#else
+ if (_isnan(c))
+ c = 0.0;
+#endif
+
+ if (c > 1.0)
+ c = 1.0;
+ else if (c < 0.0)
+ c = 0.0;
+ else if (c < 0.0031308)
+ c = 12.92 * c;
+ else
+ c = (1055.0/1000.0) * pow(c, 5.0/12.0) - (55.0/1000.0);
+
+ return (cl_uint)(c * 255.0 + 0.5);
+}
} // namespace gpu
diff --git a/rocclr/runtime/device/blit.hpp b/rocclr/runtime/device/blit.hpp
index b9b7346fd2..287fd5ab85 100644
--- a/rocclr/runtime/device/blit.hpp
+++ b/rocclr/runtime/device/blit.hpp
@@ -352,6 +352,8 @@ public:
bool entire = false //!< Entire buffer will be updated
) const;
+ cl_uint sRGBmap(float fc) const;
+
protected:
VirtualDevice& vDev_; //!< Virtual device object
const amd::Device& dev_; //!< Physical device
diff --git a/rocclr/runtime/device/gpu/gpublit.cpp b/rocclr/runtime/device/gpu/gpublit.cpp
index 34dfc5ded9..9a64e6efed 100644
--- a/rocclr/runtime/device/gpu/gpublit.cpp
+++ b/rocclr/runtime/device/gpu/gpublit.cpp
@@ -2583,6 +2583,9 @@ KernelBlitManager::fillImage(
fillType = FillImage;
dim = 3;
+ void *newpattern = const_cast(pattern);
+ cl_uint4 iFillColor;
+
bool rejected = false;
bool releaseView = false;
// For depth, we need to create a view
@@ -2605,6 +2608,13 @@ KernelBlitManager::fillImage(
}
if (gpuMem(memory).cal()->format_ == CM_SURF_FMT_RGBA8_SRGB) {
+ // Converting a linear RGB floating-point color value to a 8-bit unsigned integer sRGB value because hw is not support write_imagef for sRGB.
+ float *fColor = static_cast(newpattern);
+ iFillColor.s[0] = sRGBmap(fColor[0]);
+ iFillColor.s[1] = sRGBmap(fColor[1]);
+ iFillColor.s[2] = sRGBmap(fColor[2]);
+ iFillColor.s[3] = (cl_uint)(fColor[3]*255.0f);
+ newpattern = static_cast(&iFillColor);
for (uint i = 0; i < RejectedFormatChannelTotal; ++i) {
if (RejectedOrder[i].clOldType_ == newFormat.image_channel_order) {
newFormat.image_channel_order = RejectedOrder[i].clNewType_;
@@ -2657,9 +2667,9 @@ KernelBlitManager::fillImage(
// Program kernels arguments for the blit operation
Memory* mem = memView;
setArgument(kernels_[fillType], 0, sizeof(cl_mem), &mem);
- setArgument(kernels_[fillType], 1, sizeof(cl_float4), pattern);
- setArgument(kernels_[fillType], 2, sizeof(cl_int4), pattern);
- setArgument(kernels_[fillType], 3, sizeof(cl_uint4), pattern);
+ setArgument(kernels_[fillType], 1, sizeof(cl_float4), newpattern);
+ setArgument(kernels_[fillType], 2, sizeof(cl_int4), newpattern);
+ setArgument(kernels_[fillType], 3, sizeof(cl_uint4), newpattern);
cl_int fillOrigin[4] = { (cl_int)origin[0],
(cl_int)origin[1],