From patchwork Thu Jan 26 15:31:11 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Liviu Dudau X-Patchwork-Id: 92535 Delivered-To: patch@linaro.org Received: by 10.140.20.99 with SMTP id 90csp240058qgi; Thu, 26 Jan 2017 07:31:21 -0800 (PST) X-Received: by 10.98.208.70 with SMTP id p67mr3786502pfg.101.1485444681049; Thu, 26 Jan 2017 07:31:21 -0800 (PST) Return-Path: Received: from gabe.freedesktop.org (gabe.freedesktop.org. [131.252.210.177]) by mx.google.com with ESMTPS id l74si1651673pfa.275.2017.01.26.07.31.20 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Thu, 26 Jan 2017 07:31:21 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of dri-devel-bounces@lists.freedesktop.org designates 131.252.210.177 as permitted sender) client-ip=131.252.210.177; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of dri-devel-bounces@lists.freedesktop.org designates 131.252.210.177 as permitted sender) smtp.mailfrom=dri-devel-bounces@lists.freedesktop.org Received: from gabe.freedesktop.org (localhost [127.0.0.1]) by gabe.freedesktop.org (Postfix) with ESMTP id 588AD6EBC8; Thu, 26 Jan 2017 15:31:19 +0000 (UTC) X-Original-To: dri-devel@lists.freedesktop.org Delivered-To: dri-devel@lists.freedesktop.org Received: from cam-smtp0.cambridge.arm.com (fw-tnat.cambridge.arm.com [217.140.96.140]) by gabe.freedesktop.org (Postfix) with ESMTPS id 721CE6EBC8 for ; Thu, 26 Jan 2017 15:31:17 +0000 (UTC) Received: from e110455-lin.cambridge.arm.com (e110455-lin.cambridge.arm.com [10.2.131.175]) by cam-smtp0.cambridge.arm.com (8.13.8/8.13.8) with ESMTP id v0QFVBAd011384; Thu, 26 Jan 2017 15:31:12 GMT From: Liviu Dudau To: Brian Starkey Subject: [PATCH 2/2] drm: mali-dp: fix stride setting for multi-plane formats Date: Thu, 26 Jan 2017 15:31:11 +0000 Message-Id: <20170126153111.18813-2-Liviu.Dudau@arm.com> X-Mailer: git-send-email 2.11.0 In-Reply-To: <20170126153111.18813-1-Liviu.Dudau@arm.com> References: <20170126153111.18813-1-Liviu.Dudau@arm.com> Cc: Mihail Atanassov , Mali DP Maintainers , LKML , DRI devel X-BeenThere: dri-devel@lists.freedesktop.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: Direct Rendering Infrastructure - Development List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" From: Mihail Atanassov Hardware has multiple (2 or 3, depending on model) stride registers per layer; add a function that correctly takes that into account. On hardware that only has 2 stride registers, ensure that 3-plane (YUV) content has identical strides for both chroma planes. Signed-off-by: Mihail Atanassov [Removed smart layer stride setup, comment and commit message clarifications] Signed-off-by: Liviu Dudau --- drivers/gpu/drm/arm/malidp_hw.c | 17 ++++++++++------- drivers/gpu/drm/arm/malidp_hw.h | 5 +++++ drivers/gpu/drm/arm/malidp_planes.c | 34 +++++++++++++++++++++++++++++++--- drivers/gpu/drm/arm/malidp_regs.h | 4 ++++ 4 files changed, 50 insertions(+), 10 deletions(-) diff --git a/drivers/gpu/drm/arm/malidp_hw.c b/drivers/gpu/drm/arm/malidp_hw.c index 9ec6d6904f5e..488aedf5b58d 100644 --- a/drivers/gpu/drm/arm/malidp_hw.c +++ b/drivers/gpu/drm/arm/malidp_hw.c @@ -74,16 +74,16 @@ static const struct malidp_format_id malidp550_de_formats[] = { }; static const struct malidp_layer malidp500_layers[] = { - { DE_VIDEO1, MALIDP500_DE_LV_BASE, MALIDP500_DE_LV_PTR_BASE }, - { DE_GRAPHICS1, MALIDP500_DE_LG1_BASE, MALIDP500_DE_LG1_PTR_BASE }, - { DE_GRAPHICS2, MALIDP500_DE_LG2_BASE, MALIDP500_DE_LG2_PTR_BASE }, + { DE_VIDEO1, MALIDP500_DE_LV_BASE, MALIDP500_DE_LV_PTR_BASE, MALIDP_DE_LV_STRIDE0 }, + { DE_GRAPHICS1, MALIDP500_DE_LG1_BASE, MALIDP500_DE_LG1_PTR_BASE, MALIDP_DE_LG_STRIDE }, + { DE_GRAPHICS2, MALIDP500_DE_LG2_BASE, MALIDP500_DE_LG2_PTR_BASE, MALIDP_DE_LG_STRIDE }, }; static const struct malidp_layer malidp550_layers[] = { - { DE_VIDEO1, MALIDP550_DE_LV1_BASE, MALIDP550_DE_LV1_PTR_BASE }, - { DE_GRAPHICS1, MALIDP550_DE_LG_BASE, MALIDP550_DE_LG_PTR_BASE }, - { DE_VIDEO2, MALIDP550_DE_LV2_BASE, MALIDP550_DE_LV2_PTR_BASE }, - { DE_SMART, MALIDP550_DE_LS_BASE, MALIDP550_DE_LS_PTR_BASE }, + { DE_VIDEO1, MALIDP550_DE_LV1_BASE, MALIDP550_DE_LV1_PTR_BASE, MALIDP_DE_LV_STRIDE0 }, + { DE_GRAPHICS1, MALIDP550_DE_LG_BASE, MALIDP550_DE_LG_PTR_BASE, MALIDP_DE_LG_STRIDE }, + { DE_VIDEO2, MALIDP550_DE_LV2_BASE, MALIDP550_DE_LV2_PTR_BASE, MALIDP_DE_LV_STRIDE0 }, + { DE_SMART, MALIDP550_DE_LS_BASE, MALIDP550_DE_LS_PTR_BASE, 0 }, }; #define MALIDP_DE_DEFAULT_PREFETCH_START 5 @@ -447,6 +447,7 @@ const struct malidp_hw_device malidp_device[MALIDP_MAX_DEVICES] = { .set_config_valid = malidp500_set_config_valid, .modeset = malidp500_modeset, .rotmem_required = malidp500_rotmem_required, + .features = MALIDP_DEVICE_LV_HAS_3_STRIDES, }, [MALIDP_550] = { .map = { @@ -480,6 +481,7 @@ const struct malidp_hw_device malidp_device[MALIDP_MAX_DEVICES] = { .set_config_valid = malidp550_set_config_valid, .modeset = malidp550_modeset, .rotmem_required = malidp550_rotmem_required, + .features = 0, }, [MALIDP_650] = { .map = { @@ -514,6 +516,7 @@ const struct malidp_hw_device malidp_device[MALIDP_MAX_DEVICES] = { .set_config_valid = malidp550_set_config_valid, .modeset = malidp550_modeset, .rotmem_required = malidp550_rotmem_required, + .features = 0, }, }; diff --git a/drivers/gpu/drm/arm/malidp_hw.h b/drivers/gpu/drm/arm/malidp_hw.h index 4f8c884d1960..00974b59407d 100644 --- a/drivers/gpu/drm/arm/malidp_hw.h +++ b/drivers/gpu/drm/arm/malidp_hw.h @@ -58,6 +58,7 @@ struct malidp_layer { u16 id; /* layer ID */ u16 base; /* address offset for the register bank */ u16 ptr; /* address offset for the pointer register */ + u16 stride_offset; /* Offset to the first stride register. */ }; /* regmap features */ @@ -93,6 +94,10 @@ struct malidp_hw_regmap { const u8 bus_align_bytes; }; +/* device features */ +/* Unlike DP550/650, DP500 has 3 stride registers in its video layer. */ +#define MALIDP_DEVICE_LV_HAS_3_STRIDES BIT(0) + struct malidp_hw_device { const struct malidp_hw_regmap map; void __iomem *regs; diff --git a/drivers/gpu/drm/arm/malidp_planes.c b/drivers/gpu/drm/arm/malidp_planes.c index 837874e79334..414aada10fe5 100644 --- a/drivers/gpu/drm/arm/malidp_planes.c +++ b/drivers/gpu/drm/arm/malidp_planes.c @@ -37,7 +37,6 @@ #define LAYER_V_VAL(x) (((x) & 0x1fff) << 16) #define MALIDP_LAYER_COMP_SIZE 0x010 #define MALIDP_LAYER_OFFSET 0x014 -#define MALIDP_LAYER_STRIDE 0x018 /* * This 4-entry look-up-table is used to determine the full 8-bit alpha value @@ -138,6 +137,16 @@ static int malidp_de_plane_check(struct drm_plane *plane, (state->crtc_h < mp->hwdev->min_line_size)) return -EINVAL; + /* + * DP550/650 video layers can accept 3 plane formats only if + * fb->pitches[1] == fb->pitches[2] since they don't have a + * third plane stride register. + */ + if (ms->n_planes == 3 && + !(mp->hwdev->features & MALIDP_DEVICE_LV_HAS_3_STRIDES) && + (state->fb->pitches[1] != state->fb->pitches[2])) + return -EINVAL; + /* packed RGB888 / BGR888 can't be rotated or flipped */ if (state->rotation != DRM_ROTATE_0 && (fb->format->format == DRM_FORMAT_RGB888 || @@ -170,6 +179,25 @@ static int malidp_de_plane_check(struct drm_plane *plane, return 0; } +static void malidp_de_set_plane_pitches(struct malidp_plane *mp, + int num_planes, unsigned int pitches[3]) +{ + int i; + int num_strides = num_planes; + + if (!mp->layer->stride_offset) + return; + + if (num_planes == 3) + num_strides = (mp->hwdev->features & + MALIDP_DEVICE_LV_HAS_3_STRIDES) ? 3 : 2; + + for (i = 0; i < num_strides; ++i) + malidp_hw_write(mp->hwdev, pitches[i], + mp->layer->base + + mp->layer->stride_offset + i * 4); +} + static void malidp_de_plane_update(struct drm_plane *plane, struct drm_plane_state *old_state) { @@ -200,9 +228,9 @@ static void malidp_de_plane_update(struct drm_plane *plane, obj->paddr += plane->state->fb->offsets[i]; malidp_hw_write(mp->hwdev, lower_32_bits(obj->paddr), ptr); malidp_hw_write(mp->hwdev, upper_32_bits(obj->paddr), ptr + 4); - malidp_hw_write(mp->hwdev, plane->state->fb->pitches[i], - mp->layer->base + MALIDP_LAYER_STRIDE); } + malidp_de_set_plane_pitches(mp, ms->n_planes, + plane->state->fb->pitches); malidp_hw_write(mp->hwdev, LAYER_H_VAL(src_w) | LAYER_V_VAL(src_h), mp->layer->base + MALIDP_LAYER_SIZE); diff --git a/drivers/gpu/drm/arm/malidp_regs.h b/drivers/gpu/drm/arm/malidp_regs.h index e0651d28c485..aff6d4a84e99 100644 --- a/drivers/gpu/drm/arm/malidp_regs.h +++ b/drivers/gpu/drm/arm/malidp_regs.h @@ -81,6 +81,10 @@ #define MALIDP_DE_SYNC_WIDTH 0x8 #define MALIDP_DE_HV_ACTIVE 0xc +/* Stride register offsets relative to Lx_BASE */ +#define MALIDP_DE_LG_STRIDE 0x18 +#define MALIDP_DE_LV_STRIDE0 0x18 + /* macros to set values into registers */ #define MALIDP_DE_H_FRONTPORCH(x) (((x) & 0xfff) << 0) #define MALIDP_DE_H_BACKPORCH(x) (((x) & 0x3ff) << 16)