Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1260)

Side by Side Diff: ui/ozone/platform/drm/gpu/drm_device.cc

Issue 1914343003: Reland: ash: reset color management when new screens are hotplugged (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Add an error when trying to set a gamma table without driver support Created 4 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « ui/ozone/platform/drm/gpu/drm_device.h ('k') | ui/ozone/platform/drm/gpu/drm_display.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2014 The Chromium Authors. All rights reserved. 1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "ui/ozone/platform/drm/gpu/drm_device.h" 5 #include "ui/ozone/platform/drm/gpu/drm_device.h"
6 6
7 #include <fcntl.h> 7 #include <fcntl.h>
8 #include <sys/mman.h> 8 #include <sys/mman.h>
9 #include <unistd.h> 9 #include <unistd.h>
10 #include <xf86drm.h> 10 #include <xf86drm.h>
(...skipping 167 matching lines...) Expand 10 before | Expand all | Expand 10 after
178 ret = drmIoctl(fd, DRM_IOCTL_MODE_DESTROYPROPBLOB, &destroy); 178 ret = drmIoctl(fd, DRM_IOCTL_MODE_DESTROYPROPBLOB, &destroy);
179 return ret < 0 ? -errno : ret; 179 return ret < 0 ? -errno : ret;
180 } 180 }
181 181
182 using ScopedDrmColorLutPtr = std::unique_ptr<DrmColorLut, base::FreeDeleter>; 182 using ScopedDrmColorLutPtr = std::unique_ptr<DrmColorLut, base::FreeDeleter>;
183 using ScopedDrmColorCtmPtr = std::unique_ptr<DrmColorCtm, base::FreeDeleter>; 183 using ScopedDrmColorCtmPtr = std::unique_ptr<DrmColorCtm, base::FreeDeleter>;
184 184
185 ScopedDrmColorLutPtr CreateLutBlob( 185 ScopedDrmColorLutPtr CreateLutBlob(
186 const std::vector<GammaRampRGBEntry>& source) { 186 const std::vector<GammaRampRGBEntry>& source) {
187 TRACE_EVENT0("drm", "CreateLutBlob"); 187 TRACE_EVENT0("drm", "CreateLutBlob");
188 if (source.empty())
189 return nullptr;
190
188 ScopedDrmColorLutPtr lut( 191 ScopedDrmColorLutPtr lut(
189 static_cast<DrmColorLut*>(malloc(sizeof(DrmColorLut) * source.size()))); 192 static_cast<DrmColorLut*>(malloc(sizeof(DrmColorLut) * source.size())));
190 DrmColorLut* p = lut.get(); 193 DrmColorLut* p = lut.get();
191 for (size_t i = 0; i < source.size(); ++i) { 194 for (size_t i = 0; i < source.size(); ++i) {
192 p[i].red = source[i].r; 195 p[i].red = source[i].r;
193 p[i].green = source[i].g; 196 p[i].green = source[i].g;
194 p[i].blue = source[i].b; 197 p[i].blue = source[i].b;
195 } 198 }
196 return lut; 199 return lut;
197 } 200 }
198 201
199 ScopedDrmColorCtmPtr CreateCTMBlob( 202 ScopedDrmColorCtmPtr CreateCTMBlob(
200 const std::vector<float>& correction_matrix) { 203 const std::vector<float>& correction_matrix) {
204 if (correction_matrix.empty())
205 return nullptr;
206
201 ScopedDrmColorCtmPtr ctm( 207 ScopedDrmColorCtmPtr ctm(
202 static_cast<DrmColorCtm*>(malloc(sizeof(DrmColorCtm)))); 208 static_cast<DrmColorCtm*>(malloc(sizeof(DrmColorCtm))));
203 for (size_t i = 0; i < arraysize(ctm->ctm_coeff); ++i) { 209 for (size_t i = 0; i < arraysize(ctm->ctm_coeff); ++i) {
204 if (correction_matrix[i] < 0) { 210 if (correction_matrix[i] < 0) {
205 ctm->ctm_coeff[i] = static_cast<uint64_t>( 211 ctm->ctm_coeff[i] = static_cast<uint64_t>(
206 -correction_matrix[i] * (static_cast<uint64_t>(1) << 32)); 212 -correction_matrix[i] * (static_cast<uint64_t>(1) << 32));
207 ctm->ctm_coeff[i] |= static_cast<uint64_t>(1) << 63; 213 ctm->ctm_coeff[i] |= static_cast<uint64_t>(1) << 63;
208 } else { 214 } else {
209 ctm->ctm_coeff[i] = static_cast<uint64_t>( 215 ctm->ctm_coeff[i] = static_cast<uint64_t>(
210 correction_matrix[i] * (static_cast<uint64_t>(1) << 32)); 216 correction_matrix[i] * (static_cast<uint64_t>(1) << 32));
211 } 217 }
212 } 218 }
213 return ctm; 219 return ctm;
214 } 220 }
215 221
216 bool SetBlobProperty(int fd, 222 bool SetBlobProperty(int fd,
217 uint32_t object_id, 223 uint32_t object_id,
218 uint32_t object_type, 224 uint32_t object_type,
219 uint32_t prop_id, 225 uint32_t prop_id,
220 const char* property_name, 226 const char* property_name,
221 unsigned char* data, 227 unsigned char* data,
222 size_t length) { 228 size_t length) {
223 uint32_t blob_id; 229 uint32_t blob_id = 0;
224 int res; 230 int res;
225 res = CreatePropertyBlob(fd, data, length, &blob_id); 231
226 if (res != 0) { 232 if (data) {
227 LOG(ERROR) << "Error creating property blob: " << base::safe_strerror(res) 233 res = CreatePropertyBlob(fd, data, length, &blob_id);
228 << " for property " << property_name; 234 if (res != 0) {
229 return false; 235 LOG(ERROR) << "Error creating property blob: " << base::safe_strerror(res)
236 << " for property " << property_name;
237 return false;
238 }
230 } 239 }
240
241 bool success = false;
231 res = drmModeObjectSetProperty(fd, object_id, object_type, prop_id, blob_id); 242 res = drmModeObjectSetProperty(fd, object_id, object_type, prop_id, blob_id);
232 if (res != 0) { 243 if (res != 0) {
233 LOG(ERROR) << "Error updating property: " << base::safe_strerror(res) 244 LOG(ERROR) << "Error updating property: " << base::safe_strerror(res)
234 << " for property " << property_name; 245 << " for property " << property_name;
246 } else {
247 success = true;
248 }
249 if (blob_id != 0)
235 DestroyPropertyBlob(fd, blob_id); 250 DestroyPropertyBlob(fd, blob_id);
236 return false; 251 return success;
237 }
238 DestroyPropertyBlob(fd, blob_id);
239 return true;
240 } 252 }
241 253
242 std::vector<GammaRampRGBEntry> ResampleLut( 254 std::vector<GammaRampRGBEntry> ResampleLut(
243 const std::vector<GammaRampRGBEntry>& lut_in, 255 const std::vector<GammaRampRGBEntry>& lut_in,
244 size_t desired_size) { 256 size_t desired_size) {
245 TRACE_EVENT1("drm", "ResampleLut", "desired_size", desired_size); 257 TRACE_EVENT1("drm", "ResampleLut", "desired_size", desired_size);
258 if (lut_in.empty())
259 return std::vector<GammaRampRGBEntry>();
260
246 if (lut_in.size() == desired_size) 261 if (lut_in.size() == desired_size)
247 return lut_in; 262 return lut_in;
248 263
249 std::vector<GammaRampRGBEntry> result; 264 std::vector<GammaRampRGBEntry> result;
250 result.resize(desired_size); 265 result.resize(desired_size);
251 266
252 for (size_t i = 0; i < desired_size; ++i) { 267 for (size_t i = 0; i < desired_size; ++i) {
253 size_t base_index = lut_in.size() * i / desired_size; 268 size_t base_index = lut_in.size() * i / desired_size;
254 size_t remaining = lut_in.size() * i % desired_size; 269 size_t remaining = lut_in.size() * i % desired_size;
255 if (base_index < lut_in.size() - 1) { 270 if (base_index < lut_in.size() - 1) {
(...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after
667 682
668 bool DrmDevice::DropMaster() { 683 bool DrmDevice::DropMaster() {
669 TRACE_EVENT1("drm", "DrmDevice::DropMaster", "path", device_path_.value()); 684 TRACE_EVENT1("drm", "DrmDevice::DropMaster", "path", device_path_.value());
670 DCHECK(file_.IsValid()); 685 DCHECK(file_.IsValid());
671 return (drmDropMaster(file_.GetPlatformFile()) == 0); 686 return (drmDropMaster(file_.GetPlatformFile()) == 0);
672 } 687 }
673 688
674 bool DrmDevice::SetGammaRamp(uint32_t crtc_id, 689 bool DrmDevice::SetGammaRamp(uint32_t crtc_id,
675 const std::vector<GammaRampRGBEntry>& lut) { 690 const std::vector<GammaRampRGBEntry>& lut) {
676 ScopedDrmCrtcPtr crtc = GetCrtc(crtc_id); 691 ScopedDrmCrtcPtr crtc = GetCrtc(crtc_id);
692 size_t gamma_size = static_cast<size_t>(crtc->gamma_size);
693
694 if (gamma_size == 0 && lut.empty())
695 return true;
696
697 if (gamma_size == 0) {
698 LOG(ERROR) << "Gamma table not supported";
699 return false;
700 }
677 701
678 // TODO(robert.bradford) resample the incoming ramp to match what the kernel 702 // TODO(robert.bradford) resample the incoming ramp to match what the kernel
679 // expects. 703 // expects.
680 if (static_cast<size_t>(crtc->gamma_size) != lut.size()) { 704 if (!lut.empty() && gamma_size != lut.size()) {
681 LOG(ERROR) << "Gamma table size mismatch: supplied " << lut.size() 705 LOG(ERROR) << "Gamma table size mismatch: supplied " << lut.size()
682 << " expected " << crtc->gamma_size; 706 << " expected " << gamma_size;
707 return false;
683 } 708 }
684 709
685 std::vector<uint16_t> r, g, b; 710 std::vector<uint16_t> r, g, b;
686 r.reserve(lut.size()); 711 r.reserve(gamma_size);
687 g.reserve(lut.size()); 712 g.reserve(gamma_size);
688 b.reserve(lut.size()); 713 b.reserve(gamma_size);
689 714
690 for (size_t i = 0; i < lut.size(); ++i) { 715 if (lut.empty()) {
691 r.push_back(lut[i].r); 716 // Create a linear gamma ramp table to deactivate the feature.
692 g.push_back(lut[i].g); 717 for (size_t i = 0; i < gamma_size; ++i) {
693 b.push_back(lut[i].b); 718 uint16_t value = (i * ((1 << 16) - 1)) / (gamma_size - 1);
719 r.push_back(value);
720 g.push_back(value);
721 b.push_back(value);
722 }
723 } else {
724 for (size_t i = 0; i < gamma_size; ++i) {
725 r.push_back(lut[i].r);
726 g.push_back(lut[i].g);
727 b.push_back(lut[i].b);
728 }
694 } 729 }
695 730
696 DCHECK(file_.IsValid()); 731 DCHECK(file_.IsValid());
697 TRACE_EVENT0("drm", "DrmDevice::SetGamma"); 732 TRACE_EVENT0("drm", "DrmDevice::SetGamma");
698 return (drmModeCrtcSetGamma(file_.GetPlatformFile(), crtc_id, r.size(), &r[0], 733 return (drmModeCrtcSetGamma(file_.GetPlatformFile(), crtc_id, r.size(), &r[0],
699 &g[0], &b[0]) == 0); 734 &g[0], &b[0]) == 0);
700 } 735 }
701 736
702 bool DrmDevice::SetColorCorrection( 737 bool DrmDevice::SetColorCorrection(
703 uint32_t crtc_id, 738 uint32_t crtc_id,
(...skipping 12 matching lines...) Expand all
716 degamma_lut_size = crtc_props->prop_values[i]; 751 degamma_lut_size = crtc_props->prop_values[i];
717 } 752 }
718 if (property && !strcmp(property->name, "GAMMA_LUT_SIZE")) { 753 if (property && !strcmp(property->name, "GAMMA_LUT_SIZE")) {
719 gamma_lut_size = crtc_props->prop_values[i]; 754 gamma_lut_size = crtc_props->prop_values[i];
720 } 755 }
721 756
722 if (degamma_lut_size && gamma_lut_size) 757 if (degamma_lut_size && gamma_lut_size)
723 break; 758 break;
724 } 759 }
725 760
761 // If we can't find the degamma & gamma lut size, it means the properties
762 // aren't available. We should then use the legacy gamma ramp ioctl.
726 if (degamma_lut_size == 0 || gamma_lut_size == 0) { 763 if (degamma_lut_size == 0 || gamma_lut_size == 0) {
727 LOG(WARNING) << "No available (de)gamma tables."; 764 return SetGammaRamp(crtc_id, gamma_lut);
728 return false;
729 } 765 }
730 766
731 ScopedDrmColorLutPtr degamma_blob_data = 767 ScopedDrmColorLutPtr degamma_blob_data =
732 CreateLutBlob(ResampleLut(degamma_lut, degamma_lut_size)); 768 CreateLutBlob(ResampleLut(degamma_lut, degamma_lut_size));
733 ScopedDrmColorLutPtr gamma_blob_data = 769 ScopedDrmColorLutPtr gamma_blob_data =
734 CreateLutBlob(ResampleLut(gamma_lut, gamma_lut_size)); 770 CreateLutBlob(ResampleLut(gamma_lut, gamma_lut_size));
735 ScopedDrmColorCtmPtr ctm_blob_data = CreateCTMBlob(correction_matrix); 771 ScopedDrmColorCtmPtr ctm_blob_data = CreateCTMBlob(correction_matrix);
736 772
737 for (uint32_t i = 0; i < crtc_props->count_props; ++i) { 773 for (uint32_t i = 0; i < crtc_props->count_props; ++i) {
738 ScopedDrmPropertyPtr property( 774 ScopedDrmPropertyPtr property(
(...skipping 24 matching lines...) Expand all
763 reinterpret_cast<unsigned char*>(ctm_blob_data.get()), 799 reinterpret_cast<unsigned char*>(ctm_blob_data.get()),
764 sizeof(DrmColorCtm))) 800 sizeof(DrmColorCtm)))
765 return false; 801 return false;
766 } 802 }
767 } 803 }
768 804
769 return true; 805 return true;
770 } 806 }
771 807
772 } // namespace ui 808 } // namespace ui
OLDNEW
« no previous file with comments | « ui/ozone/platform/drm/gpu/drm_device.h ('k') | ui/ozone/platform/drm/gpu/drm_display.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698