mirror of
https://github.com/openwrt/openwrt.git
synced 2024-12-29 10:08:59 +00:00
7d7aa2fd92
This change makes the names of Broadcom targets consistent by using the common notation based on SoC/CPU ID (which is used internally anyway), bcmXXXX instead of brcmXXXX. This is even used for target TITLE in make menuconfig already, only the short target name used brcm so far. Despite, since subtargets range from bcm2708 to bcm2711, it seems appropriate to use bcm27xx instead of bcm2708 (again, as already done for BOARDNAME). This also renames the packages brcm2708-userland and brcm2708-gpu-fw. Signed-off-by: Adrian Schmutzler <freifunk@adrianschmutzler.de> Acked-by: Álvaro Fernández Rojas <noltari@gmail.com>
135 lines
4.2 KiB
Diff
135 lines
4.2 KiB
Diff
From 23e6a2c2d33050255c76a499ea080e5279d6edfc Mon Sep 17 00:00:00 2001
|
|
From: Dave Stevenson <dave.stevenson@raspberrypi.org>
|
|
Date: Thu, 30 May 2019 13:56:15 +0100
|
|
Subject: [PATCH] drm/vc4: fkms to query the VPU for HDMI clock limits
|
|
|
|
The VPU has configured clocks for 4k (or not) via config.txt,
|
|
and will limit the choice of video modes based on that.
|
|
Make fkms query it for these limits too to avoid selecting modes
|
|
that can not be handled by the current clock setup.
|
|
|
|
Signed-off-by: Dave Stevenson <dave.stevenson@raspberrypi.org>
|
|
---
|
|
drivers/gpu/drm/vc4/vc4_drv.h | 1 +
|
|
drivers/gpu/drm/vc4/vc4_firmware_kms.c | 48 ++++++++++++++++++++++
|
|
include/soc/bcm2835/raspberrypi-firmware.h | 1 +
|
|
3 files changed, 50 insertions(+)
|
|
|
|
--- a/drivers/gpu/drm/vc4/vc4_drv.h
|
|
+++ b/drivers/gpu/drm/vc4/vc4_drv.h
|
|
@@ -77,6 +77,7 @@ struct vc4_dev {
|
|
struct vc4_dsi *dsi1;
|
|
struct vc4_vec *vec;
|
|
struct vc4_txp *txp;
|
|
+ struct vc4_fkms *fkms;
|
|
|
|
struct vc4_hang_state *hang_state;
|
|
|
|
--- a/drivers/gpu/drm/vc4/vc4_firmware_kms.c
|
|
+++ b/drivers/gpu/drm/vc4/vc4_firmware_kms.c
|
|
@@ -29,6 +29,14 @@
|
|
#include "vc_image_types.h"
|
|
#include <soc/bcm2835/raspberrypi-firmware.h>
|
|
|
|
+struct get_display_cfg {
|
|
+ u32 max_pixel_clock[2]; //Max pixel clock for each display
|
|
+};
|
|
+
|
|
+struct vc4_fkms {
|
|
+ struct get_display_cfg cfg;
|
|
+};
|
|
+
|
|
#define PLANES_PER_CRTC 3
|
|
|
|
struct set_plane {
|
|
@@ -794,6 +802,11 @@ static void vc4_crtc_enable(struct drm_c
|
|
static enum drm_mode_status
|
|
vc4_crtc_mode_valid(struct drm_crtc *crtc, const struct drm_display_mode *mode)
|
|
{
|
|
+ struct vc4_crtc *vc4_crtc = to_vc4_crtc(crtc);
|
|
+ struct drm_device *dev = crtc->dev;
|
|
+ struct vc4_dev *vc4 = to_vc4_dev(dev);
|
|
+ struct vc4_fkms *fkms = vc4->fkms;
|
|
+
|
|
/* Do not allow doublescan modes from user space */
|
|
if (mode->flags & DRM_MODE_FLAG_DBLSCAN) {
|
|
DRM_DEBUG_KMS("[CRTC:%d] Doublescan mode rejected.\n",
|
|
@@ -801,6 +814,22 @@ vc4_crtc_mode_valid(struct drm_crtc *crt
|
|
return MODE_NO_DBLESCAN;
|
|
}
|
|
|
|
+ /* Limit the pixel clock based on the HDMI clock limits from the
|
|
+ * firmware
|
|
+ */
|
|
+ switch (vc4_crtc->display_number) {
|
|
+ case 2: /* HDMI0 */
|
|
+ if (fkms->cfg.max_pixel_clock[0] &&
|
|
+ mode->clock > fkms->cfg.max_pixel_clock[0])
|
|
+ return MODE_CLOCK_HIGH;
|
|
+ break;
|
|
+ case 7: /* HDMI1 */
|
|
+ if (fkms->cfg.max_pixel_clock[1] &&
|
|
+ mode->clock > fkms->cfg.max_pixel_clock[1])
|
|
+ return MODE_CLOCK_HIGH;
|
|
+ break;
|
|
+ }
|
|
+
|
|
/* Limit the pixel clock until we can get dynamic HDMI 2.0 scrambling
|
|
* working.
|
|
*/
|
|
@@ -1301,11 +1330,16 @@ static int vc4_fkms_bind(struct device *
|
|
struct device_node *firmware_node;
|
|
struct vc4_crtc **crtc_list;
|
|
u32 num_displays, display_num;
|
|
+ struct vc4_fkms *fkms;
|
|
int ret;
|
|
u32 display_id;
|
|
|
|
vc4->firmware_kms = true;
|
|
|
|
+ fkms = devm_kzalloc(dev, sizeof(*fkms), GFP_KERNEL);
|
|
+ if (!fkms)
|
|
+ return -ENOMEM;
|
|
+
|
|
/* firmware kms doesn't have precise a scanoutpos implementation, so
|
|
* we can't do the precise vblank timestamp mode.
|
|
*/
|
|
@@ -1334,6 +1368,18 @@ static int vc4_fkms_bind(struct device *
|
|
ret = 0;
|
|
}
|
|
|
|
+ ret = rpi_firmware_property(vc4->firmware,
|
|
+ RPI_FIRMWARE_GET_DISPLAY_CFG,
|
|
+ &fkms->cfg, sizeof(fkms->cfg));
|
|
+
|
|
+ if (ret)
|
|
+ return -EINVAL;
|
|
+ /* The firmware works in Hz. This will be compared against kHz, so div
|
|
+ * 1000 now rather than multiple times later.
|
|
+ */
|
|
+ fkms->cfg.max_pixel_clock[0] /= 1000;
|
|
+ fkms->cfg.max_pixel_clock[1] /= 1000;
|
|
+
|
|
/* Allocate a list, with space for a NULL on the end */
|
|
crtc_list = devm_kzalloc(dev, sizeof(crtc_list) * (num_displays + 1),
|
|
GFP_KERNEL);
|
|
@@ -1375,6 +1421,8 @@ static int vc4_fkms_bind(struct device *
|
|
DRM_WARN("No displays found. Consider forcing hotplug if HDMI is attached\n");
|
|
}
|
|
|
|
+ vc4->fkms = fkms;
|
|
+
|
|
platform_set_drvdata(pdev, crtc_list);
|
|
|
|
return 0;
|
|
--- a/include/soc/bcm2835/raspberrypi-firmware.h
|
|
+++ b/include/soc/bcm2835/raspberrypi-firmware.h
|
|
@@ -153,6 +153,7 @@ enum rpi_firmware_property_tag {
|
|
RPI_FIRMWARE_SET_PLANE = 0x00048015,
|
|
RPI_FIRMWARE_GET_DISPLAY_TIMING = 0x00040017,
|
|
RPI_FIRMWARE_SET_TIMING = 0x00048017,
|
|
+ RPI_FIRMWARE_GET_DISPLAY_CFG = 0x00040018,
|
|
|
|
RPI_FIRMWARE_GET_COMMAND_LINE = 0x00050001,
|
|
RPI_FIRMWARE_GET_DMA_CHANNELS = 0x00060001,
|