From: Ryan Walklin <ryan@testtoast.com>
To: Maxime Ripard <mripard@kernel.org>, Chen-Yu Tsai <wens@csie.org>,
Maarten Lankhorst <maarten.lankhorst@linux.intel.com>,
Thomas Zimmermann <tzimmermann@suse.de>,
David Airlie <airlied@gmail.com>, Daniel Vetter <daniel@ffwll.ch>,
Jernej Skrabec <jernej.skrabec@gmail.com>,
Samuel Holland <samuel@sholland.org>,
Rob Herring <robh@kernel.org>,
Krzysztof Kozlowski <krzk+dt@kernel.org>,
Conor Dooley <conor+dt@kernel.org>,
Michael Turquette <mturquette@baylibre.com>,
Stephen Boyd <sboyd@kernel.org>
Cc: Andre Przywara <andre.przywara@arm.com>,
Chris Morgan <macroalpha82@gmail.com>,
John Watts <contact@jookia.org>,
dri-devel@lists.freedesktop.org,
linux-arm-kernel@lists.infradead.org,
linux-sunxi@lists.linux.dev, devicetree@vger.kernel.org,
linux-clk@vger.kernel.org, Ryan Walklin <ryan@testtoast.com>
Subject: [PATCH 20/23] drm: sun4i: de33: mixer: add Display Engine 3.3 (DE33) support
Date: Thu, 20 Jun 2024 23:29:58 +1200 [thread overview]
Message-ID: <20240620113150.83466-21-ryan@testtoast.com> (raw)
In-Reply-To: <20240620113150.83466-1-ryan@testtoast.com>
From: Jernej Skrabec <jernej.skrabec@gmail.com>
The DE33 is a newer version of the Allwinner Display Engine IP block,
found in the H616, H618, H700 and T507 SoCs. DE2 and DE3 are already
supported by the mainline driver.
Notable features (from the H616 datasheet and implemented):
- 4096 x 2048 (4K) output support
- AFBC ARM Frame Buffer Compression support
- YUV420 input support
Extend the mixer to support the DE33.
Signed-off-by: Jernej Skrabec <jernej.skrabec@gmail.com>
Signed-off-by: Ryan Walklin <ryan@testtoast.com>
---
drivers/gpu/drm/sun4i/sun8i_mixer.c | 109 ++++++++++++++++++++++++----
drivers/gpu/drm/sun4i/sun8i_mixer.h | 16 +++-
2 files changed, 108 insertions(+), 17 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.c b/drivers/gpu/drm/sun4i/sun8i_mixer.c
index 533aa93d2a30e..cc0726f9cb4ae 100644
--- a/drivers/gpu/drm/sun4i/sun8i_mixer.c
+++ b/drivers/gpu/drm/sun4i/sun8i_mixer.c
@@ -254,10 +254,16 @@ int sun8i_mixer_drm_format_to_hw(u32 format, u32 *hw_format)
static void sun8i_mixer_commit(struct sunxi_engine *engine)
{
+ struct sun8i_mixer *mixer = engine_to_sun8i_mixer(engine);
+
DRM_DEBUG_DRIVER("Committing changes\n");
- regmap_write(engine->regs, SUN8I_MIXER_GLOBAL_DBUFF,
- SUN8I_MIXER_GLOBAL_DBUFF_ENABLE);
+ if (mixer->cfg->de_type == sun8i_mixer_de33)
+ regmap_write(mixer->top_regs, SUN50I_MIXER_GLOBAL_DBUFF,
+ SUN8I_MIXER_GLOBAL_DBUFF_ENABLE);
+ else
+ regmap_write(engine->regs, SUN8I_MIXER_GLOBAL_DBUFF,
+ SUN8I_MIXER_GLOBAL_DBUFF_ENABLE);
}
static struct drm_plane **sun8i_layers_init(struct drm_device *drm,
@@ -306,25 +312,33 @@ static void sun8i_mixer_mode_set(struct sunxi_engine *engine,
const struct drm_display_mode *mode)
{
struct sun8i_mixer *mixer = engine_to_sun8i_mixer(engine);
+ struct regmap *bld_regs, *disp_regs;
u32 bld_base, size, val;
bool interlaced;
bld_base = sun8i_blender_base(mixer);
+ bld_regs = sun8i_blender_regmap(mixer);
interlaced = !!(mode->flags & DRM_MODE_FLAG_INTERLACE);
size = SUN8I_MIXER_SIZE(mode->hdisplay, mode->vdisplay);
DRM_DEBUG_DRIVER("Updating global size W: %u H: %u\n",
mode->hdisplay, mode->vdisplay);
- regmap_write(engine->regs, SUN8I_MIXER_GLOBAL_SIZE, size);
- regmap_write(engine->regs, SUN8I_MIXER_BLEND_OUTSIZE(bld_base), size);
+ if (mixer->cfg->de_type == sun8i_mixer_de33) {
+ disp_regs = mixer->disp_regs;
+ regmap_write(mixer->top_regs, SUN50I_MIXER_GLOBAL_SIZE, size);
+ } else {
+ disp_regs = mixer->engine.regs;
+ regmap_write(mixer->engine.regs, SUN8I_MIXER_GLOBAL_SIZE, size);
+ }
+ regmap_write(bld_regs, SUN8I_MIXER_BLEND_OUTSIZE(bld_base), size);
if (interlaced)
val = SUN8I_MIXER_BLEND_OUTCTL_INTERLACED;
else
val = 0;
- regmap_update_bits(engine->regs, SUN8I_MIXER_BLEND_OUTCTL(bld_base),
+ regmap_update_bits(bld_regs, SUN8I_MIXER_BLEND_OUTCTL(bld_base),
SUN8I_MIXER_BLEND_OUTCTL_INTERLACED, val);
DRM_DEBUG_DRIVER("Switching display mixer interlaced mode %s\n",
@@ -335,10 +349,8 @@ static void sun8i_mixer_mode_set(struct sunxi_engine *engine,
else
val = 0xff108080;
- regmap_write(mixer->engine.regs,
- SUN8I_MIXER_BLEND_BKCOLOR(bld_base), val);
- regmap_write(mixer->engine.regs,
- SUN8I_MIXER_BLEND_ATTR_FCOLOR(bld_base, 0), val);
+ regmap_write(disp_regs, SUN8I_MIXER_BLEND_BKCOLOR(bld_base), val);
+ regmap_write(disp_regs, SUN8I_MIXER_BLEND_ATTR_FCOLOR(bld_base, 0), val);
if (mixer->cfg->has_formatter)
sun50i_fmt_setup(mixer, mode->hdisplay,
@@ -378,12 +390,29 @@ static const struct sunxi_engine_ops sun8i_engine_ops = {
};
static const struct regmap_config sun8i_mixer_regmap_config = {
+ .name = "layers",
.reg_bits = 32,
.val_bits = 32,
.reg_stride = 4,
.max_register = 0xffffc, /* guessed */
};
+static const struct regmap_config sun8i_top_regmap_config = {
+ .name = "top",
+ .reg_bits = 32,
+ .val_bits = 32,
+ .reg_stride = 4,
+ .max_register = 0x3c,
+};
+
+static const struct regmap_config sun8i_disp_regmap_config = {
+ .name = "display",
+ .reg_bits = 32,
+ .val_bits = 32,
+ .reg_stride = 4,
+ .max_register = 0x20000,
+};
+
static int sun8i_mixer_of_get_id(struct device_node *node)
{
struct device_node *ep, *remote;
@@ -406,35 +435,45 @@ static int sun8i_mixer_of_get_id(struct device_node *node)
static void sun8i_mixer_init(struct sun8i_mixer *mixer)
{
+ struct regmap *top_regs, *disp_regs;
unsigned int base;
int plane_cnt, i;
base = sun8i_blender_base(mixer);
+ if (mixer->cfg->de_type == sun8i_mixer_de33) {
+ top_regs = mixer->top_regs;
+ disp_regs = mixer->disp_regs;
+ } else {
+ top_regs = disp_regs = mixer->engine.regs;
+ }
/* Enable the mixer */
- regmap_write(mixer->engine.regs, SUN8I_MIXER_GLOBAL_CTL,
+ regmap_write(top_regs, SUN8I_MIXER_GLOBAL_CTL,
SUN8I_MIXER_GLOBAL_CTL_RT_EN);
+ if (mixer->cfg->de_type == sun8i_mixer_de33)
+ regmap_write(top_regs, SUN50I_MIXER_GLOBAL_CLK, 1);
+
/* Set background color to black */
- regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_BKCOLOR(base),
+ regmap_write(disp_regs, SUN8I_MIXER_BLEND_BKCOLOR(base),
SUN8I_MIXER_BLEND_COLOR_BLACK);
/*
* Set fill color of bottom plane to black. Generally not needed
* except when VI plane is at bottom (zpos = 0) and enabled.
*/
- regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_PIPE_CTL(base),
+ regmap_write(disp_regs, SUN8I_MIXER_BLEND_PIPE_CTL(base),
SUN8I_MIXER_BLEND_PIPE_CTL_FC_EN(0));
- regmap_write(mixer->engine.regs, SUN8I_MIXER_BLEND_ATTR_FCOLOR(base, 0),
+ regmap_write(disp_regs, SUN8I_MIXER_BLEND_ATTR_FCOLOR(base, 0),
SUN8I_MIXER_BLEND_COLOR_BLACK);
plane_cnt = mixer->cfg->vi_num + mixer->cfg->ui_num;
for (i = 0; i < plane_cnt; i++)
- regmap_write(mixer->engine.regs,
+ regmap_write(disp_regs,
SUN8I_MIXER_BLEND_MODE(base, i),
SUN8I_MIXER_BLEND_MODE_DEF);
- regmap_update_bits(mixer->engine.regs, SUN8I_MIXER_BLEND_PIPE_CTL(base),
+ regmap_update_bits(disp_regs, SUN8I_MIXER_BLEND_PIPE_CTL(base),
SUN8I_MIXER_BLEND_PIPE_CTL_EN_MSK, 0);
}
@@ -510,6 +549,30 @@ static int sun8i_mixer_bind(struct device *dev, struct device *master,
return PTR_ERR(mixer->engine.regs);
}
+ if (mixer->cfg->de_type == sun8i_mixer_de33) {
+ regs = devm_platform_ioremap_resource(pdev, 1);
+ if (IS_ERR(regs))
+ return PTR_ERR(regs);
+
+ mixer->top_regs = devm_regmap_init_mmio(dev, regs,
+ &sun8i_top_regmap_config);
+ if (IS_ERR(mixer->top_regs)) {
+ dev_err(dev, "Couldn't create the top regmap\n");
+ return PTR_ERR(mixer->top_regs);
+ }
+
+ regs = devm_platform_ioremap_resource(pdev, 2);
+ if (IS_ERR(regs))
+ return PTR_ERR(regs);
+
+ mixer->disp_regs = devm_regmap_init_mmio(dev, regs,
+ &sun8i_disp_regmap_config);
+ if (IS_ERR(mixer->disp_regs)) {
+ dev_err(dev, "Couldn't create the disp regmap\n");
+ return PTR_ERR(mixer->disp_regs);
+ }
+ }
+
mixer->reset = devm_reset_control_get(dev, NULL);
if (IS_ERR(mixer->reset)) {
dev_err(dev, "Couldn't get our reset line\n");
@@ -725,6 +788,18 @@ static const struct sun8i_mixer_cfg sun50i_h6_mixer0_cfg = {
.vi_num = 1,
};
+static const struct sun8i_mixer_cfg sun50i_h616_mixer0_cfg = {
+ .ccsc = CCSC_MIXER0_LAYOUT,
+ .de_type = sun8i_mixer_de33,
+ .has_formatter = 1,
+ .mod_rate = 600000000,
+ .scaler_mask = 0xf,
+ .scanline_yuv = 4096,
+ .ui_num = 3,
+ .vi_num = 1,
+ .map = {0, 6, 7, 8},
+};
+
static const struct of_device_id sun8i_mixer_of_table[] = {
{
.compatible = "allwinner,sun8i-a83t-de2-mixer-0",
@@ -770,6 +845,10 @@ static const struct of_device_id sun8i_mixer_of_table[] = {
.compatible = "allwinner,sun50i-h6-de3-mixer-0",
.data = &sun50i_h6_mixer0_cfg,
},
+ {
+ .compatible = "allwinner,sun50i-h616-de33-mixer-0",
+ .data = &sun50i_h616_mixer0_cfg,
+ },
{ }
};
MODULE_DEVICE_TABLE(of, sun8i_mixer_of_table);
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.h b/drivers/gpu/drm/sun4i/sun8i_mixer.h
index ed7370688d52e..29bc07a6868d5 100644
--- a/drivers/gpu/drm/sun4i/sun8i_mixer.h
+++ b/drivers/gpu/drm/sun4i/sun8i_mixer.h
@@ -20,6 +20,10 @@
#define SUN8I_MIXER_GLOBAL_DBUFF 0x8
#define SUN8I_MIXER_GLOBAL_SIZE 0xc
+#define SUN50I_MIXER_GLOBAL_SIZE 0x8
+#define SUN50I_MIXER_GLOBAL_CLK 0xc
+#define SUN50I_MIXER_GLOBAL_DBUFF 0x10
+
#define SUN8I_MIXER_GLOBAL_CTL_RT_EN BIT(0)
#define SUN8I_MIXER_GLOBAL_DBUFF_ENABLE BIT(0)
@@ -153,6 +157,7 @@ enum {
enum sun8i_mixer_type {
sun8i_mixer_de2,
sun8i_mixer_de3,
+ sun8i_mixer_de33,
};
/**
@@ -179,6 +184,7 @@ struct sun8i_mixer_cfg {
unsigned int de_type;
unsigned int has_formatter : 1;
unsigned int scanline_yuv;
+ unsigned int map[6];
};
struct sun8i_mixer {
@@ -190,6 +196,9 @@ struct sun8i_mixer {
struct clk *bus_clk;
struct clk *mod_clk;
+
+ struct regmap *top_regs;
+ struct regmap *disp_regs;
};
static inline struct sun8i_mixer *
@@ -207,13 +216,16 @@ sun8i_blender_base(struct sun8i_mixer *mixer)
static inline struct regmap *
sun8i_blender_regmap(struct sun8i_mixer *mixer)
{
- return mixer->engine.regs;
+ return mixer->cfg->de_type == sun8i_mixer_de33 ?
+ mixer->disp_regs : mixer->engine.regs;
}
static inline u32
sun8i_channel_base(struct sun8i_mixer *mixer, int channel)
{
- if (mixer->cfg->de_type == sun8i_mixer_de3)
+ if (mixer->cfg->de_type == sun8i_mixer_de33)
+ return mixer->cfg->map[channel] * 0x20000 + DE2_CH_SIZE;
+ else if (mixer->cfg->de_type == sun8i_mixer_de3)
return DE3_CH_BASE + channel * DE3_CH_SIZE;
else
return DE2_CH_BASE + channel * DE2_CH_SIZE;
--
2.45.2
next prev parent reply other threads:[~2024-06-20 11:34 UTC|newest]
Thread overview: 31+ messages / expand[flat|nested] mbox.gz Atom feed top
2024-06-20 11:29 [PATCH 00/23] drm: sun4i: add Display Engine 3.3 (DE33) support Ryan Walklin
2024-06-20 11:29 ` [PATCH 01/23] drm: sun4i: de2/de3: Change CSC argument Ryan Walklin
2024-06-25 0:27 ` Andre Przywara
2024-06-20 11:29 ` [PATCH 02/23] drm: sun4i: de2/de3: Merge CSC functions into one Ryan Walklin
2024-06-20 11:29 ` [PATCH 03/23] drm: sun4i: de2/de3: call csc setup also for UI layer Ryan Walklin
2024-06-20 11:29 ` [PATCH 04/23] drm: sun4i: de2: Initialize layer fields earlier Ryan Walklin
2024-06-20 11:29 ` [PATCH 05/23] drm: sun4i: de3: Add YUV formatter module Ryan Walklin
2024-06-20 11:29 ` [PATCH 06/23] drm: sun4i: de3: add format enumeration function to engine Ryan Walklin
2024-06-20 11:29 ` [PATCH 07/23] drm: sun4i: de3: add formatter flag to mixer config Ryan Walklin
2024-06-20 11:29 ` [PATCH 08/23] drm: sun4i: de3: add YUV support to the DE3 mixer Ryan Walklin
2024-06-20 11:29 ` [PATCH 09/23] drm: sun4i: de3: pass engine reference to ccsc setup function Ryan Walklin
2024-06-20 11:29 ` [PATCH 10/23] drm: sun4i: de3: add YUV support to the color space correction module Ryan Walklin
2024-06-20 11:29 ` [PATCH 11/23] drm: sun4i: de3: add YUV support to the TCON Ryan Walklin
2024-06-20 11:29 ` [PATCH 12/23] drm: sun4i: support YUV formats in VI scaler Ryan Walklin
2024-06-20 11:29 ` [PATCH 13/23] drm: sun4i: de2/de3: add mixer version enum Ryan Walklin
2024-06-25 0:27 ` Andre Przywara
2024-06-20 11:29 ` [PATCH 14/23] drm: sun4i: de2/de3: refactor mixer initialisation Ryan Walklin
2024-06-25 0:28 ` Andre Przywara
2024-06-25 1:23 ` Ryan Walklin
2024-06-20 11:29 ` [PATCH 15/23] drm: sun4i: vi_scaler refactor vi_scaler enablement Ryan Walklin
2024-06-20 11:29 ` [PATCH 16/23] drm: sun4i: de2/de3: make blender register references generic Ryan Walklin
2024-06-20 11:29 ` [PATCH 17/23] drm: sun4i: de3: Implement AFBC support Ryan Walklin
2024-06-20 11:29 ` [PATCH 18/23] dt-bindings: allwinner: add H616 DE33 bus, clock and display bindings Ryan Walklin
2024-06-20 12:25 ` Rob Herring (Arm)
2024-06-25 0:37 ` Andre Przywara
2024-06-25 1:24 ` Ryan Walklin
2024-06-20 11:29 ` [PATCH 19/23] clk: sunxi-ng: ccu: add Display Engine 3.3 (DE33) support Ryan Walklin
2024-06-20 11:29 ` Ryan Walklin [this message]
2024-06-20 11:29 ` [PATCH 21/23] drm: sun4i: de33: vi_scaler: " Ryan Walklin
2024-06-20 11:30 ` [PATCH 22/23] drm: sun4i: de33: fmt: " Ryan Walklin
2024-06-20 11:30 ` [PATCH 23/23] drm: sun4i: de33: csc: " Ryan Walklin
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20240620113150.83466-21-ryan@testtoast.com \
--to=ryan@testtoast.com \
--cc=airlied@gmail.com \
--cc=andre.przywara@arm.com \
--cc=conor+dt@kernel.org \
--cc=contact@jookia.org \
--cc=daniel@ffwll.ch \
--cc=devicetree@vger.kernel.org \
--cc=dri-devel@lists.freedesktop.org \
--cc=jernej.skrabec@gmail.com \
--cc=krzk+dt@kernel.org \
--cc=linux-arm-kernel@lists.infradead.org \
--cc=linux-clk@vger.kernel.org \
--cc=linux-sunxi@lists.linux.dev \
--cc=maarten.lankhorst@linux.intel.com \
--cc=macroalpha82@gmail.com \
--cc=mripard@kernel.org \
--cc=mturquette@baylibre.com \
--cc=robh@kernel.org \
--cc=samuel@sholland.org \
--cc=sboyd@kernel.org \
--cc=tzimmermann@suse.de \
--cc=wens@csie.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).