cmake: add (commented out) lines for static libc
[android/external-libkmsxx.git] / tests / db.cpp
1 #include <cstdio>
2 #include <algorithm>
4 #include <xf86drm.h>
5 #include <xf86drmMode.h>
6 #include <drm_fourcc.h>
8 #include "kms++.h"
9 #include "utils/color.h"
11 #include "test.h"
13 using namespace std;
14 using namespace kms;
16 static void draw_color_bar(Framebuffer& buf, int old_xpos, int xpos, int width);
18 static void main_loop(Card& card);
20 #define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0]))
22 class OutputFlipHandler
23 {
24 public:
25         OutputFlipHandler(Connector* conn, Crtc* crtc, Framebuffer* fb1, Framebuffer* fb2)
26                 : m_connector(conn), m_crtc(crtc), m_fbs { fb1, fb2 }, m_front_buf(1), m_bar_xpos(0)
27         {
28         }
30         ~OutputFlipHandler()
31         {
32                 delete m_fbs[0];
33                 delete m_fbs[1];
34         }
36         OutputFlipHandler(const OutputFlipHandler& other) = delete;
37         OutputFlipHandler& operator=(const OutputFlipHandler& other) = delete;
39         void set_mode()
40         {
41                 auto mode = m_connector->get_default_mode();
42                 int r = m_crtc->set_mode(m_connector, *m_fbs[0], mode);
43                 ASSERT(r == 0);
44         }
46         void handle_event()
47         {
48                 m_front_buf = (m_front_buf + 1) % 2;
50                 const int bar_width = 20;
51                 const int bar_speed = 8;
53                 auto crtc = m_crtc;
54                 auto fb = m_fbs[(m_front_buf + 1) % 2];
56                 ASSERT(crtc);
57                 ASSERT(fb);
59                 int current_xpos = m_bar_xpos;
60                 int old_xpos = (current_xpos + (fb->width() - bar_width - bar_speed)) % (fb->width() - bar_width);
61                 int new_xpos = (current_xpos + bar_speed) % (fb->width() - bar_width);
63                 draw_color_bar(*fb, old_xpos, new_xpos, bar_width);
65                 m_bar_xpos = new_xpos;
67                 auto& card = crtc->card();
69                 if (card.has_atomic()) {
70                         int r;
72                         AtomicReq ctx(card);
74                         ctx.add(m_crtc, card.get_prop("FB_ID"), fb->id());
76                         r = ctx.test();
77                         ASSERT(r == 0);
79                         r = ctx.commit(this);
80                         ASSERT(r == 0);
81                 } else {
82                         int r = drmModePageFlip(card.fd(), m_crtc->id(), fb->id(), DRM_MODE_PAGE_FLIP_EVENT, this);
83                         ASSERT(r == 0);
84                 }
85         }
87 private:
88         Connector* m_connector;
89         Crtc* m_crtc;
90         Framebuffer* m_fbs[2];
92         int m_front_buf;
93         int m_bar_xpos;
94 };
96 int main()
97 {
98         Card card;
100         if (card.master() == false)
101                 printf("Not DRM master, modeset may fail\n");
103         //card.print_short();
105         vector<OutputFlipHandler*> outputs;
107         for (auto pipe : card.get_connected_pipelines())
108         {
109                 auto conn = pipe.connector;
110                 auto crtc = pipe.crtc;
112                 auto mode = conn->get_default_mode();
114                 auto fb1 = new Framebuffer(card, mode.hdisplay, mode.vdisplay, "XR24");
115                 auto fb2 = new Framebuffer(card, mode.hdisplay, mode.vdisplay, "XR24");
117                 printf("conn %u, crtc %u, fb1 %u, fb2 %u\n", conn->id(), crtc->id(), fb1->id(), fb2->id());
119                 auto output = new OutputFlipHandler(conn, crtc, fb1, fb2);
120                 outputs.push_back(output);
121         }
123         for(auto out : outputs)
124                 out->set_mode();
126         for(auto out : outputs)
127                 out->handle_event();
129         main_loop(card);
131         for(auto out : outputs)
132                 delete out;
135 static void page_flip_handler(int fd, unsigned int frame,
136                               unsigned int sec, unsigned int usec,
137                               void *data)
139         //printf("flip event %d, %d, %u, %u, %p\n", fd, frame, sec, usec, data);
141         auto out = (OutputFlipHandler*)data;
143         out->handle_event();
147 static void main_loop(Card& card)
149         drmEventContext ev = {
150                 .version = DRM_EVENT_CONTEXT_VERSION,
151                 .vblank_handler = 0,
152                 .page_flip_handler = page_flip_handler,
153         };
155         fd_set fds;
157         FD_ZERO(&fds);
159         int fd = card.fd();
161         printf("press enter to exit\n");
163         while (true) {
164                 int r;
166                 FD_SET(0, &fds);
167                 FD_SET(fd, &fds);
169                 r = select(fd + 1, &fds, NULL, NULL, NULL);
170                 if (r < 0) {
171                         fprintf(stderr, "select() failed with %d: %m\n", errno);
172                         break;
173                 } else if (FD_ISSET(0, &fds)) {
174                         fprintf(stderr, "exit due to user-input\n");
175                         break;
176                 } else if (FD_ISSET(fd, &fds)) {
177                         drmHandleEvent(fd, &ev);
178                 }
179         }
183 static const RGB colors32[] = {
184         RGB(255, 255, 255),
185         RGB(255, 0, 0),
186         RGB(255, 255, 255),
187         RGB(0, 255, 0),
188         RGB(255, 255, 255),
189         RGB(0, 0, 255),
190         RGB(255, 255, 255),
191         RGB(200, 200, 200),
192         RGB(255, 255, 255),
193         RGB(100, 100, 100),
194         RGB(255, 255, 255),
195         RGB(50, 50, 50),
196 };
198 static const uint16_t colors16[] = {
199         colors32[0].rgb565(),
200         colors32[1].rgb565(),
201         colors32[2].rgb565(),
202         colors32[3].rgb565(),
203         colors32[4].rgb565(),
204         colors32[5].rgb565(),
205         colors32[6].rgb565(),
206         colors32[7].rgb565(),
207         colors32[8].rgb565(),
208         colors32[9].rgb565(),
209         colors32[10].rgb565(),
210         colors32[11].rgb565(),
211 };
213 static void drm_draw_color_bar_rgb888(Framebuffer& buf, int old_xpos, int xpos, int width)
215         for (unsigned y = 0; y < buf.height(); ++y) {
216                 RGB bcol = colors32[y * ARRAY_SIZE(colors32) / buf.height()];
217                 uint32_t *line = (uint32_t*)(buf.map(0) + buf.stride(0) * y);
219                 if (old_xpos >= 0) {
220                         for (int x = old_xpos; x < old_xpos + width; ++x)
221                                 line[x] = 0;
222                 }
224                 for (int x = xpos; x < xpos + width; ++x)
225                         line[x] = bcol.raw;
226         }
229 static void drm_draw_color_bar_rgb565(Framebuffer& buf, int old_xpos, int xpos, int width)
231         static_assert(ARRAY_SIZE(colors32) == ARRAY_SIZE(colors16), "bad colors arrays");
233         for (unsigned y = 0; y < buf.height(); ++y) {
234                 uint16_t bcol = colors16[y * ARRAY_SIZE(colors16) / buf.height()];
235                 uint16_t *line = (uint16_t*)(buf.map(0) + buf.stride(0) * y);
237                 if (old_xpos >= 0) {
238                         for (int x = old_xpos; x < old_xpos + width; ++x)
239                                 line[x] = 0;
240                 }
242                 for (int x = xpos; x < xpos + width; ++x)
243                         line[x] = bcol;
244         }
247 static void drm_draw_color_bar_semiplanar_yuv(Framebuffer& buf, int old_xpos, int xpos, int width)
249         const uint8_t colors[] = {
250                 0xff,
251                 0x00,
252                 0xff,
253                 0x20,
254                 0xff,
255                 0x40,
256                 0xff,
257                 0x80,
258                 0xff,
259         };
261         for (unsigned y = 0; y < buf.height(); ++y) {
262                 unsigned int bcol = colors[y * ARRAY_SIZE(colors) / buf.height()];
263                 uint8_t *line = (uint8_t*)(buf.map(0) + buf.stride(0) * y);
265                 if (old_xpos >= 0) {
266                         for (int x = old_xpos; x < old_xpos + width; ++x)
267                                 line[x] = 0;
268                 }
270                 for (int x = xpos; x < xpos + width; ++x)
271                         line[x] = bcol;
272         }
275 static void draw_color_bar(Framebuffer& buf, int old_xpos, int xpos, int width)
277         switch (buf.format()) {
278         case DRM_FORMAT_NV12:
279         case DRM_FORMAT_NV21:
280                 // XXX not right but gets something on the screen
281                 drm_draw_color_bar_semiplanar_yuv(buf, old_xpos, xpos, width);
282                 break;
284         case DRM_FORMAT_YUYV:
285         case DRM_FORMAT_UYVY:
286                 // XXX not right but gets something on the screen
287                 drm_draw_color_bar_rgb565(buf, old_xpos, xpos, width);
288                 break;
290         case DRM_FORMAT_RGB565:
291                 drm_draw_color_bar_rgb565(buf, old_xpos, xpos, width);
292                 break;
294         case DRM_FORMAT_XRGB8888:
295                 drm_draw_color_bar_rgb888(buf, old_xpos, xpos, width);
296                 break;
298         default:
299                 ASSERT(false);
300         }