1 /**************************************************************************
3 * Copyright 2016 Samsung Electronics co., Ltd. All Rights Reserved.
5 * Contact: Konstantin Drabeniuk <k.drabeniuk@samsung.com>
6 * Contact: Andrii Sokolenko <a.sokolenko@samsung.com>
7 * Contact: Roman Marchenko <r.marchenko@samsung.com>
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the
11 * "Software"), to deal in the Software without restriction, including
12 * without limitation the rights to use, copy, modify, merge, publish,
13 * distribute, sub license, and/or sell copies of the Software, and to
14 * permit persons to whom the Software is furnished to do so, subject to
15 * the following conditions:
17 * The above copyright notice and this permission notice (including the
18 * next paragraph) shall be included in all copies or substantial portions
21 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
22 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
23 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
24 * IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
25 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
26 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
27 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 **************************************************************************/
34 class TDMBackendCapture : public TDMBackendDisplay
40 tdm_capture_capability capabilities;
41 const tbm_format *formats;
49 tbm_surface_h buffers[3];
51 tdm_info_capture info;
55 const tdm_output_mode *mode;
69 bool FindLayer(int output_idx, tbm_format fmt, tdm_pos *punch);
70 bool TestPrepareDefault(void);
71 bool TestPrepare(int output_idx, int w, int h, tbm_format fmt, tdm_transform t, tdm_capture_type c, int frequency, bool stretch);
73 void ShowBuffer(int b, tdm_pos *pos);
75 void DumpBuffer(int b, char *test);
76 void DestroyBuffers(void);
79 TDMBackendCapture::TDMBackendCapture()
81 has_capture_cap = false;
83 capabilities = (tdm_capture_capability)0;
86 min_w = min_h = max_w = max_h = preferred_align = -1;
88 for (int b = 0; b < 3; b++)
90 memset(&info, 0, sizeof info);
99 memset(&dst_pos, 0, sizeof dst_pos);
105 void TDMBackendCapture::SetUp(void)
107 tdm_display_capability dpy_capabilities;
109 TDMBackendDisplay::SetUp();
111 ASSERT_EQ(tdm_display_get_capabilities(dpy, &dpy_capabilities), TDM_ERROR_NONE);
112 has_capture_cap = dpy_capabilities & TDM_DISPLAY_CAPABILITY_CAPTURE;
114 if (!has_capture_cap)
117 ASSERT_EQ(tdm_display_get_capture_capabilities(dpy, &capabilities), TDM_ERROR_NONE);
118 ASSERT_GT(capabilities, 0);
119 ASSERT_EQ(tdm_display_get_capture_available_formats(dpy, &formats, &format_count), TDM_ERROR_NONE);
120 ASSERT_NE(formats, NULL);
121 ASSERT_GT(format_count, 0);
122 ASSERT_EQ(tdm_display_get_capture_available_size(dpy, &min_w, &min_h, &max_w, &max_h, &preferred_align), TDM_ERROR_NONE);
123 ASSERT_TRUE(min_w == -1 || min_w > 0);
124 ASSERT_TRUE(min_h == -1 || min_h > 0);
125 ASSERT_TRUE(max_w == -1 || max_w > 0);
126 ASSERT_TRUE(max_h == -1 || max_h > 0);
127 ASSERT_TRUE(preferred_align == -1 || preferred_align > 0);
129 for (int o = 0; o < output_count; o++) {
130 if (!tc_tdm_output_is_connected(outputs[o]))
133 ASSERT_EQ(tc_tdm_output_prepare(dpy, outputs[o], true), true);
137 void TDMBackendCapture::TearDown(void)
140 tdm_capture_destroy(capture);
142 for (int o = 0; o < output_count; o++) {
143 if (!tc_tdm_output_is_connected(outputs[o]))
146 ASSERT_EQ(tc_tdm_output_unset(dpy, outputs[o]), true);
151 TDMBackendDisplay::TearDown();
154 bool TDMBackendCapture::FindLayer(int output_idx, tbm_format fmt, tdm_pos *punch)
158 int primary_zpos, zpos;
159 tdm_layer *primary = tc_tdm_output_get_primary_layer(outputs[output_idx]);
160 TDM_UT_RETURN_FALSE_IF_FAIL(primary != NULL);
161 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_output_get_layer_count(outputs[output_idx], &count) == TDM_ERROR_NONE);
162 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_get_zpos(primary, &primary_zpos) == TDM_ERROR_NONE);
166 for (int l = 0; l < count; l++) {
168 const tbm_format *dst_formats;
169 int dst_format_count;
171 tdm_layer *temp = tdm_output_get_layer(outputs[output_idx], l, &ret);
172 TDM_UT_RETURN_FALSE_IF_FAIL(ret == TDM_ERROR_NONE);
173 TDM_UT_RETURN_FALSE_IF_FAIL(temp != NULL);
174 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_is_usable(temp, &usable) == TDM_ERROR_NONE);
175 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_get_zpos(temp, &zpos) == TDM_ERROR_NONE);
176 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_get_available_formats(temp, &dst_formats, &dst_format_count) == TDM_ERROR_NONE);
177 TDM_UT_RETURN_FALSE_IF_FAIL(dst_formats != NULL);
178 TDM_UT_RETURN_FALSE_IF_FAIL(dst_format_count > 0);
182 for (int f = 0; f < dst_format_count; f++) {
183 if (dst_formats[f] == fmt) {
192 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_get_index(dst_layer, &dst_layer_index) == TDM_ERROR_NONE);
197 if (dst_layer && (dst_zpos < primary_zpos)) {
198 tbm_surface_h displaying_buffer = tdm_layer_get_displaying_buffer(primary, &ret);
199 TDM_UT_RETURN_FALSE_IF_FAIL(ret == TDM_ERROR_NONE);
200 TDM_UT_RETURN_FALSE_IF_FAIL(displaying_buffer != NULL);
201 tdm_helper_clear_buffer_pos(displaying_buffer, punch);
207 bool TDMBackendCapture::TestPrepareDefault(void)
211 for (int o = 0; o < output_count; o++) {
212 if (!tc_tdm_output_is_connected(outputs[o]))
215 capture = tdm_output_create_capture(outputs[o], &ret);
216 TDM_UT_RETURN_FALSE_IF_FAIL(ret == TDM_ERROR_NONE);
217 TDM_UT_RETURN_FALSE_IF_FAIL(capture != NULL);
219 TDM_UT_RETURN_FALSE_IF_FAIL(tc_tdm_buffer_create(TDM_UT_BUFFER_SIZE, TDM_UT_BUFFER_SIZE, formats[0], 0, false, 3, buffers) == true);
220 TDM_UT_RETURN_FALSE_IF_FAIL(tc_tdm_capture_fill_info(outputs[o], buffers[0], TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false, &info) == true);
221 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_capture_set_info(capture, &info) == TDM_ERROR_NONE);
229 return (capture) ? true : false;
232 bool TDMBackendCapture::TestPrepare(int output_idx, int w, int h, tbm_format fmt, tdm_transform t, tdm_capture_type c, int frequency, bool stretch)
237 TDM_UT_RETURN_FALSE_IF_FAIL(outputs != NULL);
238 TDM_UT_RETURN_FALSE_IF_FAIL(output_count > 0);
239 TDM_UT_RETURN_FALSE_IF_FAIL(output_count >= output_idx);
241 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_display_get_capture_capabilities(dpy, &capabilities) == TDM_ERROR_NONE);
242 TDM_UT_RETURN_FALSE_IF_FAIL(capabilities > 0);
244 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_display_get_capture_available_size(dpy, &min_w, &min_h, &max_w, &max_h, &preferred_align) == TDM_ERROR_NONE);
245 TDM_UT_RETURN_FALSE_IF_FAIL(min_w == -1 || min_w > 0);
246 TDM_UT_RETURN_FALSE_IF_FAIL(min_h == -1 || min_h > 0);
247 TDM_UT_RETURN_FALSE_IF_FAIL(max_w == -1 || max_w > 0);
248 TDM_UT_RETURN_FALSE_IF_FAIL(max_h == -1 || max_h > 0);
249 TDM_UT_RETURN_FALSE_IF_FAIL(preferred_align == -1 || preferred_align > 0);
251 capture = tdm_output_create_capture(outputs[output_idx], &ret);
252 TDM_UT_RETURN_FALSE_IF_FAIL(ret == TDM_ERROR_NONE);
253 TDM_UT_RETURN_FALSE_IF_FAIL(capture != NULL);
256 tdm_layer_capability capabilities;
257 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_layer_get_capabilities(dst_layer, &capabilities) == TDM_ERROR_NONE);
258 if (capabilities & TDM_LAYER_CAPABILITY_SCANOUT)
259 flags |= TBM_BO_SCANOUT;
262 TDM_UT_RETURN_FALSE_IF_FAIL(tc_tdm_buffer_create(w, h, fmt, flags, false, 3, buffers) == true);
263 TDM_UT_RETURN_FALSE_IF_FAIL(tc_tdm_capture_fill_info(outputs[output_idx], buffers[0], t, c, frequency, stretch, &info) == true);
264 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_capture_set_info(capture, &info) == TDM_ERROR_NONE);
266 output = outputs[output_idx];
271 void TDMBackendCapture::TestDone(void)
274 tdm_capture_destroy(capture);
281 void TDMBackendCapture::DumpBuffer(int b, char *test)
285 snprintf(filename, sizeof filename, "%s_%s_%d", typeid(*this).name(), test, b);
287 snprintf(filename, sizeof filename, "%s_%d", typeid(*this).name(), b);
288 tdm_helper_dump_buffer_str(buffers[b], NULL, filename);
291 void TDMBackendCapture::ShowBuffer(int b, tdm_pos *pos)
293 ASSERT_NE(output, NULL);
294 ASSERT_NE(dst_layer, NULL);
296 ASSERT_EQ(tc_tdm_layer_set_buffer_with_pos(dst_layer, buffers[b], pos), true);
297 ASSERT_EQ(tdm_output_commit(output, 0, NULL, NULL), TDM_ERROR_NONE);
300 void TDMBackendCapture::HideLayer(void)
302 ASSERT_NE(output, NULL);
303 ASSERT_NE(dst_layer, NULL);
305 tdm_layer_unset_buffer(dst_layer);
306 tdm_output_commit(output, 0, NULL, NULL);
311 void TDMBackendCapture::DestroyBuffers(void)
313 for (int b = 0; b < 3; b++) {
314 tbm_surface_destroy(buffers[b]);
320 _tc_tdm_capture_fit_rect(int src_w, int src_h, int dst_w, int dst_h, tdm_pos *fit)
324 if (src_w <= 0 || src_h <= 0 || dst_w <= 0 || dst_h <= 0 || !fit)
327 rw = (float)src_w / dst_w;
328 rh = (float)src_h / dst_h;
334 fit->y = (dst_h - fit->h) / 2;
335 } else if (rw < rh) {
338 fit->x = (dst_w - fit->w) / 2;
352 tc_tdm_capture_fill_info(tdm_output *output, tbm_surface_h buffer, tdm_transform transform,
353 tdm_capture_type type, int frequency, bool stretch, tdm_info_capture *info)
356 const tdm_output_mode *mode = NULL;
358 TDM_UT_RETURN_FALSE_IF_FAIL(tdm_output_get_mode(output, &mode) == TDM_ERROR_NONE);
359 TDM_UT_RETURN_FALSE_IF_FAIL(mode != NULL);
361 memset(info, 0, sizeof *info);
363 bw = bh = TDM_UT_INVALID_VALUE;
364 tdm_helper_get_buffer_full_size(buffer, &bw, &bh);
366 TDM_UT_RETURN_FALSE_IF_FAIL(bw != TDM_UT_INVALID_VALUE);
367 TDM_UT_RETURN_FALSE_IF_FAIL(bw >= tbm_surface_get_width(buffer));
368 TDM_UT_RETURN_FALSE_IF_FAIL(bh != TDM_UT_INVALID_VALUE);
369 TDM_UT_RETURN_FALSE_IF_FAIL(bh >= tbm_surface_get_height(buffer));
370 info->dst_config.size.h = bw;
371 info->dst_config.size.v = bh;
374 info->dst_config.pos.x = 0;
375 info->dst_config.pos.y = 0;
376 info->dst_config.pos.w = tbm_surface_get_width(buffer);
377 info->dst_config.pos.h = tbm_surface_get_height(buffer);
379 _tc_tdm_capture_fit_rect(mode->hdisplay, mode->vdisplay,
380 tbm_surface_get_width(buffer), tbm_surface_get_height(buffer),
381 &info->dst_config.pos);
384 info->dst_config.format = tbm_surface_get_format(buffer);
386 info->transform = transform;
391 frequency = mode->vrefresh;
393 info->frequency = frequency;
395 TDM_UT_INFO("filling capture info done: dst_config(%dx%d: %d,%d %dx%d: %c%c%c%c) transform(%s) type(%s) freq(%d)",
396 info->dst_config.size.h, info->dst_config.size.v,
397 info->dst_config.pos.x, info->dst_config.pos.y, info->dst_config.pos.w, info->dst_config.pos.h,
398 FOURCC_STR(info->dst_config.format),
399 tdm_transform_str(info->transform), tdm_capture_type_str(info->type), info->frequency);
404 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableFormats)
406 const tbm_format *formats = (const tbm_format *)TDM_UT_INVALID_VALUE;
407 int count = TDM_UT_INVALID_VALUE;
408 if (has_capture_cap) {
409 ASSERT_EQ(tdm_display_get_capture_available_formats(dpy, &formats, &count), TDM_ERROR_NONE);
410 ASSERT_TRUE(formats != NULL && formats != (const tbm_format *)TDM_UT_INVALID_VALUE);
411 ASSERT_TRUE(count > 0 && count != TDM_UT_INVALID_VALUE);
413 ASSERT_EQ(tdm_display_get_capture_available_formats(dpy, &formats, &count), TDM_ERROR_NO_CAPABILITY);
414 ASSERT_EQ(formats, (const tbm_format *)TDM_UT_INVALID_VALUE);
415 ASSERT_EQ(count, TDM_UT_INVALID_VALUE);
419 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableFormatsNullObject)
421 const tbm_format *formats = (const tbm_format *)TDM_UT_INVALID_VALUE;
422 int count = TDM_UT_INVALID_VALUE;
423 ASSERT_EQ(tdm_display_get_capture_available_formats(NULL, &formats, &count), TDM_ERROR_INVALID_PARAMETER);
424 ASSERT_EQ(formats, (const tbm_format *)TDM_UT_INVALID_VALUE);
425 ASSERT_EQ(count, TDM_UT_INVALID_VALUE);
428 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableFormatsNullOther)
430 ASSERT_EQ(tdm_display_get_capture_available_formats(dpy, NULL, NULL), TDM_ERROR_INVALID_PARAMETER);
433 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableSize)
435 int min_w = TDM_UT_INVALID_VALUE;
436 int min_h = TDM_UT_INVALID_VALUE;
437 int max_w = TDM_UT_INVALID_VALUE;
438 int max_h = TDM_UT_INVALID_VALUE;
439 int preferred_align = TDM_UT_INVALID_VALUE;
440 if (has_capture_cap) {
441 ASSERT_EQ(tdm_display_get_capture_available_size(dpy, &min_w, &min_h, &max_w, &max_h, &preferred_align), TDM_ERROR_NONE);
442 ASSERT_NE(min_w, TDM_UT_INVALID_VALUE);
443 ASSERT_NE(min_h, TDM_UT_INVALID_VALUE);
444 ASSERT_NE(max_w, TDM_UT_INVALID_VALUE);
445 ASSERT_NE(max_h, TDM_UT_INVALID_VALUE);
446 ASSERT_NE(preferred_align, TDM_UT_INVALID_VALUE);
448 ASSERT_EQ(tdm_display_get_capture_available_size(dpy, &min_w, &min_h, &max_w, &max_h, &preferred_align), TDM_ERROR_NO_CAPABILITY);
449 ASSERT_EQ(min_w, TDM_UT_INVALID_VALUE);
450 ASSERT_EQ(min_h, TDM_UT_INVALID_VALUE);
451 ASSERT_EQ(max_w, TDM_UT_INVALID_VALUE);
452 ASSERT_EQ(max_h, TDM_UT_INVALID_VALUE);
453 ASSERT_EQ(preferred_align, TDM_UT_INVALID_VALUE);
457 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableSizeNullObject)
459 int min_w = TDM_UT_INVALID_VALUE;
460 int min_h = TDM_UT_INVALID_VALUE;
461 int max_w = TDM_UT_INVALID_VALUE;
462 int max_h = TDM_UT_INVALID_VALUE;
463 int preferred_align = TDM_UT_INVALID_VALUE;
464 ASSERT_EQ(tdm_display_get_capture_available_size(NULL, &min_w, &min_h, &max_w, &max_h, &preferred_align), TDM_ERROR_INVALID_PARAMETER);
465 ASSERT_EQ(min_w, TDM_UT_INVALID_VALUE);
466 ASSERT_EQ(min_h, TDM_UT_INVALID_VALUE);
467 ASSERT_EQ(max_w, TDM_UT_INVALID_VALUE);
468 ASSERT_EQ(max_h, TDM_UT_INVALID_VALUE);
469 ASSERT_EQ(preferred_align, TDM_UT_INVALID_VALUE);
472 TEST_P(TDMBackendCapture, CaptureDispalyGetAvaiableSizeNullOther)
475 ASSERT_EQ(tdm_display_get_capture_available_size(dpy, NULL, NULL, NULL, NULL, NULL), TDM_ERROR_NONE);
477 ASSERT_EQ(tdm_display_get_capture_available_size(dpy, NULL, NULL, NULL, NULL, NULL), TDM_ERROR_NO_CAPABILITY);
480 TEST_P(TDMBackendCapture, CaptureDestroy)
482 TDM_UT_SKIP_FLAG(has_capture_cap);
483 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
485 ASSERT_EQ(TestPrepareDefault(), true);
490 TEST_P(TDMBackendCapture, CaptureDestroyNullObject)
492 TDM_UT_SKIP_FLAG(has_capture_cap);
493 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
495 tdm_capture_destroy(NULL);
498 TEST_P(TDMBackendCapture, CaptureSetInfo)
500 /* tested in CaptureNoScaleNoTransformNoCSC */
503 TEST_P(TDMBackendCapture, CaptureSetInfoNullObject)
505 TDM_UT_SKIP_FLAG(has_capture_cap);
506 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
508 tdm_info_capture info;
509 memset(&info, 0, sizeof info);
510 ASSERT_EQ(tdm_capture_set_info(NULL, &info), TDM_ERROR_INVALID_PARAMETER);
513 TEST_P(TDMBackendCapture, CaptureSetInfoNullOther)
515 TDM_UT_SKIP_FLAG(has_capture_cap);
516 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
518 ASSERT_EQ(TestPrepareDefault(), true);
520 ASSERT_EQ(tdm_capture_set_info(capture, NULL), TDM_ERROR_INVALID_PARAMETER);
526 _tc_tdm_capture_done_cb(tdm_capture *capture, tbm_surface_h buffer, void *user_data)
528 bool *done = (bool*)user_data;
533 TEST_P(TDMBackendCapture, CaptureSetDoneHandler)
535 TDM_UT_SKIP_FLAG(has_capture_cap);
536 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
538 ASSERT_EQ(TestPrepareDefault(), true);
540 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb, NULL), TDM_ERROR_NONE);
545 TEST_P(TDMBackendCapture, CaptureSetDoneHandlerNullObject)
547 TDM_UT_SKIP_FLAG(has_capture_cap);
548 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
550 ASSERT_EQ(tdm_capture_set_done_handler(NULL, _tc_tdm_capture_done_cb, NULL), TDM_ERROR_INVALID_PARAMETER);
553 TEST_P(TDMBackendCapture, CaptureSetDoneHandlerNullOther)
555 TDM_UT_SKIP_FLAG(has_capture_cap);
556 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
558 ASSERT_EQ(TestPrepareDefault(), true);
560 ASSERT_EQ(tdm_capture_set_done_handler(capture, NULL, NULL), TDM_ERROR_INVALID_PARAMETER);
565 TEST_P(TDMBackendCapture, CaptureAttach)
567 TDM_UT_SKIP_FLAG(has_capture_cap);
568 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
570 for (int o = 0; o < output_count; o++) {
572 if (!tc_tdm_output_is_connected(outputs[o]))
575 for (int f = 0; f < format_count; f++) {
576 FindLayer(o, formats[f], &dst_pos);
578 ASSERT_EQ(TestPrepare(o, TDM_UT_BUFFER_SIZE, TDM_UT_BUFFER_SIZE, formats[f],
579 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false), true);
581 for (int b = 0; b < 3; b++)
582 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
589 TEST_P(TDMBackendCapture, CaptureAttachNullObject)
591 TDM_UT_SKIP_FLAG(has_capture_cap);
592 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
594 tbm_surface_h buffer = (tbm_surface_h)TDM_UT_BUFFER_SIZE;
596 ASSERT_EQ(tdm_capture_attach(NULL, buffer), TDM_ERROR_INVALID_PARAMETER);
599 TEST_P(TDMBackendCapture, CaptureAttachNullOther)
601 TDM_UT_SKIP_FLAG(has_capture_cap);
602 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
604 ASSERT_EQ(TestPrepareDefault(), true);
606 ASSERT_EQ(tdm_capture_attach(capture, NULL), TDM_ERROR_INVALID_PARAMETER);
611 TEST_P(TDMBackendCapture, CaptureCommit)
613 TDM_UT_SKIP_FLAG(has_capture_cap);
614 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
616 ASSERT_EQ(TestPrepareDefault(), true);
618 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
623 TEST_P(TDMBackendCapture, CaptureCommitNullOBject)
625 TDM_UT_SKIP_FLAG(has_capture_cap);
626 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
628 ASSERT_EQ(tdm_capture_commit(NULL), TDM_ERROR_INVALID_PARAMETER);
631 TEST_P(TDMBackendCapture, CaptureCommitDpmsOff)
633 TDM_UT_SKIP_FLAG(has_capture_cap);
634 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
636 ASSERT_EQ(TestPrepareDefault(), true);
638 ASSERT_EQ(tc_tdm_output_unset(dpy, output), true);
640 ASSERT_EQ(tdm_output_set_dpms(output, TDM_OUTPUT_DPMS_OFF), TDM_ERROR_NONE);
642 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_BAD_REQUEST);
648 _tc_tdm_capture_done_cb2(tdm_capture *capture, tbm_surface_h buffer, void *user_data)
650 int *done = (int*)user_data;
655 TEST_P(TDMBackendCapture, CaptureDestroyWithoutCommit)
657 TDM_UT_SKIP_FLAG(has_capture_cap);
658 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
660 for (int o = 0; o < output_count; o++) {
661 const tdm_output_mode *mode = NULL;
664 if (!tc_tdm_output_is_connected(outputs[o]))
667 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
669 FindLayer(o, formats[f], &dst_pos);
671 ASSERT_EQ(TestPrepare(o, TDM_UT_BUFFER_SIZE, TDM_UT_BUFFER_SIZE, formats[f],
672 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false), true);
674 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb2, NULL), TDM_ERROR_NONE);
676 for (int b = 0; b < 3; b++)
677 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
679 tdm_capture_destroy(capture);
686 TEST_P(TDMBackendCapture, CaptureDestroyBeforeDone)
688 TDM_UT_SKIP_FLAG(has_capture_cap);
689 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
691 for (int o = 0; o < output_count; o++) {
692 const tdm_output_mode *mode = NULL;
695 if (!tc_tdm_output_is_connected(outputs[o]))
698 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
700 FindLayer(o, formats[f], &dst_pos);
702 ASSERT_EQ(TestPrepare(o, TDM_UT_BUFFER_SIZE, TDM_UT_BUFFER_SIZE, formats[f],
703 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false), true);
705 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb2, NULL), TDM_ERROR_NONE);
707 for (int b = 0; b < 3; b++)
708 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
710 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
712 tdm_capture_destroy(capture);
719 TEST_P(TDMBackendCapture, CaptureOneshotLetterboxSize)
721 TDM_UT_SKIP_FLAG(has_capture_cap);
722 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
723 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_ONESHOT);
727 for (int o = 0; o < output_count; o++) {
728 const tdm_output_mode *mode = NULL;
730 if (!tc_tdm_output_is_connected(outputs[o]))
733 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
735 for (int f = 0; f < format_count; f++) {
736 int half_size = ((mode->hdisplay <= mode->vdisplay) ? mode->hdisplay : mode->vdisplay) / 2;
738 dst_pos.x = (mode->hdisplay - half_size) / 2;
739 dst_pos.y = (mode->vdisplay - half_size) / 2;
740 dst_pos.w = half_size;
741 dst_pos.h = half_size;
743 TDM_UT_INFO("* testing for %c%c%c%c", FOURCC_STR(formats[f]));
745 FindLayer(o, formats[f], &dst_pos);
748 TDM_UT_INFO("no proper layer for %c%c%c%c", FOURCC_STR(formats[f]));
752 ASSERT_EQ(TestPrepare(o, half_size, half_size, formats[f],
753 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false), true);
755 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb, &done), TDM_ERROR_NONE);
758 for (int b = 0; b < 3; b++) {
760 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
761 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
764 ASSERT_EQ(tc_tdm_display_handle_events(dpy), TDM_ERROR_NONE);
768 snprintf(temp, sizeof temp, "f%d_b%d", f, b);
771 ShowBuffer(b, &dst_pos);
774 TDM_UT_ASK_YNR("* Successed to capture a output to a '%c%c%c%c' buffer as letterbox size and show? (output: %d, layer: %d)",
775 FOURCC_STR(formats[f]), pipe, dst_layer_index);
785 TEST_P(TDMBackendCapture, CaptureOneshotFullSize)
787 TDM_UT_SKIP_FLAG(has_capture_cap);
788 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
789 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_ONESHOT);
793 for (int o = 0; o < output_count; o++) {
794 const tdm_output_mode *mode = NULL;
796 if (!tc_tdm_output_is_connected(outputs[o]))
799 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
801 for (int f = 0; f < format_count; f++) {
802 int half_size = ((mode->hdisplay <= mode->vdisplay) ? mode->hdisplay : mode->vdisplay) / 2;
804 dst_pos.x = (mode->hdisplay - half_size) / 2;
805 dst_pos.y = (mode->vdisplay - half_size) / 2;
806 dst_pos.w = half_size;
807 dst_pos.h = half_size;
809 TDM_UT_INFO("* testing for %c%c%c%c", FOURCC_STR(formats[f]));
811 FindLayer(o, formats[f], &dst_pos);
814 TDM_UT_INFO("no proper layer for %c%c%c%c", FOURCC_STR(formats[f]));
818 ASSERT_EQ(TestPrepare(o, half_size, half_size, formats[f],
819 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, true), true);
821 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb, &done), TDM_ERROR_NONE);
824 for (int b = 0; b < 3; b++) {
826 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
827 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
830 ASSERT_EQ(tc_tdm_display_handle_events(dpy), TDM_ERROR_NONE);
834 snprintf(temp, sizeof temp, "f%d_b%d", f, b);
837 ShowBuffer(b, &dst_pos);
840 TDM_UT_ASK_YNR("* Successed to capture a output to a '%c%c%c%c' buffer as full size and show? (output: %d, layer: %d)",
841 FOURCC_STR(formats[f]), pipe, dst_layer_index);
851 TEST_P(TDMBackendCapture, CaptureOneshotAttachFewTimesInOneCommit)
853 TDM_UT_SKIP_FLAG(has_capture_cap);
854 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
855 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_ONESHOT);
859 for (int o = 0; o < output_count; o++) {
860 const tdm_output_mode *mode = NULL;
862 if (!tc_tdm_output_is_connected(outputs[o]))
865 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
867 for (int f = 0; f < format_count; f++) {
868 int half_size = ((mode->hdisplay <= mode->vdisplay) ? mode->hdisplay : mode->vdisplay) / 2;
870 dst_pos.x = (mode->hdisplay - half_size) / 2;
871 dst_pos.y = (mode->vdisplay - half_size) / 2;
872 dst_pos.w = half_size;
873 dst_pos.h = half_size;
875 TDM_UT_INFO("* testing for %c%c%c%c", FOURCC_STR(formats[f]));
877 FindLayer(o, formats[f], &dst_pos);
880 TDM_UT_INFO("no proper layer for %c%c%c%c", FOURCC_STR(formats[f]));
884 ASSERT_EQ(TestPrepare(o, half_size, half_size, formats[f],
885 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_ONESHOT, -1, false), true);
888 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_done_cb2, &done), TDM_ERROR_NONE);
891 for (int b = 0; b < 3; b++)
892 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
894 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
897 ASSERT_EQ(tc_tdm_display_handle_events(dpy), TDM_ERROR_NONE);
899 for (int b = 0; b < 3; b++) {
902 snprintf(temp, sizeof temp, "f%d_b%d", f, b);
905 ShowBuffer(b, &dst_pos);
908 TDM_UT_ASK_YNR("* Successed to capture a output to a '%c%c%c%c' buffer as letterbox size and show? (output: %d, layer: %d)",
909 FOURCC_STR(formats[f]), pipe, dst_layer_index);
920 _tc_tdm_backend_capture_buffer_release_cb(tbm_surface_h buffer, void *user_data)
922 TDMBackendCapture *backend_capture = (TDMBackendCapture*)user_data;
924 tdm_buffer_remove_release_handler(buffer, _tc_tdm_backend_capture_buffer_release_cb, backend_capture);
926 ASSERT_EQ(tdm_capture_attach(backend_capture->capture, buffer), TDM_ERROR_NONE);
927 ASSERT_EQ(tdm_capture_commit(backend_capture->capture), TDM_ERROR_NONE);
931 _tc_tdm_capture_stream_done_cb(tdm_capture *capture, tbm_surface_h buffer, void *user_data)
933 TDMBackendCapture *backend_capture = (TDMBackendCapture*)user_data;
935 for (int b = 0; b < 3; b++) {
936 if (backend_capture->buffers[b] == buffer) {
939 snprintf(temp, sizeof temp, "f%d_b%d", f, b);
942 tdm_buffer_add_release_handler(buffer, _tc_tdm_backend_capture_buffer_release_cb, (void*)backend_capture);
943 backend_capture->ShowBuffer(b, &backend_capture->dst_pos);
948 if (--backend_capture->stream_count == 0) {
949 backend_capture->stream_exit = 1;
953 TEST_P(TDMBackendCapture, CaptureStreamLetterboxSize)
955 TDM_UT_SKIP_FLAG(has_capture_cap);
956 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
957 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_STREAM);
959 for (int o = 0; o < output_count; o++) {
960 const tdm_output_mode *mode = NULL;
962 if (!tc_tdm_output_is_connected(outputs[o]))
965 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
967 for (int f = 0; f < format_count; f++) {
968 int half_size = ((mode->hdisplay <= mode->vdisplay) ? mode->hdisplay : mode->vdisplay) / 2;
970 dst_pos.x = (mode->hdisplay - half_size) / 2;
971 dst_pos.y = (mode->vdisplay - half_size) / 2;
972 dst_pos.w = half_size;
973 dst_pos.h = half_size;
975 TDM_UT_INFO("* testing for %c%c%c%c", FOURCC_STR(formats[f]));
977 FindLayer(o, formats[f], &dst_pos);
980 TDM_UT_INFO("no proper layer for %c%c%c%c", FOURCC_STR(formats[f]));
984 ASSERT_EQ(TestPrepare(o, half_size, half_size, formats[f],
985 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_STREAM, -1, false), true);
987 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_stream_done_cb, (void*)this), TDM_ERROR_NONE);
989 for (int b = 0; b < 3; b++)
990 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
997 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
1000 ASSERT_EQ(tc_tdm_display_handle_events(dpy), TDM_ERROR_NONE);
1002 TDM_UT_ASK_YNR("* Successed to capture a output to a '%c%c%c%c' buffer as letterbox size and show? (output: %d, layer: %d)",
1003 FOURCC_STR(formats[f]), pipe, dst_layer_index);
1013 TEST_P(TDMBackendCapture, CaptureStreamFullSize)
1015 TDM_UT_SKIP_FLAG(has_capture_cap);
1016 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_OUTPUT);
1017 TDM_UT_SKIP_FLAG(capabilities & TDM_CAPTURE_CAPABILITY_STREAM);
1019 for (int o = 0; o < output_count; o++) {
1020 const tdm_output_mode *mode = NULL;
1022 if (!tc_tdm_output_is_connected(outputs[o]))
1025 ASSERT_EQ(tdm_output_get_mode(outputs[o], &mode), TDM_ERROR_NONE);
1027 for (int f = 0; f < format_count; f++) {
1028 int half_size = ((mode->hdisplay <= mode->vdisplay) ? mode->hdisplay : mode->vdisplay) / 2;
1030 dst_pos.x = (mode->hdisplay - half_size) / 2;
1031 dst_pos.y = (mode->vdisplay - half_size) / 2;
1032 dst_pos.w = half_size;
1033 dst_pos.h = half_size;
1035 TDM_UT_INFO("* testing for %c%c%c%c", FOURCC_STR(formats[f]));
1037 FindLayer(o, formats[f], &dst_pos);
1040 TDM_UT_INFO("no proper layer for %c%c%c%c", FOURCC_STR(formats[f]));
1044 ASSERT_EQ(TestPrepare(o, half_size, half_size, formats[f],
1045 TDM_TRANSFORM_NORMAL, TDM_CAPTURE_TYPE_STREAM, -1, true), true);
1047 ASSERT_EQ(tdm_capture_set_done_handler(capture, _tc_tdm_capture_stream_done_cb, (void*)this), TDM_ERROR_NONE);
1049 for (int b = 0; b < 3; b++)
1050 ASSERT_EQ(tdm_capture_attach(capture, buffers[b]), TDM_ERROR_NONE);
1054 stream_exit = false;
1057 ASSERT_EQ(tdm_capture_commit(capture), TDM_ERROR_NONE);
1059 while (!stream_exit)
1060 ASSERT_EQ(tc_tdm_display_handle_events(dpy), TDM_ERROR_NONE);
1062 TDM_UT_ASK_YNR("* Successed to capture a output to a '%c%c%c%c' buffer as full size and show? (output: %d, layer: %d)",
1063 FOURCC_STR(formats[f]), pipe, dst_layer_index);
1073 #ifdef TDM_UT_TEST_WITH_PARAMS
1074 INSTANTIATE_TEST_CASE_P(TDMBackendCaptureParams,
1076 Combine(Bool(), Bool(), Values(TDM_DEFAULT_MODULE)));
1078 INSTANTIATE_TEST_CASE_P(TDMBackendCaptureParams,
1080 Values(TDM_DEFAULT_MODULE));