summaryrefslogtreecommitdiff
path: root/drivers/gpu/drm/msm/disp/mdp4
diff options
context:
space:
mode:
authorDave Airlie <airlied@redhat.com>2023-10-23 11:29:18 +0300
committerDave Airlie <airlied@redhat.com>2023-10-23 11:29:18 +0300
commit3f5ba636d6987ddffeaa056dea1c524da63912f3 (patch)
tree7e30f36deb4a566fdb4b24113d486633b694d270 /drivers/gpu/drm/msm/disp/mdp4
parent7cd62eab9babd1fed9c497141650b31168f4f430 (diff)
parentb08d26dac1a1075c874f40ee02ec8ddc39e20146 (diff)
downloadlinux-3f5ba636d6987ddffeaa056dea1c524da63912f3.tar.xz
Merge tag 'drm-msm-next-2023-10-17' of https://gitlab.freedesktop.org/drm/msm into drm-next
Updates for v6.7 DP: - use existing helpers for DPCD handling instead of open-coded functions - set the subconnector type according to the plugged cable / dongle skip validity check for DP CTS EDID checksum DPU: - continued migration of feature flags to use core revision checks - reworked interrupts code to use '0' as NO_IRQ, removed raw IRQ indices from log / trace output gpu: - a7xx support (a730, a740) - fixes and additional speedbins for a635, a643 core: - decouple msm_drv from kms to more cleanly support headless devices (like imx5+a2xx) From: Rob Clark <robdclark@gmail.com> Link: https://patchwork.freedesktop.org/patch/msgid/CAF6AEGvzkBL2_OgyOeP_b6rVEjrNdfm8jcKzaB04HqHyT5jYwA@mail.gmail.com Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/msm/disp/mdp4')
-rw-r--r--drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c112
1 files changed, 54 insertions, 58 deletions
diff --git a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c
index e5012fa6771f..4ba1cb74ad76 100644
--- a/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c
+++ b/drivers/gpu/drm/msm/disp/mdp4/mdp4_kms.c
@@ -135,8 +135,6 @@ static void mdp4_destroy(struct msm_kms *kms)
pm_runtime_disable(dev);
mdp_kms_destroy(&mdp4_kms->base);
-
- kfree(mdp4_kms);
}
static const struct mdp_kms_funcs kms_funcs = {
@@ -380,56 +378,27 @@ static int mdp4_kms_init(struct drm_device *dev)
{
struct platform_device *pdev = to_platform_device(dev->dev);
struct msm_drm_private *priv = dev->dev_private;
- struct mdp4_kms *mdp4_kms;
+ struct mdp4_kms *mdp4_kms = to_mdp4_kms(to_mdp_kms(priv->kms));
struct msm_kms *kms = NULL;
struct msm_mmu *mmu;
struct msm_gem_address_space *aspace;
- int irq, ret;
+ int ret;
u32 major, minor;
unsigned long max_clk;
/* TODO: Chips that aren't apq8064 have a 200 Mhz max_clk */
max_clk = 266667000;
- mdp4_kms = kzalloc(sizeof(*mdp4_kms), GFP_KERNEL);
- if (!mdp4_kms) {
- DRM_DEV_ERROR(dev->dev, "failed to allocate kms\n");
- return -ENOMEM;
- }
-
ret = mdp_kms_init(&mdp4_kms->base, &kms_funcs);
if (ret) {
DRM_DEV_ERROR(dev->dev, "failed to init kms\n");
goto fail;
}
- priv->kms = &mdp4_kms->base.base;
kms = priv->kms;
mdp4_kms->dev = dev;
- mdp4_kms->mmio = msm_ioremap(pdev, NULL);
- if (IS_ERR(mdp4_kms->mmio)) {
- ret = PTR_ERR(mdp4_kms->mmio);
- goto fail;
- }
-
- irq = platform_get_irq(pdev, 0);
- if (irq < 0) {
- ret = irq;
- goto fail;
- }
-
- kms->irq = irq;
-
- /* NOTE: driver for this regulator still missing upstream.. use
- * _get_exclusive() and ignore the error if it does not exist
- * (and hope that the bootloader left it on for us)
- */
- mdp4_kms->vdd = devm_regulator_get_exclusive(&pdev->dev, "vdd");
- if (IS_ERR(mdp4_kms->vdd))
- mdp4_kms->vdd = NULL;
-
if (mdp4_kms->vdd) {
ret = regulator_enable(mdp4_kms->vdd);
if (ret) {
@@ -438,24 +407,6 @@ static int mdp4_kms_init(struct drm_device *dev)
}
}
- mdp4_kms->clk = devm_clk_get(&pdev->dev, "core_clk");
- if (IS_ERR(mdp4_kms->clk)) {
- DRM_DEV_ERROR(dev->dev, "failed to get core_clk\n");
- ret = PTR_ERR(mdp4_kms->clk);
- goto fail;
- }
-
- mdp4_kms->pclk = devm_clk_get(&pdev->dev, "iface_clk");
- if (IS_ERR(mdp4_kms->pclk))
- mdp4_kms->pclk = NULL;
-
- mdp4_kms->axi_clk = devm_clk_get(&pdev->dev, "bus_clk");
- if (IS_ERR(mdp4_kms->axi_clk)) {
- DRM_DEV_ERROR(dev->dev, "failed to get axi_clk\n");
- ret = PTR_ERR(mdp4_kms->axi_clk);
- goto fail;
- }
-
clk_set_rate(mdp4_kms->clk, max_clk);
read_mdp_hw_revision(mdp4_kms, &major, &minor);
@@ -470,10 +421,9 @@ static int mdp4_kms_init(struct drm_device *dev)
mdp4_kms->rev = minor;
if (mdp4_kms->rev >= 2) {
- mdp4_kms->lut_clk = devm_clk_get(&pdev->dev, "lut_clk");
- if (IS_ERR(mdp4_kms->lut_clk)) {
+ if (!mdp4_kms->lut_clk) {
DRM_DEV_ERROR(dev->dev, "failed to get lut_clk\n");
- ret = PTR_ERR(mdp4_kms->lut_clk);
+ ret = -ENODEV;
goto fail;
}
clk_set_rate(mdp4_kms->lut_clk, max_clk);
@@ -551,13 +501,59 @@ fail:
}
static const struct dev_pm_ops mdp4_pm_ops = {
- .prepare = msm_pm_prepare,
- .complete = msm_pm_complete,
+ .prepare = msm_kms_pm_prepare,
+ .complete = msm_kms_pm_complete,
};
static int mdp4_probe(struct platform_device *pdev)
{
- return msm_drv_probe(&pdev->dev, mdp4_kms_init);
+ struct device *dev = &pdev->dev;
+ struct mdp4_kms *mdp4_kms;
+ int irq;
+
+ mdp4_kms = devm_kzalloc(dev, sizeof(*mdp4_kms), GFP_KERNEL);
+ if (!mdp4_kms)
+ return dev_err_probe(dev, -ENOMEM, "failed to allocate kms\n");
+
+ mdp4_kms->mmio = msm_ioremap(pdev, NULL);
+ if (IS_ERR(mdp4_kms->mmio))
+ return PTR_ERR(mdp4_kms->mmio);
+
+ irq = platform_get_irq(pdev, 0);
+ if (irq < 0)
+ return dev_err_probe(dev, irq, "failed to get irq\n");
+
+ mdp4_kms->base.base.irq = irq;
+
+ /* NOTE: driver for this regulator still missing upstream.. use
+ * _get_exclusive() and ignore the error if it does not exist
+ * (and hope that the bootloader left it on for us)
+ */
+ mdp4_kms->vdd = devm_regulator_get_exclusive(&pdev->dev, "vdd");
+ if (IS_ERR(mdp4_kms->vdd))
+ mdp4_kms->vdd = NULL;
+
+ mdp4_kms->clk = devm_clk_get(&pdev->dev, "core_clk");
+ if (IS_ERR(mdp4_kms->clk))
+ return dev_err_probe(dev, PTR_ERR(mdp4_kms->clk), "failed to get core_clk\n");
+
+ mdp4_kms->pclk = devm_clk_get(&pdev->dev, "iface_clk");
+ if (IS_ERR(mdp4_kms->pclk))
+ mdp4_kms->pclk = NULL;
+
+ mdp4_kms->axi_clk = devm_clk_get(&pdev->dev, "bus_clk");
+ if (IS_ERR(mdp4_kms->axi_clk))
+ return dev_err_probe(dev, PTR_ERR(mdp4_kms->axi_clk), "failed to get axi_clk\n");
+
+ /*
+ * This is required for revn >= 2. Handle errors here and let the kms
+ * init bail out if the clock is not provided.
+ */
+ mdp4_kms->lut_clk = devm_clk_get_optional(&pdev->dev, "lut_clk");
+ if (IS_ERR(mdp4_kms->lut_clk))
+ return dev_err_probe(dev, PTR_ERR(mdp4_kms->lut_clk), "failed to get lut_clk\n");
+
+ return msm_drv_probe(&pdev->dev, mdp4_kms_init, &mdp4_kms->base.base);
}
static void mdp4_remove(struct platform_device *pdev)
@@ -574,7 +570,7 @@ MODULE_DEVICE_TABLE(of, mdp4_dt_match);
static struct platform_driver mdp4_platform_driver = {
.probe = mdp4_probe,
.remove_new = mdp4_remove,
- .shutdown = msm_drv_shutdown,
+ .shutdown = msm_kms_shutdown,
.driver = {
.name = "mdp4",
.of_match_table = mdp4_dt_match,