Supervised user whitelists: Cleanup
[chromium-blink-merge.git] / ui / ozone / platform / drm / gpu / drm_util.cc
blob67f3c94e6b00749406021c342924986b55cd527a
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
3 // found in the LICENSE file.
5 #include "ui/ozone/platform/drm/gpu/drm_util.h"
7 #include <fcntl.h>
8 #include <stdint.h>
9 #include <stdlib.h>
10 #include <sys/mman.h>
11 #include <xf86drm.h>
12 #include <xf86drmMode.h>
14 #include "base/strings/stringprintf.h"
15 #include "ui/ozone/platform/drm/gpu/drm_device.h"
16 #include "ui/ozone/platform/drm/gpu/screen_manager.h"
18 namespace ui {
20 namespace {
22 const char kDefaultGraphicsCardPattern[] = "/dev/dri/card%d";
24 bool IsCrtcInUse(uint32_t crtc,
25 const ScopedVector<HardwareDisplayControllerInfo>& displays) {
26 for (size_t i = 0; i < displays.size(); ++i) {
27 if (crtc == displays[i]->crtc()->crtc_id)
28 return true;
31 return false;
34 uint32_t GetCrtc(int fd,
35 drmModeConnector* connector,
36 drmModeRes* resources,
37 const ScopedVector<HardwareDisplayControllerInfo>& displays) {
38 // If the connector already has an encoder try to re-use.
39 if (connector->encoder_id) {
40 ScopedDrmEncoderPtr encoder(drmModeGetEncoder(fd, connector->encoder_id));
41 if (encoder && encoder->crtc_id && !IsCrtcInUse(encoder->crtc_id, displays))
42 return encoder->crtc_id;
45 // Try to find an encoder for the connector.
46 for (int i = 0; i < connector->count_encoders; ++i) {
47 ScopedDrmEncoderPtr encoder(drmModeGetEncoder(fd, connector->encoders[i]));
48 if (!encoder)
49 continue;
51 for (int j = 0; j < resources->count_crtcs; ++j) {
52 // Check if the encoder is compatible with this CRTC
53 if (!(encoder->possible_crtcs & (1 << j)) ||
54 IsCrtcInUse(resources->crtcs[j], displays))
55 continue;
57 return resources->crtcs[j];
61 return 0;
64 } // namespace
66 HardwareDisplayControllerInfo::HardwareDisplayControllerInfo(
67 ScopedDrmConnectorPtr connector,
68 ScopedDrmCrtcPtr crtc)
69 : connector_(connector.Pass()), crtc_(crtc.Pass()) {
72 HardwareDisplayControllerInfo::~HardwareDisplayControllerInfo() {
75 ScopedVector<HardwareDisplayControllerInfo> GetAvailableDisplayControllerInfos(
76 int fd) {
77 ScopedDrmResourcesPtr resources(drmModeGetResources(fd));
78 DCHECK(resources) << "Failed to get DRM resources";
79 ScopedVector<HardwareDisplayControllerInfo> displays;
81 for (int i = 0; i < resources->count_connectors; ++i) {
82 ScopedDrmConnectorPtr connector(
83 drmModeGetConnector(fd, resources->connectors[i]));
85 if (!connector || connector->connection != DRM_MODE_CONNECTED ||
86 connector->count_modes == 0)
87 continue;
89 uint32_t crtc_id = GetCrtc(fd, connector.get(), resources.get(), displays);
90 if (!crtc_id)
91 continue;
93 ScopedDrmCrtcPtr crtc(drmModeGetCrtc(fd, crtc_id));
94 displays.push_back(
95 new HardwareDisplayControllerInfo(connector.Pass(), crtc.Pass()));
98 return displays.Pass();
101 bool SameMode(const drmModeModeInfo& lhs, const drmModeModeInfo& rhs) {
102 return lhs.clock == rhs.clock && lhs.hdisplay == rhs.hdisplay &&
103 lhs.vdisplay == rhs.vdisplay && lhs.vrefresh == rhs.vrefresh &&
104 lhs.hsync_start == rhs.hsync_start && lhs.hsync_end == rhs.hsync_end &&
105 lhs.htotal == rhs.htotal && lhs.hskew == rhs.hskew &&
106 lhs.vsync_start == rhs.vsync_start && lhs.vsync_end == rhs.vsync_end &&
107 lhs.vtotal == rhs.vtotal && lhs.vscan == rhs.vscan &&
108 lhs.flags == rhs.flags && strcmp(lhs.name, rhs.name) == 0;
111 void ForceInitializationOfPrimaryDisplay(const scoped_refptr<DrmDevice>& drm,
112 ScreenManager* screen_manager) {
113 VLOG(2) << "Forcing initialization of primary display.";
114 ScopedVector<HardwareDisplayControllerInfo> displays =
115 GetAvailableDisplayControllerInfos(drm->get_fd());
117 if (displays.empty())
118 return;
120 screen_manager->AddDisplayController(drm, displays[0]->crtc()->crtc_id,
121 displays[0]->connector()->connector_id);
122 screen_manager->ConfigureDisplayController(
123 drm, displays[0]->crtc()->crtc_id, displays[0]->connector()->connector_id,
124 gfx::Point(), displays[0]->connector()->modes[0]);
127 base::FilePath GetPrimaryDisplayCardPath() {
128 struct drm_mode_card_res res;
129 for (int i = 0; /* end on first card# that does not exist */; i++) {
130 std::string card_path = base::StringPrintf(kDefaultGraphicsCardPattern, i);
132 if (access(card_path.c_str(), F_OK) != 0)
133 break;
135 int fd = open(card_path.c_str(), O_RDWR | O_CLOEXEC);
136 if (fd < 0) {
137 VPLOG(1) << "Failed to open '" << card_path << "'";
138 continue;
141 memset(&res, 0, sizeof(struct drm_mode_card_res));
142 int ret = drmIoctl(fd, DRM_IOCTL_MODE_GETRESOURCES, &res);
143 close(fd);
144 if (ret == 0 && res.count_crtcs > 0) {
145 return base::FilePath(card_path);
148 VPLOG_IF(1, ret) << "Failed to get DRM resources for '" << card_path << "'";
151 return base::FilePath();
154 } // namespace ui