X-Git-Url: https://git.ti.com/gitweb?p=android%2Fexternal-libkmsxx.git;a=blobdiff_plain;f=utils%2Ftestpat.cpp;h=6aa658345e6cea14855350cf33fb20e2d870842f;hp=0dc7c1735a7de2ba93e4e36fe8ceb8f8984ebe28;hb=0b3c14f8db44bfa7f7bfa5e1655c5b15d2104f91;hpb=b35fc6442d02d8a405bf71864b18de16a1184647 diff --git a/utils/testpat.cpp b/utils/testpat.cpp index 0dc7c17..6aa6583 100644 --- a/utils/testpat.cpp +++ b/utils/testpat.cpp @@ -22,7 +22,7 @@ struct PlaneInfo unsigned w; unsigned h; - DumbFramebuffer* fb; + vector fbs; }; struct OutputInfo @@ -30,15 +30,17 @@ struct OutputInfo Connector* connector; Crtc* crtc; + Plane* primary_plane; Videomode mode; bool user_set_crtc; - DumbFramebuffer* fb; + vector fbs; vector planes; }; static bool s_use_dmt; static bool s_use_cea; +static unsigned s_num_buffers = 1; static set s_used_crtcs; static set s_used_planes; @@ -243,12 +245,17 @@ static void parse_plane(Card& card, const string& plane_str, const OutputInfo& o pinfo.y = output.mode.vdisplay / 2 - pinfo.h / 2; } -static DumbFramebuffer* get_default_fb(Card& card, unsigned width, unsigned height) +static vector get_default_fb(Card& card, unsigned width, unsigned height) { - return new DumbFramebuffer(card, width, height, PixelFormat::XRGB8888); + vector v; + + for (unsigned i = 0; i < s_num_buffers; ++i) + v.push_back(new DumbFramebuffer(card, width, height, PixelFormat::XRGB8888)); + + return v; } -static DumbFramebuffer* parse_fb(Card& card, const string& fb_str, unsigned def_w, unsigned def_h) +static vector parse_fb(Card& card, const string& fb_str, unsigned def_w, unsigned def_h) { unsigned w = def_w; unsigned h = def_h; @@ -271,7 +278,12 @@ static DumbFramebuffer* parse_fb(Card& card, const string& fb_str, unsigned def_ format = FourCCToPixelFormat(sm[3]); } - return new DumbFramebuffer(card, w, h, format); + vector v; + + for (unsigned i = 0; i < s_num_buffers; ++i) + v.push_back(new DumbFramebuffer(card, w, h, format)); + + return v; } static const char* usage_str = @@ -391,7 +403,7 @@ static vector setups_to_outputs(Card& card, const vector& outpu output.crtc = pipe.crtc; output.mode = output.connector->get_default_mode(); - output.fb = get_default_fb(card, output.mode.hdisplay, output.mode.vdisplay); + output.fbs = get_default_fb(card, output.mode.hdisplay, output.mode.vdisplay); outputs.push_back(output); } @@ -478,12 +490,12 @@ static vector setups_to_outputs(Card& card, const vector& outpu def_h = current_output->mode.vdisplay; } - auto fb = parse_fb(card, arg.arg, def_w, def_h); + auto fbs = parse_fb(card, arg.arg, def_w, def_h); if (current_plane) - current_plane->fb = fb; + current_plane->fbs = fbs; else - current_output->fb = fb; + current_output->fbs = fbs; break; } @@ -497,12 +509,12 @@ static vector setups_to_outputs(Card& card, const vector& outpu o.user_set_crtc = true; } - if (!o.fb && o.user_set_crtc) - o.fb = get_default_fb(card, o.mode.hdisplay, o.mode.vdisplay); + if (o.fbs.empty() && o.user_set_crtc) + o.fbs = get_default_fb(card, o.mode.hdisplay, o.mode.vdisplay); for (PlaneInfo &p : o.planes) { - if (!p.fb) - p.fb = get_default_fb(card, p.w, p.h); + if (p.fbs.empty()) + p.fbs = get_default_fb(card, p.w, p.h); } } @@ -541,19 +553,25 @@ static void print_outputs(const vector& outputs) printf("Connector %u/@%u: %s\n", o.connector->id(), o.connector->idx(), o.connector->fullname().c_str()); - printf(" Crtc %u/@%u: %ux%u-%u (%s)\n", o.crtc->id(), o.crtc->idx(), + printf(" Crtc %u/@%u", o.crtc->id(), o.crtc->idx()); + if (o.primary_plane) + printf(" (plane %u/@%u)", o.primary_plane->id(), o.primary_plane->idx()); + printf(": %ux%u-%u (%s)\n", o.mode.hdisplay, o.mode.vdisplay, o.mode.vrefresh, videomode_to_string(o.mode).c_str()); - if (o.fb) - printf(" Fb %ux%u-%s\n", o.fb->width(), o.fb->height(), - PixelFormatToFourCC(o.fb->format()).c_str()); + if (!o.fbs.empty()) { + auto fb = o.fbs[0]; + printf(" Fb %ux%u-%s\n", fb->width(), fb->height(), + PixelFormatToFourCC(fb->format()).c_str()); + } for (unsigned j = 0; j < o.planes.size(); ++j) { const PlaneInfo& p = o.planes[j]; + auto fb = p.fbs[0]; printf(" Plane %u/@%u: %u,%u-%ux%u\n", p.plane->id(), p.plane->idx(), p.x, p.y, p.w, p.h); - printf(" Fb %ux%u-%s\n", p.fb->width(), p.fb->height(), - PixelFormatToFourCC(p.fb->format()).c_str()); + printf(" Fb %ux%u-%s\n", fb->width(), fb->height(), + PixelFormatToFourCC(fb->format()).c_str()); } } } @@ -561,31 +579,34 @@ static void print_outputs(const vector& outputs) static void draw_test_patterns(const vector& outputs) { for (const OutputInfo& o : outputs) { - if (o.fb) - draw_test_pattern(*o.fb); + for (auto fb : o.fbs) + draw_test_pattern(*fb); for (const PlaneInfo& p : o.planes) - draw_test_pattern(*p.fb); + for (auto fb : p.fbs) + draw_test_pattern(*fb); } } -static void set_crtcs_n_planes(Card& card, const vector& outputs) +static void set_crtcs_n_planes_legacy(Card& card, const vector& outputs) { for (const OutputInfo& o : outputs) { auto conn = o.connector; auto crtc = o.crtc; - if (o.fb) { - int r = crtc->set_mode(conn, *o.fb, o.mode); + if (!o.fbs.empty()) { + auto fb = o.fbs[0]; + int r = crtc->set_mode(conn, *fb, o.mode); if (r) printf("crtc->set_mode() failed for crtc %u: %s\n", crtc->id(), strerror(-r)); } for (const PlaneInfo& p : o.planes) { - int r = crtc->set_plane(p.plane, *p.fb, + auto fb = p.fbs[0]; + int r = crtc->set_plane(p.plane, *fb, p.x, p.y, p.w, p.h, - 0, 0, p.fb->width(), p.fb->height()); + 0, 0, fb->width(), fb->height()); if (r) printf("crtc->set_plane() failed for plane %u: %s\n", p.plane->id(), strerror(-r)); @@ -593,6 +614,75 @@ static void set_crtcs_n_planes(Card& card, const vector& outputs) } } +static void set_crtcs_n_planes(Card& card, const vector& outputs) +{ + // Keep blobs here so that we keep ref to them until we have committed the req + vector> blobs; + + AtomicReq req(card); + + for (const OutputInfo& o : outputs) { + auto conn = o.connector; + auto crtc = o.crtc; + + if (!o.fbs.empty()) { + auto fb = o.fbs[0]; + + blobs.emplace_back(o.mode.to_blob(card)); + Blob* mode_blob = blobs.back().get(); + + req.add(conn, { + { "CRTC_ID", crtc->id() }, + }); + + req.add(crtc, { + { "ACTIVE", 1 }, + { "MODE_ID", mode_blob->id() }, + }); + + req.add(o.primary_plane, { + { "FB_ID", fb->id() }, + { "CRTC_ID", crtc->id() }, + { "SRC_X", 0 << 16 }, + { "SRC_Y", 0 << 16 }, + { "SRC_W", fb->width() << 16 }, + { "SRC_H", fb->height() << 16 }, + { "CRTC_X", 0 }, + { "CRTC_Y", 0 }, + { "CRTC_W", fb->width() }, + { "CRTC_H", fb->height() }, + }); + } + + for (const PlaneInfo& p : o.planes) { + auto fb = p.fbs[0]; + + req.add(p.plane, { + { "FB_ID", fb->id() }, + { "CRTC_ID", crtc->id() }, + { "SRC_X", 0 << 16 }, + { "SRC_Y", 0 << 16 }, + { "SRC_W", fb->width() << 16 }, + { "SRC_H", fb->height() << 16 }, + { "CRTC_X", p.x }, + { "CRTC_Y", p.y }, + { "CRTC_W", p.w }, + { "CRTC_H", p.h }, + }); + } + } + + int r; + + r = req.test(true); + if (r) + EXIT("Atomic test failed: %d\n", r); + + r = req.commit_sync(true); + if (r) + EXIT("Atomic commit failed: %d\n", r); +} + int main(int argc, char **argv) { vector output_args = parse_cmdline(argc, argv); @@ -601,11 +691,23 @@ int main(int argc, char **argv) vector outputs = setups_to_outputs(card, output_args); + if (card.has_atomic()) { + for (OutputInfo& o : outputs) { + o.primary_plane = o.crtc->get_primary_plane(); + + if (!o.fbs.empty() && !o.primary_plane) + EXIT("Could not get primary plane for crtc '%u'", o.crtc->id()); + } + } + draw_test_patterns(outputs); print_outputs(outputs); - set_crtcs_n_planes(card, outputs); + if (card.has_atomic()) + set_crtcs_n_planes(card, outputs); + else + set_crtcs_n_planes_legacy(card, outputs); printf("press enter to exit\n");