1 #include <stdio.h>
2 #include <iostream>
3 #include <unistd.h>
4 #include <fcntl.h>
5 #include <cassert>
6 #include <xf86drm.h>
7 #include <xf86drmMode.h>
8 #include <algorithm>
9
10 #include <kms++/kms++.h>
11
12 using namespace std;
13
14 namespace kms
15 {
16
17 struct PlanePriv
18 {
19 drmModePlanePtr drm_plane;
20 };
21
Plane(Card & card,uint32_t id,uint32_t idx)22 Plane::Plane(Card &card, uint32_t id, uint32_t idx)
23 :DrmPropObject(card, id, DRM_MODE_OBJECT_PLANE, idx)
24 {
25 m_priv = new PlanePriv();
26 m_priv->drm_plane = drmModeGetPlane(this->card().fd(), this->id());
27 assert(m_priv->drm_plane);
28 }
29
~Plane()30 Plane::~Plane()
31 {
32 drmModeFreePlane(m_priv->drm_plane);
33 delete m_priv;
34 }
35
supports_crtc(Crtc * crtc) const36 bool Plane::supports_crtc(Crtc* crtc) const
37 {
38 return m_priv->drm_plane->possible_crtcs & (1 << crtc->idx());
39 }
40
supports_format(PixelFormat fmt) const41 bool Plane::supports_format(PixelFormat fmt) const
42 {
43 auto p = m_priv->drm_plane;
44
45 for (unsigned i = 0; i < p->count_formats; ++i)
46 if ((uint32_t)fmt == p->formats[i])
47 return true;
48
49 return false;
50 }
51
plane_type() const52 PlaneType Plane::plane_type() const
53 {
54 if (card().has_has_universal_planes()) {
55 switch (get_prop_value("type")) {
56 case DRM_PLANE_TYPE_OVERLAY:
57 return PlaneType::Overlay;
58 case DRM_PLANE_TYPE_PRIMARY:
59 return PlaneType::Primary;
60 case DRM_PLANE_TYPE_CURSOR:
61 return PlaneType::Cursor;
62 default:
63 throw invalid_argument("Bad plane type");
64 }
65 } else {
66 return PlaneType::Overlay;
67 }
68 }
69
get_possible_crtcs() const70 vector<Crtc*> Plane::get_possible_crtcs() const
71 {
72 unsigned idx = 0;
73 vector<Crtc*> v;
74 auto crtcs = card().get_crtcs();
75
76 for (uint32_t crtc_mask = m_priv->drm_plane->possible_crtcs;
77 crtc_mask;
78 idx++, crtc_mask >>= 1) {
79
80 if ((crtc_mask & 1) == 0)
81 continue;
82
83 auto iter = find_if(crtcs.begin(), crtcs.end(), [idx](Crtc* crtc) { return crtc->idx() == idx; });
84
85 if (iter == crtcs.end())
86 throw runtime_error("get_possible_crtcs: crtc missing");
87
88 v.push_back(*iter);
89 }
90
91 return v;
92 }
93
get_formats() const94 vector<PixelFormat> Plane::get_formats() const
95 {
96 auto p = m_priv->drm_plane;
97 vector<PixelFormat> r;
98
99 for (unsigned i = 0; i < p->count_formats; ++i)
100 r.push_back((PixelFormat) p->formats[i]);
101
102 return r;
103 }
104
crtc_id() const105 uint32_t Plane::crtc_id() const
106 {
107 return m_priv->drm_plane->crtc_id;
108 }
109
fb_id() const110 uint32_t Plane::fb_id() const
111 {
112 return m_priv->drm_plane->fb_id;
113 }
114
crtc_x() const115 uint32_t Plane::crtc_x() const
116 {
117 return m_priv->drm_plane->crtc_x;
118 }
119
crtc_y() const120 uint32_t Plane::crtc_y() const
121 {
122 return m_priv->drm_plane->crtc_y;
123 }
124
x() const125 uint32_t Plane::x() const
126 {
127 return m_priv->drm_plane->x;
128 }
129
y() const130 uint32_t Plane::y() const
131 {
132 return m_priv->drm_plane->y;
133 }
134
gamma_size() const135 uint32_t Plane::gamma_size() const
136 {
137 return m_priv->drm_plane->gamma_size;
138 }
139
140 }
141