This series adds binding and driver support for Display Engine 2.0 variant found in the Allwinner D1.
So far it has only been tested with HDMI. I will be sending the HDMI support series separately, because the hardware comes with a brand new custom HDMI PHY, which requires some refactoring to support cleanly.
Samuel Holland (10): dt-bindings: display: Separate clock item lists by compatible dt-bindings: display: Add D1 display engine compatibles drm/sun4i: Remove obsolete references to PHYS_OFFSET drm/sun4i: Allow building the driver on RISC-V drm/sun4i: csc: Add support for the new MMIO layout drm/sun4i: Allow VI layers to be primary planes drm/sun4i: Add support for D1 mixers drm/sun4i: Add support for D1 TCON TOP drm/sun4i: Add support for D1 TCONs drm/sun4i: Add compatible for D1 display engine
.../allwinner,sun4i-a10-display-engine.yaml | 1 + .../display/allwinner,sun4i-a10-tcon.yaml | 2 + .../allwinner,sun8i-a83t-de2-mixer.yaml | 2 + .../display/allwinner,sun8i-r40-tcon-top.yaml | 145 ++++++++++++------ drivers/gpu/drm/sun4i/Kconfig | 2 +- drivers/gpu/drm/sun4i/sun4i_drv.c | 1 + drivers/gpu/drm/sun4i/sun4i_frontend.c | 3 - drivers/gpu/drm/sun4i/sun4i_tcon.c | 8 + drivers/gpu/drm/sun4i/sun8i_csc.c | 3 +- drivers/gpu/drm/sun4i/sun8i_csc.h | 1 + drivers/gpu/drm/sun4i/sun8i_mixer.c | 26 ++++ drivers/gpu/drm/sun4i/sun8i_mixer.h | 6 +- drivers/gpu/drm/sun4i/sun8i_tcon_top.c | 15 +- drivers/gpu/drm/sun4i/sun8i_vi_layer.c | 36 ++++- 14 files changed, 196 insertions(+), 55 deletions(-)
So far, the binding and driver have relied on the fact that the H6 clocks are both a prefix and a subset of the R40 clocks. This allows them to share the clocks/clock-names items and the clock-output-names order between the hardware variants.
However, the D1 hardware has TCON TV0 and DSI, but no TCON TV1. This cannot be supported by the existing scheme because it puts a gap in the middle of the item lists. To prepare for adding D1 support, use separate lists for variants with different combinations of clocks.
Signed-off-by: Samuel Holland samuel@sholland.org ---
.../display/allwinner,sun8i-r40-tcon-top.yaml | 111 +++++++++++------- 1 file changed, 67 insertions(+), 44 deletions(-)
diff --git a/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml b/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml index 61ef7b337218..784b267635fb 100644 --- a/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml +++ b/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml @@ -48,31 +48,15 @@ properties:
clocks: minItems: 2 - items: - - description: The TCON TOP interface clock - - description: The TCON TOP TV0 clock - - description: The TCON TOP TVE0 clock - - description: The TCON TOP TV1 clock - - description: The TCON TOP TVE1 clock - - description: The TCON TOP MIPI DSI clock + maxItems: 6
clock-names: minItems: 2 - items: - - const: bus - - const: tcon-tv0 - - const: tve0 - - const: tcon-tv1 - - const: tve1 - - const: dsi + maxItems: 6
clock-output-names: minItems: 1 maxItems: 3 - description: > - The first item is the name of the clock created for the TV0 - channel, the second item is the name of the TCON TV1 channel - clock and the third one is the name of the DSI channel clock.
resets: maxItems: 1 @@ -129,32 +113,71 @@ required:
additionalProperties: false
-if: - properties: - compatible: - contains: - const: allwinner,sun50i-h6-tcon-top - -then: - properties: - clocks: - maxItems: 2 - - clock-output-names: - maxItems: 1 - -else: - properties: - clocks: - minItems: 6 - - clock-output-names: - minItems: 3 - - ports: - required: - - port@2 - - port@3 +allOf: + - if: + properties: + compatible: + contains: + const: allwinner,sun8i-r40-tcon-top + + then: + properties: + clocks: + minItems: 6 + items: + - description: The TCON TOP interface clock + - description: The TCON TOP TV0 clock + - description: The TCON TOP TVE0 clock + - description: The TCON TOP TV1 clock + - description: The TCON TOP TVE1 clock + - description: The TCON TOP MIPI DSI clock + + clock-names: + minItems: 6 + items: + - const: bus + - const: tcon-tv0 + - const: tve0 + - const: tcon-tv1 + - const: tve1 + - const: dsi + + clock-output-names: + minItems: 3 + items: + - description: TCON TV0 output clock name + - description: TCON TV1 output clock name + - description: DSI output clock name + + ports: + required: + - port@2 + - port@3 + + - if: + properties: + compatible: + contains: + const: allwinner,sun50i-h6-tcon-top + + then: + properties: + clocks: + maxItems: 2 + items: + - description: The TCON TOP interface clock + - description: The TCON TOP TV0 clock + + clock-names: + maxItems: 2 + items: + - const: bus + - const: tcon-tv0 + + clock-output-names: + maxItems: 1 + items: + - description: TCON TV0 output clock name
examples: - |
On 11/04/2022 06:34, Samuel Holland wrote:
So far, the binding and driver have relied on the fact that the H6 clocks are both a prefix and a subset of the R40 clocks. This allows them to share the clocks/clock-names items and the clock-output-names order between the hardware variants.
However, the D1 hardware has TCON TV0 and DSI, but no TCON TV1. This cannot be supported by the existing scheme because it puts a gap in the middle of the item lists. To prepare for adding D1 support, use separate lists for variants with different combinations of clocks.
Signed-off-by: Samuel Holland samuel@sholland.org
Reviewed-by: Krzysztof Kozlowski krzysztof.kozlowski@linaro.org
Best regards, Krzysztof
Allwinner D1 contains a display engine 2.0. It features two mixers, a TCON TOP (with DSI and HDMI), one TCON LCD, and one TCON TV.
Signed-off-by: Samuel Holland samuel@sholland.org ---
.../allwinner,sun4i-a10-display-engine.yaml | 1 + .../display/allwinner,sun4i-a10-tcon.yaml | 2 ++ .../allwinner,sun8i-a83t-de2-mixer.yaml | 2 ++ .../display/allwinner,sun8i-r40-tcon-top.yaml | 34 +++++++++++++++++++ 4 files changed, 39 insertions(+)
diff --git a/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-display-engine.yaml b/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-display-engine.yaml index d4412aea7b73..c388ae5da1e4 100644 --- a/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-display-engine.yaml +++ b/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-display-engine.yaml @@ -62,6 +62,7 @@ properties: - allwinner,sun8i-r40-display-engine - allwinner,sun8i-v3s-display-engine - allwinner,sun9i-a80-display-engine + - allwinner,sun20i-d1-display-engine - allwinner,sun50i-a64-display-engine - allwinner,sun50i-h6-display-engine
diff --git a/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-tcon.yaml b/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-tcon.yaml index 3a7d5d731712..4a92a4c7dcd7 100644 --- a/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-tcon.yaml +++ b/Documentation/devicetree/bindings/display/allwinner,sun4i-a10-tcon.yaml @@ -33,6 +33,8 @@ properties: - const: allwinner,sun8i-v3s-tcon - const: allwinner,sun9i-a80-tcon-lcd - const: allwinner,sun9i-a80-tcon-tv + - const: allwinner,sun20i-d1-tcon-lcd + - const: allwinner,sun20i-d1-tcon-tv
- items: - enum: diff --git a/Documentation/devicetree/bindings/display/allwinner,sun8i-a83t-de2-mixer.yaml b/Documentation/devicetree/bindings/display/allwinner,sun8i-a83t-de2-mixer.yaml index 4f91eec26de9..cb243bc58ef7 100644 --- a/Documentation/devicetree/bindings/display/allwinner,sun8i-a83t-de2-mixer.yaml +++ b/Documentation/devicetree/bindings/display/allwinner,sun8i-a83t-de2-mixer.yaml @@ -19,6 +19,8 @@ properties: - allwinner,sun8i-r40-de2-mixer-0 - allwinner,sun8i-r40-de2-mixer-1 - allwinner,sun8i-v3s-de2-mixer + - allwinner,sun20i-d1-de2-mixer-0 + - allwinner,sun20i-d1-de2-mixer-1 - allwinner,sun50i-a64-de2-mixer-0 - allwinner,sun50i-a64-de2-mixer-1 - allwinner,sun50i-h6-de3-mixer-0 diff --git a/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml b/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml index 784b267635fb..cc32e2faed91 100644 --- a/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml +++ b/Documentation/devicetree/bindings/display/allwinner,sun8i-r40-tcon-top.yaml @@ -41,6 +41,7 @@ properties: compatible: enum: - allwinner,sun8i-r40-tcon-top + - allwinner,sun20i-d1-tcon-top - allwinner,sun50i-h6-tcon-top
reg: @@ -154,6 +155,39 @@ allOf: - port@2 - port@3
+ - if: + properties: + compatible: + contains: + const: allwinner,sun20i-d1-tcon-top + + then: + properties: + clocks: + minItems: 4 + maxItems: 4 + items: + - description: The TCON TOP interface clock + - description: The TCON TOP TV0 clock + - description: The TCON TOP TVE0 clock + - description: The TCON TOP MIPI DSI clock + + clock-names: + minItems: 4 + maxItems: 4 + items: + - const: bus + - const: tcon-tv0 + - const: tve0 + - const: dsi + + clock-output-names: + minItems: 2 + maxItems: 2 + items: + - description: TCON TV0 output clock name + - description: DSI output clock name + - if: properties: compatible:
On 11/04/2022 06:34, Samuel Holland wrote:
Allwinner D1 contains a display engine 2.0. It features two mixers, a TCON TOP (with DSI and HDMI), one TCON LCD, and one TCON TV.
Signed-off-by: Samuel Holland samuel@sholland.org
Reviewed-by: Krzysztof Kozlowski krzysztof.kozlowski@linaro.org
Best regards, Krzysztof
commit b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central place") added a platform device notifier that sets the DMA offset for all of the display engine frontend and backend devices.
The code applying the offset to DMA buffer physical addresses was then removed from the backend driver in commit 756668ba682e ("drm/sun4i: backend: Remove the MBUS quirks"), but the code subtracting PHYS_OFFSET was left in the frontend driver.
As a result, the offset was applied twice in the frontend driver. This likely went unnoticed because it only affects specific configurations (scaling or certain pixel formats) where the frontend is used, on boards with both one of these older SoCs and more than 1 GB of DRAM.
In addition, the references to PHYS_OFFSET prevent compiling the driver on architectures where PHYS_OFFSET is not defined.
Fixes: b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central place") Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun4i_frontend.c | 3 --- 1 file changed, 3 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun4i_frontend.c b/drivers/gpu/drm/sun4i/sun4i_frontend.c index 56ae38389db0..462fae73eae9 100644 --- a/drivers/gpu/drm/sun4i/sun4i_frontend.c +++ b/drivers/gpu/drm/sun4i/sun4i_frontend.c @@ -222,13 +222,11 @@ void sun4i_frontend_update_buffer(struct sun4i_frontend *frontend,
/* Set the physical address of the buffer in memory */ paddr = drm_fb_cma_get_gem_addr(fb, state, 0); - paddr -= PHYS_OFFSET; DRM_DEBUG_DRIVER("Setting buffer #0 address to %pad\n", &paddr); regmap_write(frontend->regs, SUN4I_FRONTEND_BUF_ADDR0_REG, paddr);
if (fb->format->num_planes > 1) { paddr = drm_fb_cma_get_gem_addr(fb, state, swap ? 2 : 1); - paddr -= PHYS_OFFSET; DRM_DEBUG_DRIVER("Setting buffer #1 address to %pad\n", &paddr); regmap_write(frontend->regs, SUN4I_FRONTEND_BUF_ADDR1_REG, paddr); @@ -236,7 +234,6 @@ void sun4i_frontend_update_buffer(struct sun4i_frontend *frontend,
if (fb->format->num_planes > 2) { paddr = drm_fb_cma_get_gem_addr(fb, state, swap ? 1 : 2); - paddr -= PHYS_OFFSET; DRM_DEBUG_DRIVER("Setting buffer #2 address to %pad\n", &paddr); regmap_write(frontend->regs, SUN4I_FRONTEND_BUF_ADDR2_REG, paddr);
Dne ponedeljek, 11. april 2022 ob 06:34:15 CEST je Samuel Holland napisal(a):
commit b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central place") added a platform device notifier that sets the DMA offset for all of the display engine frontend and backend devices.
The code applying the offset to DMA buffer physical addresses was then removed from the backend driver in commit 756668ba682e ("drm/sun4i: backend: Remove the MBUS quirks"), but the code subtracting PHYS_OFFSET was left in the frontend driver.
As a result, the offset was applied twice in the frontend driver. This likely went unnoticed because it only affects specific configurations (scaling or certain pixel formats) where the frontend is used, on boards with both one of these older SoCs and more than 1 GB of DRAM.
In addition, the references to PHYS_OFFSET prevent compiling the driver on architectures where PHYS_OFFSET is not defined.
Fixes: b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central
place")
Signed-off-by: Samuel Holland samuel@sholland.org
Good catch! Actually, people complained about non-working display on Cubietruck IIRC, which has 2 GB of RAM.
Did you test this on HW?
Reviewed-by: Jernej Skrabec jernej.skrabec@gmail.com
Best regards, Jernej
drivers/gpu/drm/sun4i/sun4i_frontend.c | 3 --- 1 file changed, 3 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun4i_frontend.c b/drivers/gpu/drm/sun4i/
sun4i_frontend.c
index 56ae38389db0..462fae73eae9 100644 --- a/drivers/gpu/drm/sun4i/sun4i_frontend.c +++ b/drivers/gpu/drm/sun4i/sun4i_frontend.c @@ -222,13 +222,11 @@ void sun4i_frontend_update_buffer(struct sun4i_frontend
*frontend,
/* Set the physical address of the buffer in memory */ paddr = drm_fb_cma_get_gem_addr(fb, state, 0);
paddr -= PHYS_OFFSET; DRM_DEBUG_DRIVER("Setting buffer #0 address to %pad\n", &paddr); regmap_write(frontend->regs, SUN4I_FRONTEND_BUF_ADDR0_REG, paddr);
if (fb->format->num_planes > 1) { paddr = drm_fb_cma_get_gem_addr(fb, state, swap ? 2 :
1);
DRM_DEBUG_DRIVER("Setting buffer #1 address to %pad\n",paddr -= PHYS_OFFSET;
&paddr);
regmap_write(frontend->regs,
SUN4I_FRONTEND_BUF_ADDR1_REG,
paddr);
@@ -236,7 +234,6 @@ void sun4i_frontend_update_buffer(struct sun4i_frontend
*frontend,
if (fb->format->num_planes > 2) { paddr = drm_fb_cma_get_gem_addr(fb, state, swap ? 1 :
2);
DRM_DEBUG_DRIVER("Setting buffer #2 address to %pad\n",paddr -= PHYS_OFFSET;
&paddr);
regmap_write(frontend->regs,
SUN4I_FRONTEND_BUF_ADDR2_REG,
paddr);
-- 2.35.1
On 4/11/22 10:37 AM, Jernej Škrabec wrote:
Dne ponedeljek, 11. april 2022 ob 06:34:15 CEST je Samuel Holland napisal(a):
commit b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central place") added a platform device notifier that sets the DMA offset for all of the display engine frontend and backend devices.
The code applying the offset to DMA buffer physical addresses was then removed from the backend driver in commit 756668ba682e ("drm/sun4i: backend: Remove the MBUS quirks"), but the code subtracting PHYS_OFFSET was left in the frontend driver.
As a result, the offset was applied twice in the frontend driver. This likely went unnoticed because it only affects specific configurations (scaling or certain pixel formats) where the frontend is used, on boards with both one of these older SoCs and more than 1 GB of DRAM.
In addition, the references to PHYS_OFFSET prevent compiling the driver on architectures where PHYS_OFFSET is not defined.
Fixes: b4bdc4fbf8d0 ("soc: sunxi: Deal with the MBUS DMA offsets in a central
place")
Signed-off-by: Samuel Holland samuel@sholland.org
Good catch! Actually, people complained about non-working display on Cubietruck IIRC, which has 2 GB of RAM.
Did you test this on HW?
The only DE1 board I have is an A33 tablet with 512 MB of DRAM. So while I boot-tested the patch, I am not able to verify if it has any real effect.
The reason for sending this is that folks ran in to compilation errors on RISC-V. And I was surprised to still see references to PHYS_OFFSET, since sunxi_mbus.c includes the frontend compatibles.
Regards, Samuel
Reviewed-by: Jernej Skrabec jernej.skrabec@gmail.com
Best regards, Jernej
Allwinner D1 is a RISC-V SoC which contains a DE 2.0 engine. Let's remove the dependency on a specific CPU architecture, so the driver can be built wherever ARCH_SUNXI is selected.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/sun4i/Kconfig b/drivers/gpu/drm/sun4i/Kconfig index befc5a80222d..3a43c436c74a 100644 --- a/drivers/gpu/drm/sun4i/Kconfig +++ b/drivers/gpu/drm/sun4i/Kconfig @@ -1,7 +1,7 @@ # SPDX-License-Identifier: GPL-2.0-only config DRM_SUN4I tristate "DRM Support for Allwinner A10 Display Engine" - depends on DRM && (ARM || ARM64) && COMMON_CLK + depends on DRM && COMMON_CLK depends on ARCH_SUNXI || COMPILE_TEST select DRM_GEM_CMA_HELPER select DRM_KMS_HELPER
Dne ponedeljek, 11. april 2022 ob 06:34:16 CEST je Samuel Holland napisal(a):
Allwinner D1 is a RISC-V SoC which contains a DE 2.0 engine. Let's remove the dependency on a specific CPU architecture, so the driver can be built wherever ARCH_SUNXI is selected.
Signed-off-by: Samuel Holland samuel@sholland.org
Acked-by: Jernej Skrabec jernej.skrabec@gmail.com
Best regards, Jernej
drivers/gpu/drm/sun4i/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/sun4i/Kconfig b/drivers/gpu/drm/sun4i/Kconfig index befc5a80222d..3a43c436c74a 100644 --- a/drivers/gpu/drm/sun4i/Kconfig +++ b/drivers/gpu/drm/sun4i/Kconfig @@ -1,7 +1,7 @@ # SPDX-License-Identifier: GPL-2.0-only config DRM_SUN4I tristate "DRM Support for Allwinner A10 Display Engine"
- depends on DRM && (ARM || ARM64) && COMMON_CLK
- depends on DRM && COMMON_CLK depends on ARCH_SUNXI || COMPILE_TEST select DRM_GEM_CMA_HELPER select DRM_KMS_HELPER
-- 2.35.1
Hi Samuel,
I love your patch! Yet something to improve:
[auto build test ERROR on sunxi/sunxi/for-next] [also build test ERROR on drm/drm-next linus/master v5.18-rc2 next-20220411] [cannot apply to mripard/sunxi/for-next] [If your patch is applied to the wrong git tree, kindly drop us a note. And when submitting patch, we suggest to use '--base' as documented in https://git-scm.com/docs/git-format-patch]
url: https://github.com/intel-lab-lkp/linux/commits/Samuel-Holland/drm-sun4i-Allw... base: https://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux.git sunxi/for-next config: alpha-allyesconfig (https://download.01.org/0day-ci/archive/20220412/202204120528.TRFC7Ywj-lkp@i...) compiler: alpha-linux-gcc (GCC) 11.2.0 reproduce (this is a W=1 build): wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross chmod +x ~/bin/make.cross # https://github.com/intel-lab-lkp/linux/commit/829dac8ee2cbb6d1b7bda1c513cc2a... git remote add linux-review https://github.com/intel-lab-lkp/linux git fetch --no-tags linux-review Samuel-Holland/drm-sun4i-Allwinner-D1-Display-Engine-2-0-Support/20220411-123701 git checkout 829dac8ee2cbb6d1b7bda1c513cc2ad1939fca53 # save the config file to linux build tree mkdir build_dir COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-11.2.0 make.cross O=build_dir ARCH=alpha SHELL=/bin/bash
If you fix the issue, kindly add following tag as appropriate Reported-by: kernel test robot lkp@intel.com
All errors (new ones prefixed by >>):
drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c: In function 'fifo_transfer':
drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:59:17: error: implicit declaration of function 'readsb'; did you mean 'readb'? [-Werror=implicit-function-declaration]
59 | readsb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); | ^~~~~~ | readb
drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:61:17: error: implicit declaration of function 'writesb'; did you mean 'writeb'? [-Werror=implicit-function-declaration]
61 | writesb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); | ^~~~~~~ | writeb cc1: some warnings being treated as errors
vim +59 drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c
f0a3dd33ba685b Jonathan Liu 2017-07-02 24 f0a3dd33ba685b Jonathan Liu 2017-07-02 25 static int fifo_transfer(struct sun4i_hdmi *hdmi, u8 *buf, int len, bool read) f0a3dd33ba685b Jonathan Liu 2017-07-02 26 { f0a3dd33ba685b Jonathan Liu 2017-07-02 27 /* f0a3dd33ba685b Jonathan Liu 2017-07-02 28 * 1 byte takes 9 clock cycles (8 bits + 1 ACK) = 90 us for 100 kHz f0a3dd33ba685b Jonathan Liu 2017-07-02 29 * clock. As clock rate is fixed, just round it up to 100 us. f0a3dd33ba685b Jonathan Liu 2017-07-02 30 */ f0a3dd33ba685b Jonathan Liu 2017-07-02 31 const unsigned long byte_time_ns = 100; f0a3dd33ba685b Jonathan Liu 2017-07-02 32 const u32 mask = SUN4I_HDMI_DDC_INT_STATUS_ERROR_MASK | f0a3dd33ba685b Jonathan Liu 2017-07-02 33 SUN4I_HDMI_DDC_INT_STATUS_FIFO_REQUEST | f0a3dd33ba685b Jonathan Liu 2017-07-02 34 SUN4I_HDMI_DDC_INT_STATUS_TRANSFER_COMPLETE; f0a3dd33ba685b Jonathan Liu 2017-07-02 35 u32 reg; 939d749ad6649c Chen-Yu Tsai 2017-10-10 36 /* 939d749ad6649c Chen-Yu Tsai 2017-10-10 37 * If threshold is inclusive, then the FIFO may only have 939d749ad6649c Chen-Yu Tsai 2017-10-10 38 * RX_THRESHOLD number of bytes, instead of RX_THRESHOLD + 1. 939d749ad6649c Chen-Yu Tsai 2017-10-10 39 */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 40 int read_len = RX_THRESHOLD + 939d749ad6649c Chen-Yu Tsai 2017-10-10 41 (hdmi->variant->ddc_fifo_thres_incl ? 0 : 1); f0a3dd33ba685b Jonathan Liu 2017-07-02 42 939d749ad6649c Chen-Yu Tsai 2017-10-10 43 /* 939d749ad6649c Chen-Yu Tsai 2017-10-10 44 * Limit transfer length by FIFO threshold or FIFO size. 939d749ad6649c Chen-Yu Tsai 2017-10-10 45 * For TX the threshold is for an empty FIFO. 939d749ad6649c Chen-Yu Tsai 2017-10-10 46 */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 47 len = min_t(int, len, read ? read_len : SUN4I_HDMI_DDC_FIFO_SIZE); f0a3dd33ba685b Jonathan Liu 2017-07-02 48 f0a3dd33ba685b Jonathan Liu 2017-07-02 49 /* Wait until error, FIFO request bit set or transfer complete */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 50 if (regmap_field_read_poll_timeout(hdmi->field_ddc_int_status, reg, 939d749ad6649c Chen-Yu Tsai 2017-10-10 51 reg & mask, len * byte_time_ns, 939d749ad6649c Chen-Yu Tsai 2017-10-10 52 100000)) f0a3dd33ba685b Jonathan Liu 2017-07-02 53 return -ETIMEDOUT; f0a3dd33ba685b Jonathan Liu 2017-07-02 54 f0a3dd33ba685b Jonathan Liu 2017-07-02 55 if (reg & SUN4I_HDMI_DDC_INT_STATUS_ERROR_MASK) f0a3dd33ba685b Jonathan Liu 2017-07-02 56 return -EIO; f0a3dd33ba685b Jonathan Liu 2017-07-02 57 f0a3dd33ba685b Jonathan Liu 2017-07-02 58 if (read) 939d749ad6649c Chen-Yu Tsai 2017-10-10 @59 readsb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); f0a3dd33ba685b Jonathan Liu 2017-07-02 60 else 939d749ad6649c Chen-Yu Tsai 2017-10-10 @61 writesb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); f0a3dd33ba685b Jonathan Liu 2017-07-02 62 939d749ad6649c Chen-Yu Tsai 2017-10-10 63 /* Clear FIFO request bit by forcing a write to that bit */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 64 regmap_field_force_write(hdmi->field_ddc_int_status, 939d749ad6649c Chen-Yu Tsai 2017-10-10 65 SUN4I_HDMI_DDC_INT_STATUS_FIFO_REQUEST); f0a3dd33ba685b Jonathan Liu 2017-07-02 66 f0a3dd33ba685b Jonathan Liu 2017-07-02 67 return len; f0a3dd33ba685b Jonathan Liu 2017-07-02 68 } f0a3dd33ba685b Jonathan Liu 2017-07-02 69
Hi Samuel,
I love your patch! Yet something to improve:
[auto build test ERROR on sunxi/sunxi/for-next] [also build test ERROR on drm/drm-next linus/master v5.18-rc2 next-20220412] [If your patch is applied to the wrong git tree, kindly drop us a note. And when submitting patch, we suggest to use '--base' as documented in https://git-scm.com/docs/git-format-patch]
url: https://github.com/intel-lab-lkp/linux/commits/Samuel-Holland/drm-sun4i-Allw... base: https://git.kernel.org/pub/scm/linux/kernel/git/sunxi/linux.git sunxi/for-next config: hexagon-allyesconfig (https://download.01.org/0day-ci/archive/20220412/202204121758.QeUxJKUh-lkp@i...) compiler: clang version 15.0.0 (https://github.com/llvm/llvm-project c6e83f560f06cdfe8aa47b248d8bdc58f947274b) reproduce (this is a W=1 build): wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross chmod +x ~/bin/make.cross # https://github.com/intel-lab-lkp/linux/commit/829dac8ee2cbb6d1b7bda1c513cc2a... git remote add linux-review https://github.com/intel-lab-lkp/linux git fetch --no-tags linux-review Samuel-Holland/drm-sun4i-Allwinner-D1-Display-Engine-2-0-Support/20220411-123701 git checkout 829dac8ee2cbb6d1b7bda1c513cc2ad1939fca53 # save the config file to linux build tree mkdir build_dir COMPILER_INSTALL_PATH=$HOME/0day COMPILER=clang make.cross W=1 O=build_dir ARCH=hexagon SHELL=/bin/bash
If you fix the issue, kindly add following tag as appropriate Reported-by: kernel test robot lkp@intel.com
All errors (new ones prefixed by >>):
drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:59:3: error: implicit declaration of function 'readsb' is invalid in C99 [-Werror,-Wimplicit-function-declaration]
readsb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); ^ drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:59:3: note: did you mean 'readb'? arch/hexagon/include/asm/io.h:83:18: note: 'readb' declared here static inline u8 readb(const volatile void __iomem *addr) ^
drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:61:3: error: implicit declaration of function 'writesb' is invalid in C99 [-Werror,-Wimplicit-function-declaration]
writesb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); ^ drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c:61:3: note: did you mean 'writeb'? arch/hexagon/include/asm/io.h:122:20: note: 'writeb' declared here static inline void writeb(u8 data, volatile void __iomem *addr) ^ 2 errors generated.
vim +/readsb +59 drivers/gpu/drm/sun4i/sun4i_hdmi_i2c.c
f0a3dd33ba685b Jonathan Liu 2017-07-02 24 f0a3dd33ba685b Jonathan Liu 2017-07-02 25 static int fifo_transfer(struct sun4i_hdmi *hdmi, u8 *buf, int len, bool read) f0a3dd33ba685b Jonathan Liu 2017-07-02 26 { f0a3dd33ba685b Jonathan Liu 2017-07-02 27 /* f0a3dd33ba685b Jonathan Liu 2017-07-02 28 * 1 byte takes 9 clock cycles (8 bits + 1 ACK) = 90 us for 100 kHz f0a3dd33ba685b Jonathan Liu 2017-07-02 29 * clock. As clock rate is fixed, just round it up to 100 us. f0a3dd33ba685b Jonathan Liu 2017-07-02 30 */ f0a3dd33ba685b Jonathan Liu 2017-07-02 31 const unsigned long byte_time_ns = 100; f0a3dd33ba685b Jonathan Liu 2017-07-02 32 const u32 mask = SUN4I_HDMI_DDC_INT_STATUS_ERROR_MASK | f0a3dd33ba685b Jonathan Liu 2017-07-02 33 SUN4I_HDMI_DDC_INT_STATUS_FIFO_REQUEST | f0a3dd33ba685b Jonathan Liu 2017-07-02 34 SUN4I_HDMI_DDC_INT_STATUS_TRANSFER_COMPLETE; f0a3dd33ba685b Jonathan Liu 2017-07-02 35 u32 reg; 939d749ad6649c Chen-Yu Tsai 2017-10-10 36 /* 939d749ad6649c Chen-Yu Tsai 2017-10-10 37 * If threshold is inclusive, then the FIFO may only have 939d749ad6649c Chen-Yu Tsai 2017-10-10 38 * RX_THRESHOLD number of bytes, instead of RX_THRESHOLD + 1. 939d749ad6649c Chen-Yu Tsai 2017-10-10 39 */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 40 int read_len = RX_THRESHOLD + 939d749ad6649c Chen-Yu Tsai 2017-10-10 41 (hdmi->variant->ddc_fifo_thres_incl ? 0 : 1); f0a3dd33ba685b Jonathan Liu 2017-07-02 42 939d749ad6649c Chen-Yu Tsai 2017-10-10 43 /* 939d749ad6649c Chen-Yu Tsai 2017-10-10 44 * Limit transfer length by FIFO threshold or FIFO size. 939d749ad6649c Chen-Yu Tsai 2017-10-10 45 * For TX the threshold is for an empty FIFO. 939d749ad6649c Chen-Yu Tsai 2017-10-10 46 */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 47 len = min_t(int, len, read ? read_len : SUN4I_HDMI_DDC_FIFO_SIZE); f0a3dd33ba685b Jonathan Liu 2017-07-02 48 f0a3dd33ba685b Jonathan Liu 2017-07-02 49 /* Wait until error, FIFO request bit set or transfer complete */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 50 if (regmap_field_read_poll_timeout(hdmi->field_ddc_int_status, reg, 939d749ad6649c Chen-Yu Tsai 2017-10-10 51 reg & mask, len * byte_time_ns, 939d749ad6649c Chen-Yu Tsai 2017-10-10 52 100000)) f0a3dd33ba685b Jonathan Liu 2017-07-02 53 return -ETIMEDOUT; f0a3dd33ba685b Jonathan Liu 2017-07-02 54 f0a3dd33ba685b Jonathan Liu 2017-07-02 55 if (reg & SUN4I_HDMI_DDC_INT_STATUS_ERROR_MASK) f0a3dd33ba685b Jonathan Liu 2017-07-02 56 return -EIO; f0a3dd33ba685b Jonathan Liu 2017-07-02 57 f0a3dd33ba685b Jonathan Liu 2017-07-02 58 if (read) 939d749ad6649c Chen-Yu Tsai 2017-10-10 @59 readsb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); f0a3dd33ba685b Jonathan Liu 2017-07-02 60 else 939d749ad6649c Chen-Yu Tsai 2017-10-10 @61 writesb(hdmi->base + hdmi->variant->ddc_fifo_reg, buf, len); f0a3dd33ba685b Jonathan Liu 2017-07-02 62 939d749ad6649c Chen-Yu Tsai 2017-10-10 63 /* Clear FIFO request bit by forcing a write to that bit */ 939d749ad6649c Chen-Yu Tsai 2017-10-10 64 regmap_field_force_write(hdmi->field_ddc_int_status, 939d749ad6649c Chen-Yu Tsai 2017-10-10 65 SUN4I_HDMI_DDC_INT_STATUS_FIFO_REQUEST); f0a3dd33ba685b Jonathan Liu 2017-07-02 66 f0a3dd33ba685b Jonathan Liu 2017-07-02 67 return len; f0a3dd33ba685b Jonathan Liu 2017-07-02 68 } f0a3dd33ba685b Jonathan Liu 2017-07-02 69
D1 changes the MMIO address offset for the CSC blocks in the first mixer. The ccsc field value is used as an index into the ccsc_base array; allocate the next available value to represent the new variant.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun8i_csc.c | 3 ++- drivers/gpu/drm/sun4i/sun8i_csc.h | 1 + drivers/gpu/drm/sun4i/sun8i_mixer.h | 6 ++++-- 3 files changed, 7 insertions(+), 3 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_csc.c b/drivers/gpu/drm/sun4i/sun8i_csc.c index 9bd62de0c288..1ed10c6447a3 100644 --- a/drivers/gpu/drm/sun4i/sun8i_csc.c +++ b/drivers/gpu/drm/sun4i/sun8i_csc.c @@ -8,9 +8,10 @@ #include "sun8i_csc.h" #include "sun8i_mixer.h"
-static const u32 ccsc_base[2][2] = { +static const u32 ccsc_base[][2] = { {CCSC00_OFFSET, CCSC01_OFFSET}, {CCSC10_OFFSET, CCSC11_OFFSET}, + {CCSC00_OFFSET, CCSC01_OFFSET_D1}, };
/* diff --git a/drivers/gpu/drm/sun4i/sun8i_csc.h b/drivers/gpu/drm/sun4i/sun8i_csc.h index 022cafa6c06c..bd54166b2bcc 100644 --- a/drivers/gpu/drm/sun4i/sun8i_csc.h +++ b/drivers/gpu/drm/sun4i/sun8i_csc.h @@ -13,6 +13,7 @@ struct sun8i_mixer; /* VI channel CSC units offsets */ #define CCSC00_OFFSET 0xAA050 #define CCSC01_OFFSET 0xFA050 +#define CCSC01_OFFSET_D1 0xFA000 #define CCSC10_OFFSET 0xA0000 #define CCSC11_OFFSET 0xF0000
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.h b/drivers/gpu/drm/sun4i/sun8i_mixer.h index 5b3fbee18671..22f1b7ef9225 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.h +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.h @@ -151,8 +151,10 @@ * scaler and 2 UI channels with scaler, bitmask would be 0xC. * @ccsc: select set of CCSC base addresses * Set value to 0 if this is first mixer or second mixer with VEP support. - * Set value to 1 if this is second mixer without VEP support. Other values - * are invalid. + * Set value to 1 if this is second mixer without VEP support. + * Set value to 2 if this is first mixer or second mixer with VEP support, + * and the SoC uses the MMIO layout found in the D1 SoC. + * Other values are invalid. * @mod_rate: module clock rate that needs to be set in order to have * a functional block. * @is_de3: true, if this is next gen display engine 3.0, false otherwise.
Dne ponedeljek, 11. april 2022 ob 06:34:17 CEST je Samuel Holland napisal(a):
D1 changes the MMIO address offset for the CSC blocks in the first mixer. The ccsc field value is used as an index into the ccsc_base array; allocate the next available value to represent the new variant.
Signed-off-by: Samuel Holland samuel@sholland.org
drivers/gpu/drm/sun4i/sun8i_csc.c | 3 ++- drivers/gpu/drm/sun4i/sun8i_csc.h | 1 + drivers/gpu/drm/sun4i/sun8i_mixer.h | 6 ++++-- 3 files changed, 7 insertions(+), 3 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_csc.c b/drivers/gpu/drm/sun4i/
sun8i_csc.c
index 9bd62de0c288..1ed10c6447a3 100644 --- a/drivers/gpu/drm/sun4i/sun8i_csc.c +++ b/drivers/gpu/drm/sun4i/sun8i_csc.c @@ -8,9 +8,10 @@ #include "sun8i_csc.h" #include "sun8i_mixer.h"
-static const u32 ccsc_base[2][2] = { +static const u32 ccsc_base[][2] = { {CCSC00_OFFSET, CCSC01_OFFSET}, {CCSC10_OFFSET, CCSC11_OFFSET},
- {CCSC00_OFFSET, CCSC01_OFFSET_D1},
};
/* diff --git a/drivers/gpu/drm/sun4i/sun8i_csc.h b/drivers/gpu/drm/sun4i/
sun8i_csc.h
index 022cafa6c06c..bd54166b2bcc 100644 --- a/drivers/gpu/drm/sun4i/sun8i_csc.h +++ b/drivers/gpu/drm/sun4i/sun8i_csc.h @@ -13,6 +13,7 @@ struct sun8i_mixer; /* VI channel CSC units offsets */ #define CCSC00_OFFSET 0xAA050 #define CCSC01_OFFSET 0xFA050 +#define CCSC01_OFFSET_D1 0xFA000 #define CCSC10_OFFSET 0xA0000 #define CCSC11_OFFSET 0xF0000
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.h b/drivers/gpu/drm/sun4i/
sun8i_mixer.h
index 5b3fbee18671..22f1b7ef9225 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.h +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.h @@ -151,8 +151,10 @@
- scaler and 2 UI channels with scaler, bitmask would be 0xC.
- @ccsc: select set of CCSC base addresses
- Set value to 0 if this is first mixer or second mixer with VEP
support.
- Set value to 1 if this is second mixer without VEP support. Other
values
- are invalid.
- Set value to 1 if this is second mixer without VEP support.
- Set value to 2 if this is first mixer or second mixer with VEP
support,
- and the SoC uses the MMIO layout found in the D1 SoC.
- Other values are invalid.
It would be better to introduce some kind of enum. Number 2 is completely arbitrary.
Best regards, Jernej
- @mod_rate: module clock rate that needs to be set in order to have
- a functional block.
- @is_de3: true, if this is next gen display engine 3.0, false otherwise.
-- 2.35.1
D1's mixer 1 has no UI layers, only a single VI layer. That means the mixer can only be used if the primary plane comes from this VI layer. Add the code to handle this case, setting the mixer's global registers in the same way as when the primary plane comes from a UI layer.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun8i_vi_layer.c | 36 +++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c b/drivers/gpu/drm/sun4i/sun8i_vi_layer.c index bb7c43036dfa..86212cb2098c 100644 --- a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c +++ b/drivers/gpu/drm/sun4i/sun8i_vi_layer.c @@ -146,6 +146,36 @@ static int sun8i_vi_layer_update_coord(struct sun8i_mixer *mixer, int channel, insize = SUN8I_MIXER_SIZE(src_w, src_h); outsize = SUN8I_MIXER_SIZE(dst_w, dst_h);
+ if (plane->type == DRM_PLANE_TYPE_PRIMARY) { + bool interlaced = false; + u32 val; + + DRM_DEBUG_DRIVER("Primary layer, updating global size W: %u H: %u\n", + dst_w, dst_h); + regmap_write(mixer->engine.regs, + SUN8I_MIXER_GLOBAL_SIZE, + outsize); + regmap_write(mixer->engine.regs, + SUN8I_MIXER_BLEND_OUTSIZE(bld_base), outsize); + + if (state->crtc) + interlaced = state->crtc->state->adjusted_mode.flags + & DRM_MODE_FLAG_INTERLACE; + + if (interlaced) + val = SUN8I_MIXER_BLEND_OUTCTL_INTERLACED; + else + val = 0; + + regmap_update_bits(mixer->engine.regs, + SUN8I_MIXER_BLEND_OUTCTL(bld_base), + SUN8I_MIXER_BLEND_OUTCTL_INTERLACED, + val); + + DRM_DEBUG_DRIVER("Switching display mixer interlaced mode %s\n", + interlaced ? "on" : "off"); + } + /* Set height and width */ DRM_DEBUG_DRIVER("Layer source offset X: %d Y: %d\n", (state->src.x1 >> 16) & ~(format->hsub - 1), @@ -542,6 +572,7 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct drm_device *drm, struct sun8i_mixer *mixer, int index) { + enum drm_plane_type type = DRM_PLANE_TYPE_OVERLAY; u32 supported_encodings, supported_ranges; unsigned int plane_cnt, format_count; struct sun8i_vi_layer *layer; @@ -560,12 +591,15 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct drm_device *drm, format_count = ARRAY_SIZE(sun8i_vi_layer_formats); }
+ if (!mixer->cfg->ui_num && index == 0) + type = DRM_PLANE_TYPE_PRIMARY; + /* possible crtcs are set later */ ret = drm_universal_plane_init(drm, &layer->plane, 0, &sun8i_vi_layer_funcs, formats, format_count, sun8i_layer_modifiers, - DRM_PLANE_TYPE_OVERLAY, NULL); + type, NULL); if (ret) { dev_err(drm->dev, "Couldn't initialize layer\n"); return ERR_PTR(ret);
Dne ponedeljek, 11. april 2022 ob 06:34:18 CEST je Samuel Holland napisal(a):
D1's mixer 1 has no UI layers, only a single VI layer. That means the mixer can only be used if the primary plane comes from this VI layer. Add the code to handle this case, setting the mixer's global registers in the same way as when the primary plane comes from a UI layer.
Signed-off-by: Samuel Holland samuel@sholland.org
drivers/gpu/drm/sun4i/sun8i_vi_layer.c | 36 +++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c b/drivers/gpu/drm/sun4i/
sun8i_vi_layer.c
index bb7c43036dfa..86212cb2098c 100644 --- a/drivers/gpu/drm/sun4i/sun8i_vi_layer.c +++ b/drivers/gpu/drm/sun4i/sun8i_vi_layer.c @@ -146,6 +146,36 @@ static int sun8i_vi_layer_update_coord(struct
sun8i_mixer *mixer, int channel,
insize = SUN8I_MIXER_SIZE(src_w, src_h); outsize = SUN8I_MIXER_SIZE(dst_w, dst_h);
- if (plane->type == DRM_PLANE_TYPE_PRIMARY) {
bool interlaced = false;
u32 val;
DRM_DEBUG_DRIVER("Primary layer, updating global size W:
%u H: %u\n",
dst_w, dst_h);
regmap_write(mixer->engine.regs,
SUN8I_MIXER_GLOBAL_SIZE,
outsize);
regmap_write(mixer->engine.regs,
SUN8I_MIXER_BLEND_OUTSIZE(bld_base),
outsize);
if (state->crtc)
interlaced = state->crtc->state-
adjusted_mode.flags
& DRM_MODE_FLAG_INTERLACE;
if (interlaced)
val = SUN8I_MIXER_BLEND_OUTCTL_INTERLACED;
else
val = 0;
regmap_update_bits(mixer->engine.regs,
SUN8I_MIXER_BLEND_OUTCTL(bld_base),
SUN8I_MIXER_BLEND_OUTCTL_INTERLACED,
val);
DRM_DEBUG_DRIVER("Switching display mixer interlaced
mode %s\n",
interlaced ? "on" : "off");
- }
Above code doesn't really belong to layer management and actually cause an issue when primary plane is reconfigured to cover only part of display. It should be executed at mode set time. I already wrote patches for that. Feel free to reuse them:
https://github.com/jernejsk/linux-1/commit/ bddb61cfa9c8ab70f5af6ed384fc7ffe159ac064 https://github.com/jernejsk/linux-1/commit/ 3320184b88df81b7d3d2b375db899442e1085519 https://github.com/jernejsk/linux-1/commit/ 05a04d721ae31dbff0432606892ec94b6a63b8bc
FWIW, I have other clean ups stacked here: https://github.com/jernejsk/ linux-1/commits/hdmi-yuv420
Best regards, Jernej
/* Set height and width */ DRM_DEBUG_DRIVER("Layer source offset X: %d Y: %d\n", (state->src.x1 >> 16) & ~(format->hsub -
1),
@@ -542,6 +572,7 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct
drm_device *drm,
struct
sun8i_mixer *mixer,
int index)
{
- enum drm_plane_type type = DRM_PLANE_TYPE_OVERLAY; u32 supported_encodings, supported_ranges; unsigned int plane_cnt, format_count; struct sun8i_vi_layer *layer;
@@ -560,12 +591,15 @@ struct sun8i_vi_layer *sun8i_vi_layer_init_one(struct
drm_device *drm,
format_count = ARRAY_SIZE(sun8i_vi_layer_formats);
}
- if (!mixer->cfg->ui_num && index == 0)
type = DRM_PLANE_TYPE_PRIMARY;
- /* possible crtcs are set later */ ret = drm_universal_plane_init(drm, &layer->plane, 0, &sun8i_vi_layer_funcs, formats, format_count, sun8i_layer_modifiers,
DRM_PLANE_TYPE_OVERLAY,
NULL);
if (ret) { dev_err(drm->dev, "Couldn't initialize layer\n"); return ERR_PTR(ret);type, NULL);
-- 2.35.1
D1 has a display engine with the usual pair of mixers, albeit with relatively few layers. In fact, D1 appears to be the first SoC to have a mixer without any UI layers. Add support for these new variants.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun8i_mixer.c | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+)
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.c b/drivers/gpu/drm/sun4i/sun8i_mixer.c index f5e8aeaa3cdf..49c0d17c6f0a 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.c +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.c @@ -585,6 +585,24 @@ static const struct sun8i_mixer_cfg sun8i_v3s_mixer_cfg = { .mod_rate = 150000000, };
+static const struct sun8i_mixer_cfg sun20i_d1_mixer0_cfg = { + .ccsc = 2, + .mod_rate = 297000000, + .scaler_mask = 0x3, + .scanline_yuv = 2048, + .ui_num = 1, + .vi_num = 1, +}; + +static const struct sun8i_mixer_cfg sun20i_d1_mixer1_cfg = { + .ccsc = 1, + .mod_rate = 297000000, + .scaler_mask = 0x1, + .scanline_yuv = 1024, + .ui_num = 0, + .vi_num = 1, +}; + static const struct sun8i_mixer_cfg sun50i_a64_mixer0_cfg = { .ccsc = 0, .mod_rate = 297000000, @@ -638,6 +656,14 @@ static const struct of_device_id sun8i_mixer_of_table[] = { .compatible = "allwinner,sun8i-v3s-de2-mixer", .data = &sun8i_v3s_mixer_cfg, }, + { + .compatible = "allwinner,sun20i-d1-de2-mixer-0", + .data = &sun20i_d1_mixer0_cfg, + }, + { + .compatible = "allwinner,sun20i-d1-de2-mixer-1", + .data = &sun20i_d1_mixer1_cfg, + }, { .compatible = "allwinner,sun50i-a64-de2-mixer-0", .data = &sun50i_a64_mixer0_cfg,
Dne ponedeljek, 11. april 2022 ob 06:34:19 CEST je Samuel Holland napisal(a):
D1 has a display engine with the usual pair of mixers, albeit with relatively few layers. In fact, D1 appears to be the first SoC to have a mixer without any UI layers. Add support for these new variants.
Signed-off-by: Samuel Holland samuel@sholland.org
Acked-by: Jernej Skrabec jernej.skrabec@gmail.com
Best regards, Jernej
drivers/gpu/drm/sun4i/sun8i_mixer.c | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+)
diff --git a/drivers/gpu/drm/sun4i/sun8i_mixer.c b/drivers/gpu/drm/sun4i/
sun8i_mixer.c
index f5e8aeaa3cdf..49c0d17c6f0a 100644 --- a/drivers/gpu/drm/sun4i/sun8i_mixer.c +++ b/drivers/gpu/drm/sun4i/sun8i_mixer.c @@ -585,6 +585,24 @@ static const struct sun8i_mixer_cfg sun8i_v3s_mixer_cfg
= {
.mod_rate = 150000000, };
+static const struct sun8i_mixer_cfg sun20i_d1_mixer0_cfg = {
- .ccsc = 2,
- .mod_rate = 297000000,
- .scaler_mask = 0x3,
- .scanline_yuv = 2048,
- .ui_num = 1,
- .vi_num = 1,
+};
+static const struct sun8i_mixer_cfg sun20i_d1_mixer1_cfg = {
- .ccsc = 1,
- .mod_rate = 297000000,
- .scaler_mask = 0x1,
- .scanline_yuv = 1024,
- .ui_num = 0,
- .vi_num = 1,
+};
static const struct sun8i_mixer_cfg sun50i_a64_mixer0_cfg = { .ccsc = 0, .mod_rate = 297000000, @@ -638,6 +656,14 @@ static const struct of_device_id sun8i_mixer_of_table[]
= {
.compatible = "allwinner,sun8i-v3s-de2-mixer", .data = &sun8i_v3s_mixer_cfg,
},
- {
.compatible = "allwinner,sun20i-d1-de2-mixer-0",
.data = &sun20i_d1_mixer0_cfg,
- },
- {
.compatible = "allwinner,sun20i-d1-de2-mixer-1",
.data = &sun20i_d1_mixer1_cfg,
- }, { .compatible = "allwinner,sun50i-a64-de2-mixer-0", .data = &sun50i_a64_mixer0_cfg,
-- 2.35.1
D1 has a TCON TOP with TCON TV0 and DSI, but no TCON TV1. This puts the DSI clock name at index 1 in clock-output-names. Support this by only incrementing the index for clocks that are actually supported.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun8i_tcon_top.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-)
diff --git a/drivers/gpu/drm/sun4i/sun8i_tcon_top.c b/drivers/gpu/drm/sun4i/sun8i_tcon_top.c index 1b9b8b48f4a7..da97682b6835 100644 --- a/drivers/gpu/drm/sun4i/sun8i_tcon_top.c +++ b/drivers/gpu/drm/sun4i/sun8i_tcon_top.c @@ -189,22 +189,23 @@ static int sun8i_tcon_top_bind(struct device *dev, struct device *master, * if TVE is active on each TCON TV. If it is, mux should be switched * to TVE clock parent. */ + i = 0; clk_data->hws[CLK_TCON_TOP_TV0] = sun8i_tcon_top_register_gate(dev, "tcon-tv0", regs, &tcon_top->reg_lock, - TCON_TOP_TCON_TV0_GATE, 0); + TCON_TOP_TCON_TV0_GATE, i++);
if (quirks->has_tcon_tv1) clk_data->hws[CLK_TCON_TOP_TV1] = sun8i_tcon_top_register_gate(dev, "tcon-tv1", regs, &tcon_top->reg_lock, - TCON_TOP_TCON_TV1_GATE, 1); + TCON_TOP_TCON_TV1_GATE, i++);
if (quirks->has_dsi) clk_data->hws[CLK_TCON_TOP_DSI] = sun8i_tcon_top_register_gate(dev, "dsi", regs, &tcon_top->reg_lock, - TCON_TOP_TCON_DSI_GATE, 2); + TCON_TOP_TCON_DSI_GATE, i++);
for (i = 0; i < CLK_NUM; i++) if (IS_ERR(clk_data->hws[i])) { @@ -272,6 +273,10 @@ static const struct sun8i_tcon_top_quirks sun8i_r40_tcon_top_quirks = { .has_dsi = true, };
+static const struct sun8i_tcon_top_quirks sun20i_d1_tcon_top_quirks = { + .has_dsi = true, +}; + static const struct sun8i_tcon_top_quirks sun50i_h6_tcon_top_quirks = { /* Nothing special */ }; @@ -282,6 +287,10 @@ const struct of_device_id sun8i_tcon_top_of_table[] = { .compatible = "allwinner,sun8i-r40-tcon-top", .data = &sun8i_r40_tcon_top_quirks }, + { + .compatible = "allwinner,sun20i-d1-tcon-top", + .data = &sun20i_d1_tcon_top_quirks + }, { .compatible = "allwinner,sun50i-h6-tcon-top", .data = &sun50i_h6_tcon_top_quirks
D1 has a TCON TOP, so its quirks are similar to those for the R40 TCONs. While there are some register changes, the part of the TCON TV supported by the driver matches the R40 quirks, so that quirks structure can be reused. D1 has the first supported TCON LCD with a TCON TOP, so the TCON LCD needs a new quirks structure.
D1's TCON LCD hardware supports LVDS; in fact it provides dual-link LVDS from a single TCON. However, it comes with a brand new LVDS PHY. Since this PHY has not been tested, leave out LVDS driver support for now.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun4i_tcon.c | 8 ++++++++ 1 file changed, 8 insertions(+)
diff --git a/drivers/gpu/drm/sun4i/sun4i_tcon.c b/drivers/gpu/drm/sun4i/sun4i_tcon.c index 88db2d2a9336..2ee158aaeb9e 100644 --- a/drivers/gpu/drm/sun4i/sun4i_tcon.c +++ b/drivers/gpu/drm/sun4i/sun4i_tcon.c @@ -1542,6 +1542,12 @@ static const struct sun4i_tcon_quirks sun9i_a80_tcon_tv_quirks = { .needs_edp_reset = true, };
+static const struct sun4i_tcon_quirks sun20i_d1_lcd_quirks = { + .has_channel_0 = true, + .dclk_min_div = 1, + .set_mux = sun8i_r40_tcon_tv_set_mux, +}; + /* sun4i_drv uses this list to check if a device node is a TCON */ const struct of_device_id sun4i_tcon_of_table[] = { { .compatible = "allwinner,sun4i-a10-tcon", .data = &sun4i_a10_quirks }, @@ -1559,6 +1565,8 @@ const struct of_device_id sun4i_tcon_of_table[] = { { .compatible = "allwinner,sun8i-v3s-tcon", .data = &sun8i_v3s_quirks }, { .compatible = "allwinner,sun9i-a80-tcon-lcd", .data = &sun9i_a80_tcon_lcd_quirks }, { .compatible = "allwinner,sun9i-a80-tcon-tv", .data = &sun9i_a80_tcon_tv_quirks }, + { .compatible = "allwinner,sun20i-d1-tcon-lcd", .data = &sun20i_d1_lcd_quirks }, + { .compatible = "allwinner,sun20i-d1-tcon-tv", .data = &sun8i_r40_tv_quirks }, { } }; MODULE_DEVICE_TABLE(of, sun4i_tcon_of_table);
Now that the various blocks in the D1 display engine pipeline are supported, we can enable the overall engine.
Signed-off-by: Samuel Holland samuel@sholland.org ---
drivers/gpu/drm/sun4i/sun4i_drv.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/gpu/drm/sun4i/sun4i_drv.c b/drivers/gpu/drm/sun4i/sun4i_drv.c index 6a9ba8a77c77..275f7e4a03ae 100644 --- a/drivers/gpu/drm/sun4i/sun4i_drv.c +++ b/drivers/gpu/drm/sun4i/sun4i_drv.c @@ -418,6 +418,7 @@ static const struct of_device_id sun4i_drv_of_table[] = { { .compatible = "allwinner,sun8i-r40-display-engine" }, { .compatible = "allwinner,sun8i-v3s-display-engine" }, { .compatible = "allwinner,sun9i-a80-display-engine" }, + { .compatible = "allwinner,sun20i-d1-display-engine" }, { .compatible = "allwinner,sun50i-a64-display-engine" }, { .compatible = "allwinner,sun50i-h6-display-engine" }, { }
Dne ponedeljek, 11. april 2022 ob 06:34:22 CEST je Samuel Holland napisal(a):
Now that the various blocks in the D1 display engine pipeline are supported, we can enable the overall engine.
Signed-off-by: Samuel Holland samuel@sholland.org
Acked-by: Jernej Skrabec jernej.skrabec@gmail.com
Best regards, Jernej
drivers/gpu/drm/sun4i/sun4i_drv.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/gpu/drm/sun4i/sun4i_drv.c b/drivers/gpu/drm/sun4i/
sun4i_drv.c
index 6a9ba8a77c77..275f7e4a03ae 100644 --- a/drivers/gpu/drm/sun4i/sun4i_drv.c +++ b/drivers/gpu/drm/sun4i/sun4i_drv.c @@ -418,6 +418,7 @@ static const struct of_device_id sun4i_drv_of_table[] =
{
{ .compatible = "allwinner,sun8i-r40-display-engine" }, { .compatible = "allwinner,sun8i-v3s-display-engine" }, { .compatible = "allwinner,sun9i-a80-display-engine" },
- { .compatible = "allwinner,sun20i-d1-display-engine" }, { .compatible = "allwinner,sun50i-a64-display-engine" }, { .compatible = "allwinner,sun50i-h6-display-engine" }, { }
-- 2.35.1
dri-devel@lists.freedesktop.org