OLD | NEW |
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/crtc_controller.h" | 5 #include "ui/ozone/platform/drm/gpu/crtc_controller.h" |
6 | 6 |
7 #include "base/logging.h" | 7 #include "base/logging.h" |
8 #include "base/time/time.h" | 8 #include "base/time/time.h" |
9 #include "ui/ozone/platform/drm/gpu/drm_device.h" | 9 #include "ui/ozone/platform/drm/gpu/drm_device.h" |
10 #include "ui/ozone/platform/drm/gpu/page_flip_observer.h" | 10 #include "ui/ozone/platform/drm/gpu/page_flip_observer.h" |
11 #include "ui/ozone/platform/drm/gpu/scanout_buffer.h" | 11 #include "ui/ozone/platform/drm/gpu/scanout_buffer.h" |
12 | 12 |
13 namespace ui { | 13 namespace ui { |
14 | 14 |
15 CrtcController::CrtcController(const scoped_refptr<DrmDevice>& drm, | 15 CrtcController::CrtcController(const scoped_refptr<DrmDevice>& drm, |
16 uint32_t crtc, | 16 uint32_t crtc, |
17 uint32_t connector) | 17 uint32_t connector) |
18 : drm_(drm), | 18 : drm_(drm), |
19 crtc_(crtc), | 19 crtc_(crtc), |
20 connector_(connector), | 20 connector_(connector), |
21 saved_crtc_(drm->GetCrtc(crtc)), | 21 saved_crtc_(drm->GetCrtc(crtc)), |
22 is_disabled_(true), | 22 is_disabled_(true), |
23 page_flip_pending_(false), | 23 page_flip_pending_(false), |
24 time_of_last_flip_(0) { | 24 time_of_last_flip_(0) { |
25 } | 25 } |
26 | 26 |
27 CrtcController::~CrtcController() { | 27 CrtcController::~CrtcController() { |
28 if (!is_disabled_) { | 28 if (!is_disabled_) { |
29 drm_->SetCrtc(saved_crtc_.get(), std::vector<uint32_t>(1, connector_)); | 29 drm_->SetCrtc(saved_crtc_.get(), std::vector<uint32_t>(1, connector_)); |
30 UnsetCursor(); | 30 SetCursor(nullptr); |
31 } | 31 } |
32 } | 32 } |
33 | 33 |
34 bool CrtcController::Modeset(const OverlayPlane& plane, drmModeModeInfo mode) { | 34 bool CrtcController::Modeset(const OverlayPlane& plane, drmModeModeInfo mode) { |
35 if (!drm_->SetCrtc(crtc_, plane.buffer->GetFramebufferId(), | 35 if (!drm_->SetCrtc(crtc_, plane.buffer->GetFramebufferId(), |
36 std::vector<uint32_t>(1, connector_), &mode)) { | 36 std::vector<uint32_t>(1, connector_), &mode)) { |
37 PLOG(ERROR) << "Failed to modeset: crtc=" << crtc_ | 37 PLOG(ERROR) << "Failed to modeset: crtc=" << crtc_ |
38 << " connector=" << connector_ | 38 << " connector=" << connector_ |
39 << " framebuffer_id=" << plane.buffer->GetFramebufferId() | 39 << " framebuffer_id=" << plane.buffer->GetFramebufferId() |
40 << " mode=" << mode.hdisplay << "x" << mode.vdisplay << "@" | 40 << " mode=" << mode.hdisplay << "x" << mode.vdisplay << "@" |
41 << mode.vrefresh; | 41 << mode.vrefresh; |
42 return false; | 42 return false; |
43 } | 43 } |
44 | 44 |
45 mode_ = mode; | 45 mode_ = mode; |
46 pending_planes_.clear(); | 46 pending_planes_.clear(); |
47 is_disabled_ = false; | 47 is_disabled_ = false; |
48 | 48 |
49 // drmModeSetCrtc has an immediate effect, so we can assume that the current | 49 // drmModeSetCrtc has an immediate effect, so we can assume that the current |
50 // planes have been updated. However if a page flip is still pending, set the | 50 // planes have been updated. However if a page flip is still pending, set the |
51 // pending planes to the same values so that the callback keeps the correct | 51 // pending planes to the same values so that the callback keeps the correct |
52 // state. | 52 // state. |
53 current_planes_ = std::vector<OverlayPlane>(1, plane); | 53 current_planes_ = std::vector<OverlayPlane>(1, plane); |
54 if (page_flip_pending_) | 54 if (page_flip_pending_) |
55 pending_planes_ = current_planes_; | 55 pending_planes_ = current_planes_; |
56 | 56 |
| 57 if (!ResetCursor()) |
| 58 return false; |
| 59 |
57 return true; | 60 return true; |
58 } | 61 } |
59 | 62 |
60 bool CrtcController::Disable() { | 63 bool CrtcController::Disable() { |
61 if (is_disabled_) | 64 if (is_disabled_) |
62 return true; | 65 return true; |
63 | 66 |
64 is_disabled_ = true; | 67 is_disabled_ = true; |
65 return drm_->DisableCrtc(crtc_); | 68 return drm_->DisableCrtc(crtc_); |
66 } | 69 } |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
111 static_cast<uint64_t>(seconds) * base::Time::kMicrosecondsPerSecond + | 114 static_cast<uint64_t>(seconds) * base::Time::kMicrosecondsPerSecond + |
112 useconds; | 115 useconds; |
113 | 116 |
114 current_planes_.clear(); | 117 current_planes_.clear(); |
115 current_planes_.swap(pending_planes_); | 118 current_planes_.swap(pending_planes_); |
116 | 119 |
117 FOR_EACH_OBSERVER(PageFlipObserver, observers_, OnPageFlipEvent()); | 120 FOR_EACH_OBSERVER(PageFlipObserver, observers_, OnPageFlipEvent()); |
118 } | 121 } |
119 | 122 |
120 bool CrtcController::SetCursor(const scoped_refptr<ScanoutBuffer>& buffer) { | 123 bool CrtcController::SetCursor(const scoped_refptr<ScanoutBuffer>& buffer) { |
121 DCHECK(!is_disabled_); | 124 DCHECK(!is_disabled_ || !buffer); |
122 cursor_buffer_ = buffer; | 125 cursor_buffer_ = buffer; |
123 return drm_->SetCursor(crtc_, buffer->GetHandle(), buffer->GetSize()); | |
124 } | |
125 | 126 |
126 bool CrtcController::UnsetCursor() { | 127 return ResetCursor(); |
127 bool state = drm_->SetCursor(crtc_, 0, gfx::Size()); | |
128 cursor_buffer_ = NULL; | |
129 return state; | |
130 } | 128 } |
131 | 129 |
132 bool CrtcController::MoveCursor(const gfx::Point& location) { | 130 bool CrtcController::MoveCursor(const gfx::Point& location) { |
133 DCHECK(!is_disabled_); | 131 DCHECK(!is_disabled_); |
134 return drm_->MoveCursor(crtc_, location); | 132 return drm_->MoveCursor(crtc_, location); |
135 } | 133 } |
136 | 134 |
137 void CrtcController::AddObserver(PageFlipObserver* observer) { | 135 void CrtcController::AddObserver(PageFlipObserver* observer) { |
138 observers_.AddObserver(observer); | 136 observers_.AddObserver(observer); |
139 } | 137 } |
140 | 138 |
141 void CrtcController::RemoveObserver(PageFlipObserver* observer) { | 139 void CrtcController::RemoveObserver(PageFlipObserver* observer) { |
142 observers_.RemoveObserver(observer); | 140 observers_.RemoveObserver(observer); |
143 } | 141 } |
144 | 142 |
| 143 bool CrtcController::ResetCursor() { |
| 144 uint32_t handle = 0; |
| 145 gfx::Size size; |
| 146 |
| 147 if (cursor_buffer_) { |
| 148 handle = cursor_buffer_->GetHandle(); |
| 149 size = cursor_buffer_->GetSize(); |
| 150 } |
| 151 |
| 152 bool status = drm_->SetCursor(crtc_, handle, size); |
| 153 if (!status) { |
| 154 PLOG(ERROR) << "drmModeSetCursor: device " << drm_->device_path().value() |
| 155 << " crtc " << crtc_ << " handle " << handle << " size " |
| 156 << size.ToString(); |
| 157 } |
| 158 |
| 159 return status; |
| 160 } |
| 161 |
145 } // namespace ui | 162 } // namespace ui |
OLD | NEW |