From patchwork Wed Jun 27 16:45:14 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Jernej_=C5=A0krabec?= X-Patchwork-Id: 10492213 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 1B62060325 for ; Wed, 27 Jun 2018 16:47:53 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 40F6D296E7 for ; Wed, 27 Jun 2018 16:47:53 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 3ED0D29546; Wed, 27 Jun 2018 16:47:53 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.9 required=2.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,MAILING_LIST_MULTI autolearn=unavailable version=3.3.1 Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 447AC296FB for ; Wed, 27 Jun 2018 16:47:52 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20170209; h=Sender: Content-Transfer-Encoding:Content-Type:MIME-Version:Cc:List-Subscribe: List-Help:List-Post:List-Archive:List-Unsubscribe:List-Id:Message-Id:Date: Subject:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:In-Reply-To: References:List-Owner; bh=0djl+nvXAV22ZI1xU7Bu3RwJL9lE3MaMc2d4F4Ttgh8=; b=fd6 OrVaUF44KHFUP0Q70L3WOjf4VtNSHnYmkru2bPL8tmQMbmciIoZ9B0tFkb8xxso7A5YBa22k077sv uG2l7+ueCRhNhh0m1kki3nocQwl76F2Fmn45UNZpjLManNg3ooEFnqBW8hE23iIbAIg7pQ4q4TqOM g0TWUiIeIdbfkPzP2uW04X6ozfBRl6Bz5fmiHci79tjlOltbRR/irOxlcbuIWjnIS+Lw1xUosO3HB 5CxMIuxPquED77PtBaDYyd0Doz0Nib9OPz56HN0NIEa0x7EZw0quHq24ARi7Zm/ABdJS0CjVXkZbz 3J7yE4O8IIO6A4xVvhwFBgFW6D2f99g==; Received: from localhost ([127.0.0.1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.90_1 #2 (Red Hat Linux)) id 1fYDbc-00027K-1W; Wed, 27 Jun 2018 16:47:44 +0000 Received: from mailoutvs56.siol.net ([185.57.226.247] helo=mail.siol.net) by bombadil.infradead.org with esmtps (Exim 4.90_1 #2 (Red Hat Linux)) id 1fYDb5-0001nY-By for linux-arm-kernel@lists.infradead.org; Wed, 27 Jun 2018 16:47:21 +0000 Received: from localhost (localhost [127.0.0.1]) by mail.siol.net (Postfix) with ESMTP id 20514521FC5; Wed, 27 Jun 2018 18:46:49 +0200 (CEST) X-Virus-Scanned: amavisd-new at psrvmta10.zcs-production.pri Received: from mail.siol.net ([127.0.0.1]) by localhost (psrvmta10.zcs-production.pri [127.0.0.1]) (amavisd-new, port 10032) with ESMTP id isCmzl9S1SGf; Wed, 27 Jun 2018 18:46:48 +0200 (CEST) Received: from mail.siol.net (localhost [127.0.0.1]) by mail.siol.net (Postfix) with ESMTPS id F2B61521CEE; Wed, 27 Jun 2018 18:46:47 +0200 (CEST) Received: from localhost.localdomain (unknown [194.152.15.144]) (Authenticated sender: 031275009) by mail.siol.net (Postfix) with ESMTPSA id 2FCA4521E86; Wed, 27 Jun 2018 18:46:45 +0200 (CEST) From: Jernej Skrabec To: maxime.ripard@bootlin.com, wens@csie.org Subject: [PATCH] drm/sun4i: Implement zpos for DE2 Date: Wed, 27 Jun 2018 18:45:14 +0200 Message-Id: <20180627164514.4777-1-jernej.skrabec@siol.net> X-Mailer: git-send-email 2.18.0 X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20180627_094712_237207_EAE06D5D X-CRM114-Status: GOOD ( 15.14 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: paul.kocialkowski@bootlin.com, linux-sunxi@googlegroups.com, linux-arm-kernel@lists.infradead.org, dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org MIME-Version: 1.0 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+patchwork-linux-arm=patchwork.kernel.org@lists.infradead.org X-Virus-Scanned: ClamAV using ClamSMTP Initial implementation of DE2 planes only supported fixed zpos. Expand implementation with configurable zpos property. Signed-off-by: Jernej Skrabec Tested-by: Paul Kocialkowski --- drivers/gpu/drm/sun4i/sun8i_mixer.c | 15 +++++++-- drivers/gpu/drm/sun4i/sun8i_mixer.h | 4 +++ drivers/gpu/drm/sun4i/sun8i_ui_layer.c | 45 ++++++++++++++++---------- drivers/gpu/drm/sun4i/sun8i_vi_layer.c | 45 ++++++++++++++++---------- 4 files changed, 72 insertions(+), 37 deletions(-) diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.c b/drivers/gpu/drm/sun4i/sun8i_mixer.c index ee8febb25903..0747a9a69654 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.c +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.c @@ -260,6 +260,17 @@ const struct de2_fmt_info *sun8i_mixer_format_info(u32 format) return NULL; } +static void sun8i_mixer_atomic_begin(struct sunxi_engine *engine, + struct drm_crtc_state *old_state) +{ + /* + * Disable all pipes at the beginning. They will be enabled + * again if needed in plane update callback. + */ + regmap_update_bits(engine->regs, SUN8I_MIXER_BLEND_PIPE_CTL, + SUN8I_MIXER_BLEND_PIPE_CTL_EN_MSK, 0); +} + static void sun8i_mixer_commit(struct sunxi_engine *engine) { DRM_DEBUG_DRIVER("Committing changes\n"); @@ -311,6 +322,7 @@ static struct drm_plane **sun8i_layers_init(struct drm_device *drm, } static const struct sunxi_engine_ops sun8i_engine_ops = { + .atomic_begin = sun8i_mixer_atomic_begin, .commit = sun8i_mixer_commit, .layers_init = sun8i_layers_init, }; @@ -432,9 +444,6 @@ static int sun8i_mixer_bind(struct device *dev, struct device *master, regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_ATTR_FCOLOR(0), SUN8I_MIXER_BLEND_COLOR_BLACK); - /* Fixed zpos for now */ - regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_ROUTE, 0x43210); - plane_cnt = mixer->cfg->vi_num + mixer->cfg->ui_num; for (i = 0; i < plane_cnt; i++) regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_MODE(i), diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.h b/drivers/gpu/drm/sun4i/sun8i_mixer.h index f34e70c42adf..406c42e752d7 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.h +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.h @@ -44,6 +44,7 @@ #define SUN8I_MIXER_BLEND_CK_MIN(x) (0x10e0 + 0x04 * (x)) #define SUN8I_MIXER_BLEND_OUTCTL 0x10fc +#define SUN8I_MIXER_BLEND_PIPE_CTL_EN_MSK GENMASK(12, 8) #define SUN8I_MIXER_BLEND_PIPE_CTL_EN(pipe) BIT(8 + pipe) #define SUN8I_MIXER_BLEND_PIPE_CTL_FC_EN(pipe) BIT(pipe) /* colors are always in AARRGGBB format */ @@ -51,6 +52,9 @@ /* The following numbers are some still unknown magic numbers */ #define SUN8I_MIXER_BLEND_MODE_DEF 0x03010301 +#define SUN8I_MIXER_BLEND_ROUTE_PIPE_MSK(n) (0xf << ((n) << 2)) +#define SUN8I_MIXER_BLEND_ROUTE_PIPE_SHIFT(n) ((n) << 2) + #define SUN8I_MIXER_BLEND_OUTCTL_INTERLACED BIT(1) #define SUN8I_MIXER_FBFMT_ARGB8888 0 diff --git a/drivers/gpu/drm/sun4i/sun8i_ui_layer.c b/drivers/gpu/drm/sun4i/sun8i_ui_layer.c index 9a540330cb79..518e1921f47e 100644 --- a/drivers/gpu/drm/sun4i/sun8i_ui_layer.c +++ b/drivers/gpu/drm/sun4i/sun8i_ui_layer.c @@ -27,7 +27,7 @@ #include "sun8i_ui_scaler.h" static void sun8i_ui_layer_enable(struct sun8i_mixer *mixer, int channel, - int overlay, bool enable) + int overlay, bool enable, unsigned int zpos) { u32 val; @@ -43,18 +43,24 @@ static void sun8i_ui_layer_enable(struct sun8i_mixer *mixer, int channel, SUN8I_MIXER_CHAN_UI_LAYER_ATTR(channel, overlay), SUN8I_MIXER_CHAN_UI_LAYER_ATTR_EN, val); - if (enable) - val = SUN8I_MIXER_BLEND_PIPE_CTL_EN(channel); - else - val = 0; + if (enable) { + val = SUN8I_MIXER_BLEND_PIPE_CTL_EN(zpos); - regmap_update_bits(mixer->engine.regs, - SUN8I_MIXER_BLEND_PIPE_CTL, - SUN8I_MIXER_BLEND_PIPE_CTL_EN(channel), val); + regmap_update_bits(mixer->engine.regs, + SUN8I_MIXER_BLEND_PIPE_CTL, val, val); + + val = channel << SUN8I_MIXER_BLEND_ROUTE_PIPE_SHIFT(zpos); + + regmap_update_bits(mixer->engine.regs, + SUN8I_MIXER_BLEND_ROUTE, + SUN8I_MIXER_BLEND_ROUTE_PIPE_MSK(zpos), + val); + } } static int sun8i_ui_layer_update_coord(struct sun8i_mixer *mixer, int channel, - int overlay, struct drm_plane *plane) + int overlay, struct drm_plane *plane, + unsigned int zpos) { struct drm_plane_state *state = plane->state; u32 src_w, src_h, dst_w, dst_h; @@ -137,10 +143,10 @@ static int sun8i_ui_layer_update_coord(struct sun8i_mixer *mixer, int channel, state->dst.x1, state->dst.y1); DRM_DEBUG_DRIVER("Layer destination size W: %d H: %d\n", dst_w, dst_h); regmap_write(mixer->engine.regs, - SUN8I_MIXER_BLEND_ATTR_COORD(channel), + SUN8I_MIXER_BLEND_ATTR_COORD(zpos), SUN8I_MIXER_COORD(state->dst.x1, state->dst.y1)); regmap_write(mixer->engine.regs, - SUN8I_MIXER_BLEND_ATTR_INSIZE(channel), + SUN8I_MIXER_BLEND_ATTR_INSIZE(zpos), outsize); return 0; @@ -238,28 +244,30 @@ static void sun8i_ui_layer_atomic_disable(struct drm_plane *plane, struct sun8i_ui_layer *layer = plane_to_sun8i_ui_layer(plane); struct sun8i_mixer *mixer = layer->mixer; - sun8i_ui_layer_enable(mixer, layer->channel, layer->overlay, false); + sun8i_ui_layer_enable(mixer, layer->channel, layer->overlay, false, 0); } static void sun8i_ui_layer_atomic_update(struct drm_plane *plane, struct drm_plane_state *old_state) { struct sun8i_ui_layer *layer = plane_to_sun8i_ui_layer(plane); + unsigned int zpos = plane->state->normalized_zpos; struct sun8i_mixer *mixer = layer->mixer; if (!plane->state->visible) { sun8i_ui_layer_enable(mixer, layer->channel, - layer->overlay, false); + layer->overlay, false, 0); return; } sun8i_ui_layer_update_coord(mixer, layer->channel, - layer->overlay, plane); + layer->overlay, plane, zpos); sun8i_ui_layer_update_formats(mixer, layer->channel, layer->overlay, plane); sun8i_ui_layer_update_buffer(mixer, layer->channel, layer->overlay, plane); - sun8i_ui_layer_enable(mixer, layer->channel, layer->overlay, true); + sun8i_ui_layer_enable(mixer, layer->channel, layer->overlay, + true, zpos); } static struct drm_plane_helper_funcs sun8i_ui_layer_helper_funcs = { @@ -307,6 +315,7 @@ struct sun8i_ui_layer *sun8i_ui_layer_init_one(struct drm_device *drm, enum drm_plane_type type = DRM_PLANE_TYPE_OVERLAY; int channel = mixer->cfg->vi_num + index; struct sun8i_ui_layer *layer; + unsigned int plane_cnt; int ret; layer = devm_kzalloc(drm->dev, sizeof(*layer), GFP_KERNEL); @@ -327,8 +336,10 @@ struct sun8i_ui_layer *sun8i_ui_layer_init_one(struct drm_device *drm, return ERR_PTR(ret); } - /* fixed zpos for now */ - ret = drm_plane_create_zpos_immutable_property(&layer->plane, channel); + plane_cnt = mixer->cfg->ui_num + mixer->cfg->vi_num; + + ret = drm_plane_create_zpos_property(&layer->plane, channel, + 0, plane_cnt - 1); if (ret) { dev_err(drm->dev, "Couldn't add zpos property\n"); return ERR_PTR(ret); diff --git a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c b/drivers/gpu/drm/sun4i/sun8i_vi_layer.c index 5877f8ef5895..17e0d00cfd8a 100644 --- a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c +++ b/drivers/gpu/drm/sun4i/sun8i_vi_layer.c @@ -21,7 +21,7 @@ #include "sun8i_vi_scaler.h" static void sun8i_vi_layer_enable(struct sun8i_mixer *mixer, int channel, - int overlay, bool enable) + int overlay, bool enable, unsigned int zpos) { u32 val; @@ -37,18 +37,24 @@ static void sun8i_vi_layer_enable(struct sun8i_mixer *mixer, int channel, SUN8I_MIXER_CHAN_VI_LAYER_ATTR(channel, overlay), SUN8I_MIXER_CHAN_VI_LAYER_ATTR_EN, val); - if (enable) - val = SUN8I_MIXER_BLEND_PIPE_CTL_EN(channel); - else - val = 0; + if (enable) { + val = SUN8I_MIXER_BLEND_PIPE_CTL_EN(zpos); - regmap_update_bits(mixer->engine.regs, - SUN8I_MIXER_BLEND_PIPE_CTL, - SUN8I_MIXER_BLEND_PIPE_CTL_EN(channel), val); + regmap_update_bits(mixer->engine.regs, + SUN8I_MIXER_BLEND_PIPE_CTL, val, val); + + val = channel << SUN8I_MIXER_BLEND_ROUTE_PIPE_SHIFT(zpos); + + regmap_update_bits(mixer->engine.regs, + SUN8I_MIXER_BLEND_ROUTE, + SUN8I_MIXER_BLEND_ROUTE_PIPE_MSK(zpos), + val); + } } static int sun8i_vi_layer_update_coord(struct sun8i_mixer *mixer, int channel, - int overlay, struct drm_plane *plane) + int overlay, struct drm_plane *plane, + unsigned int zpos) { struct drm_plane_state *state = plane->state; const struct drm_format_info *format = state->fb->format; @@ -130,10 +136,10 @@ static int sun8i_vi_layer_update_coord(struct sun8i_mixer *mixer, int channel, state->dst.x1, state->dst.y1); DRM_DEBUG_DRIVER("Layer destination size W: %d H: %d\n", dst_w, dst_h); regmap_write(mixer->engine.regs, - SUN8I_MIXER_BLEND_ATTR_COORD(channel), + SUN8I_MIXER_BLEND_ATTR_COORD(zpos), SUN8I_MIXER_COORD(state->dst.x1, state->dst.y1)); regmap_write(mixer->engine.regs, - SUN8I_MIXER_BLEND_ATTR_INSIZE(channel), + SUN8I_MIXER_BLEND_ATTR_INSIZE(zpos), outsize); return 0; @@ -266,28 +272,30 @@ static void sun8i_vi_layer_atomic_disable(struct drm_plane *plane, struct sun8i_vi_layer *layer = plane_to_sun8i_vi_layer(plane); struct sun8i_mixer *mixer = layer->mixer; - sun8i_vi_layer_enable(mixer, layer->channel, layer->overlay, false); + sun8i_vi_layer_enable(mixer, layer->channel, layer->overlay, false, 0); } static void sun8i_vi_layer_atomic_update(struct drm_plane *plane, struct drm_plane_state *old_state) { struct sun8i_vi_layer *layer = plane_to_sun8i_vi_layer(plane); + unsigned int zpos = plane->state->normalized_zpos; struct sun8i_mixer *mixer = layer->mixer; if (!plane->state->visible) { sun8i_vi_layer_enable(mixer, layer->channel, - layer->overlay, false); + layer->overlay, false, 0); return; } sun8i_vi_layer_update_coord(mixer, layer->channel, - layer->overlay, plane); + layer->overlay, plane, zpos); sun8i_vi_layer_update_formats(mixer, layer->channel, layer->overlay, plane); sun8i_vi_layer_update_buffer(mixer, layer->channel, layer->overlay, plane); - sun8i_vi_layer_enable(mixer, layer->channel, layer->overlay, true); + sun8i_vi_layer_enable(mixer, layer->channel, layer->overlay, + true, zpos); } static struct drm_plane_helper_funcs sun8i_vi_layer_helper_funcs = { @@ -351,6 +359,7 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct drm_device *drm, int index) { struct sun8i_vi_layer *layer; + unsigned int plane_cnt; int ret; layer = devm_kzalloc(drm->dev, sizeof(*layer), GFP_KERNEL); @@ -368,8 +377,10 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct drm_device *drm, return ERR_PTR(ret); } - /* fixed zpos for now */ - ret = drm_plane_create_zpos_immutable_property(&layer->plane, index); + plane_cnt = mixer->cfg->ui_num + mixer->cfg->vi_num; + + ret = drm_plane_create_zpos_property(&layer->plane, index, + 0, plane_cnt - 1); if (ret) { dev_err(drm->dev, "Couldn't add zpos property\n"); return ERR_PTR(ret);