Re: [PATCH] drm/komeda: Adds power management support
On Tue, Oct 8, 2019 at 1:47 PM Sean Paul wrote: > > On Mon, Sep 23, 2019 at 01:59:25AM +, Lowry Li (Arm Technology China) > wrote: > > From: "Lowry Li (Arm Technology China)" > > > > Adds system power management support in KMS kernel driver. > > > > Depends on: > > https://patchwork.freedesktop.org/series/62377/ > > > > Changes since v1: > > Since we have unified mclk/pclk/pipeline->aclk to one mclk, which will > > be turned on/off when crtc atomic enable/disable, removed runtime power > > management. > > Removes run time get/put related flow. > > Adds to disable the aclk when register access finished. > > > > Changes since v2: > > Rebases to the drm-misc-next branch. > > > > Signed-off-by: Lowry Li (Arm Technology China) > > --- > > .../gpu/drm/arm/display/komeda/komeda_crtc.c | 1 - > > .../gpu/drm/arm/display/komeda/komeda_dev.c | 65 +-- > > .../gpu/drm/arm/display/komeda/komeda_dev.h | 3 + > > .../gpu/drm/arm/display/komeda/komeda_drv.c | 30 - > > 4 files changed, 91 insertions(+), 8 deletions(-) > > > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > index 38d5cb20e908..b47c0dabd0d1 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > @@ -5,7 +5,6 @@ > > * > > */ > > #include > > -#include > > #include > > > > #include > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > index bee4633cdd9f..8a03324f02a5 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > @@ -258,7 +258,7 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > > product->product_id, > > MALIDP_CORE_ID_PRODUCT_ID(mdev->chip.core_id)); > > err = -ENODEV; > > - goto err_cleanup; > > + goto disable_clk; > > } > > > > DRM_INFO("Found ARM Mali-D%x version r%dp%d\n", > > @@ -271,19 +271,19 @@ struct komeda_dev *komeda_dev_create(struct device > > *dev) > > err = mdev->funcs->enum_resources(mdev); > > if (err) { > > DRM_ERROR("enumerate display resource failed.\n"); > > - goto err_cleanup; > > + goto disable_clk; > > } > > > > err = komeda_parse_dt(dev, mdev); > > if (err) { > > DRM_ERROR("parse device tree failed.\n"); > > - goto err_cleanup; > > + goto disable_clk; > > } > > > > err = komeda_assemble_pipelines(mdev); > > if (err) { > > DRM_ERROR("assemble display pipelines failed.\n"); > > - goto err_cleanup; > > + goto disable_clk; > > } > > > > dev->dma_parms = >dma_parms; > > @@ -296,11 +296,14 @@ struct komeda_dev *komeda_dev_create(struct device > > *dev) > > if (mdev->iommu && mdev->funcs->connect_iommu) { > > err = mdev->funcs->connect_iommu(mdev); > > if (err) { > > + DRM_ERROR("connect iommu failed.\n"); > > mdev->iommu = NULL; > > - goto err_cleanup; > > + goto disable_clk; > > } > > } > > > > + clk_disable_unprepare(mdev->aclk); > > + > > err = sysfs_create_group(>kobj, _sysfs_attr_group); > > if (err) { > > DRM_ERROR("create sysfs group failed.\n"); > > @@ -313,6 +316,8 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > > > > return mdev; > > > > +disable_clk: > > + clk_disable_unprepare(mdev->aclk); > > err_cleanup: > > komeda_dev_destroy(mdev); > > return ERR_PTR(err); > > @@ -330,8 +335,12 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > > debugfs_remove_recursive(mdev->debugfs_root); > > #endif > > > > + if (mdev->aclk) > > + clk_prepare_enable(mdev->aclk); > > + > > if (mdev->iommu && mdev->funcs->disconnect_iommu) > > - mdev->funcs->disconnect_iommu(mdev); > > + if (mdev->funcs->disconnect_iommu(mdev)) > > + DRM_ERROR("disconnect iommu failed.\n"); > > mdev->iommu = NULL; > > > > for (i = 0; i < mdev->n_pipelines; i++) { > > @@ -359,3 +368,47 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > > > > devm_kfree(dev, mdev); > > } > > + > > +int komeda_dev_resume(struct komeda_dev *mdev) > > +{ > > + int ret = 0; > > + > > + clk_prepare_enable(mdev->aclk); > > + > > + if (mdev->iommu && mdev->funcs->connect_iommu) { > > + ret = mdev->funcs->connect_iommu(mdev); > > + if (ret < 0) { > > + DRM_ERROR("connect iommu failed.\n"); > > + goto disable_clk; > > + } > > + } > > + > > + ret = mdev->funcs->enable_irq(mdev); > > +
Re: [PATCH] drm/komeda: Adds power management support
On Mon, Sep 23, 2019 at 01:59:25AM +, Lowry Li (Arm Technology China) wrote: > From: "Lowry Li (Arm Technology China)" > > Adds system power management support in KMS kernel driver. > > Depends on: > https://patchwork.freedesktop.org/series/62377/ > > Changes since v1: > Since we have unified mclk/pclk/pipeline->aclk to one mclk, which will > be turned on/off when crtc atomic enable/disable, removed runtime power > management. > Removes run time get/put related flow. > Adds to disable the aclk when register access finished. > > Changes since v2: > Rebases to the drm-misc-next branch. > > Signed-off-by: Lowry Li (Arm Technology China) > --- > .../gpu/drm/arm/display/komeda/komeda_crtc.c | 1 - > .../gpu/drm/arm/display/komeda/komeda_dev.c | 65 +-- > .../gpu/drm/arm/display/komeda/komeda_dev.h | 3 + > .../gpu/drm/arm/display/komeda/komeda_drv.c | 30 - > 4 files changed, 91 insertions(+), 8 deletions(-) > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > index 38d5cb20e908..b47c0dabd0d1 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > @@ -5,7 +5,6 @@ > * > */ > #include > -#include > #include > > #include > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > index bee4633cdd9f..8a03324f02a5 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > @@ -258,7 +258,7 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > product->product_id, > MALIDP_CORE_ID_PRODUCT_ID(mdev->chip.core_id)); > err = -ENODEV; > - goto err_cleanup; > + goto disable_clk; > } > > DRM_INFO("Found ARM Mali-D%x version r%dp%d\n", > @@ -271,19 +271,19 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > err = mdev->funcs->enum_resources(mdev); > if (err) { > DRM_ERROR("enumerate display resource failed.\n"); > - goto err_cleanup; > + goto disable_clk; > } > > err = komeda_parse_dt(dev, mdev); > if (err) { > DRM_ERROR("parse device tree failed.\n"); > - goto err_cleanup; > + goto disable_clk; > } > > err = komeda_assemble_pipelines(mdev); > if (err) { > DRM_ERROR("assemble display pipelines failed.\n"); > - goto err_cleanup; > + goto disable_clk; > } > > dev->dma_parms = >dma_parms; > @@ -296,11 +296,14 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > if (mdev->iommu && mdev->funcs->connect_iommu) { > err = mdev->funcs->connect_iommu(mdev); > if (err) { > + DRM_ERROR("connect iommu failed.\n"); > mdev->iommu = NULL; > - goto err_cleanup; > + goto disable_clk; > } > } > > + clk_disable_unprepare(mdev->aclk); > + > err = sysfs_create_group(>kobj, _sysfs_attr_group); > if (err) { > DRM_ERROR("create sysfs group failed.\n"); > @@ -313,6 +316,8 @@ struct komeda_dev *komeda_dev_create(struct device *dev) > > return mdev; > > +disable_clk: > + clk_disable_unprepare(mdev->aclk); > err_cleanup: > komeda_dev_destroy(mdev); > return ERR_PTR(err); > @@ -330,8 +335,12 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > debugfs_remove_recursive(mdev->debugfs_root); > #endif > > + if (mdev->aclk) > + clk_prepare_enable(mdev->aclk); > + > if (mdev->iommu && mdev->funcs->disconnect_iommu) > - mdev->funcs->disconnect_iommu(mdev); > + if (mdev->funcs->disconnect_iommu(mdev)) > + DRM_ERROR("disconnect iommu failed.\n"); > mdev->iommu = NULL; > > for (i = 0; i < mdev->n_pipelines; i++) { > @@ -359,3 +368,47 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > > devm_kfree(dev, mdev); > } > + > +int komeda_dev_resume(struct komeda_dev *mdev) > +{ > + int ret = 0; > + > + clk_prepare_enable(mdev->aclk); > + > + if (mdev->iommu && mdev->funcs->connect_iommu) { > + ret = mdev->funcs->connect_iommu(mdev); > + if (ret < 0) { > + DRM_ERROR("connect iommu failed.\n"); > + goto disable_clk; > + } > + } > + > + ret = mdev->funcs->enable_irq(mdev); > + > +disable_clk: > + clk_disable_unprepare(mdev->aclk); > + > + return ret; > +} > + > +int komeda_dev_suspend(struct komeda_dev *mdev) > +{ > + int ret = 0; > + > + clk_prepare_enable(mdev->aclk); > + > + if (mdev->iommu && mdev->funcs->disconnect_iommu) { > + ret =
[PATCH] drm/komeda: Adds power management support
From: "Lowry Li (Arm Technology China)" Adds system power management support in KMS kernel driver. Depends on: https://patchwork.freedesktop.org/series/62377/ Changes since v1: Since we have unified mclk/pclk/pipeline->aclk to one mclk, which will be turned on/off when crtc atomic enable/disable, removed runtime power management. Removes run time get/put related flow. Adds to disable the aclk when register access finished. Changes since v2: Rebases to the drm-misc-next branch. Signed-off-by: Lowry Li (Arm Technology China) --- .../gpu/drm/arm/display/komeda/komeda_crtc.c | 1 - .../gpu/drm/arm/display/komeda/komeda_dev.c | 65 +-- .../gpu/drm/arm/display/komeda/komeda_dev.h | 3 + .../gpu/drm/arm/display/komeda/komeda_drv.c | 30 - 4 files changed, 91 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c index 38d5cb20e908..b47c0dabd0d1 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c @@ -5,7 +5,6 @@ * */ #include -#include #include #include diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c index bee4633cdd9f..8a03324f02a5 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c @@ -258,7 +258,7 @@ struct komeda_dev *komeda_dev_create(struct device *dev) product->product_id, MALIDP_CORE_ID_PRODUCT_ID(mdev->chip.core_id)); err = -ENODEV; - goto err_cleanup; + goto disable_clk; } DRM_INFO("Found ARM Mali-D%x version r%dp%d\n", @@ -271,19 +271,19 @@ struct komeda_dev *komeda_dev_create(struct device *dev) err = mdev->funcs->enum_resources(mdev); if (err) { DRM_ERROR("enumerate display resource failed.\n"); - goto err_cleanup; + goto disable_clk; } err = komeda_parse_dt(dev, mdev); if (err) { DRM_ERROR("parse device tree failed.\n"); - goto err_cleanup; + goto disable_clk; } err = komeda_assemble_pipelines(mdev); if (err) { DRM_ERROR("assemble display pipelines failed.\n"); - goto err_cleanup; + goto disable_clk; } dev->dma_parms = >dma_parms; @@ -296,11 +296,14 @@ struct komeda_dev *komeda_dev_create(struct device *dev) if (mdev->iommu && mdev->funcs->connect_iommu) { err = mdev->funcs->connect_iommu(mdev); if (err) { + DRM_ERROR("connect iommu failed.\n"); mdev->iommu = NULL; - goto err_cleanup; + goto disable_clk; } } + clk_disable_unprepare(mdev->aclk); + err = sysfs_create_group(>kobj, _sysfs_attr_group); if (err) { DRM_ERROR("create sysfs group failed.\n"); @@ -313,6 +316,8 @@ struct komeda_dev *komeda_dev_create(struct device *dev) return mdev; +disable_clk: + clk_disable_unprepare(mdev->aclk); err_cleanup: komeda_dev_destroy(mdev); return ERR_PTR(err); @@ -330,8 +335,12 @@ void komeda_dev_destroy(struct komeda_dev *mdev) debugfs_remove_recursive(mdev->debugfs_root); #endif + if (mdev->aclk) + clk_prepare_enable(mdev->aclk); + if (mdev->iommu && mdev->funcs->disconnect_iommu) - mdev->funcs->disconnect_iommu(mdev); + if (mdev->funcs->disconnect_iommu(mdev)) + DRM_ERROR("disconnect iommu failed.\n"); mdev->iommu = NULL; for (i = 0; i < mdev->n_pipelines; i++) { @@ -359,3 +368,47 @@ void komeda_dev_destroy(struct komeda_dev *mdev) devm_kfree(dev, mdev); } + +int komeda_dev_resume(struct komeda_dev *mdev) +{ + int ret = 0; + + clk_prepare_enable(mdev->aclk); + + if (mdev->iommu && mdev->funcs->connect_iommu) { + ret = mdev->funcs->connect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("connect iommu failed.\n"); + goto disable_clk; + } + } + + ret = mdev->funcs->enable_irq(mdev); + +disable_clk: + clk_disable_unprepare(mdev->aclk); + + return ret; +} + +int komeda_dev_suspend(struct komeda_dev *mdev) +{ + int ret = 0; + + clk_prepare_enable(mdev->aclk); + + if (mdev->iommu && mdev->funcs->disconnect_iommu) { + ret = mdev->funcs->disconnect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("disconnect iommu failed.\n"); + goto disable_clk; + } + } + + ret = mdev->funcs->disable_irq(mdev);
[PATCH] drm/komeda: Adds power management support
From: "Lowry Li (Arm Technology China)" Adds system power management support in KMS kernel driver. Depends on: - https://patchwork.freedesktop.org/series/61650/ - https://patchwork.freedesktop.org/series/60083/ Changes since v1: Since we have unified mclk/pclk/pipeline->aclk to one mclk, which will be turned on/off when crtc atomic enable/disable, removed runtime power management. Removes run time get/put related flow. Adds to disable the aclk when register access finished. Signed-off-by: Lowry Li (Arm Technology China) --- drivers/gpu/drm/arm/display/komeda/komeda_crtc.c | 1 - drivers/gpu/drm/arm/display/komeda/komeda_dev.c | 65 +--- drivers/gpu/drm/arm/display/komeda/komeda_dev.h | 2 + drivers/gpu/drm/arm/display/komeda/komeda_drv.c | 30 ++- 4 files changed, 90 insertions(+), 8 deletions(-) diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c index cafb445..d14e7f3 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c @@ -5,7 +5,6 @@ * */ #include -#include #include #include diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c index e1aa58e..a82f67b 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c @@ -209,7 +209,7 @@ struct komeda_dev *komeda_dev_create(struct device *dev) product->product_id, MALIDP_CORE_ID_PRODUCT_ID(mdev->chip.core_id)); err = -ENODEV; - goto err_cleanup; + goto disable_clk; } DRM_INFO("Found ARM Mali-D%x version r%dp%d\n", @@ -222,19 +222,19 @@ struct komeda_dev *komeda_dev_create(struct device *dev) err = mdev->funcs->enum_resources(mdev); if (err) { DRM_ERROR("enumerate display resource failed.\n"); - goto err_cleanup; + goto disable_clk; } err = komeda_parse_dt(dev, mdev); if (err) { DRM_ERROR("parse device tree failed.\n"); - goto err_cleanup; + goto disable_clk; } err = komeda_assemble_pipelines(mdev); if (err) { DRM_ERROR("assemble display pipelines failed.\n"); - goto err_cleanup; + goto disable_clk; } dev->dma_parms = >dma_parms; @@ -247,11 +247,14 @@ struct komeda_dev *komeda_dev_create(struct device *dev) if (mdev->iommu && mdev->funcs->connect_iommu) { err = mdev->funcs->connect_iommu(mdev); if (err) { + DRM_ERROR("connect iommu failed.\n"); mdev->iommu = NULL; - goto err_cleanup; + goto disable_clk; } } + clk_disable_unprepare(mdev->aclk); + err = sysfs_create_group(>kobj, _sysfs_attr_group); if (err) { DRM_ERROR("create sysfs group failed.\n"); @@ -264,6 +267,8 @@ struct komeda_dev *komeda_dev_create(struct device *dev) return mdev; +disable_clk: + clk_disable_unprepare(mdev->aclk); err_cleanup: komeda_dev_destroy(mdev); return ERR_PTR(err); @@ -281,8 +286,12 @@ void komeda_dev_destroy(struct komeda_dev *mdev) debugfs_remove_recursive(mdev->debugfs_root); #endif + if (mdev->aclk) + clk_prepare_enable(mdev->aclk); + if (mdev->iommu && mdev->funcs->disconnect_iommu) - mdev->funcs->disconnect_iommu(mdev); + if (mdev->funcs->disconnect_iommu(mdev)) + DRM_ERROR("disconnect iommu failed.\n"); mdev->iommu = NULL; for (i = 0; i < mdev->n_pipelines; i++) { @@ -308,3 +317,47 @@ void komeda_dev_destroy(struct komeda_dev *mdev) devm_kfree(dev, mdev); } + +int komeda_dev_resume(struct komeda_dev *mdev) +{ + int ret = 0; + + clk_prepare_enable(mdev->aclk); + + if (mdev->iommu && mdev->funcs->connect_iommu) { + ret = mdev->funcs->connect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("connect iommu failed.\n"); + goto disable_clk; + } + } + + ret = mdev->funcs->enable_irq(mdev); + +disable_clk: + clk_disable_unprepare(mdev->aclk); + + return ret; +} + +int komeda_dev_suspend(struct komeda_dev *mdev) +{ + int ret = 0; + + clk_prepare_enable(mdev->aclk); + + if (mdev->iommu && mdev->funcs->disconnect_iommu) { + ret = mdev->funcs->disconnect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("disconnect iommu failed.\n"); + goto disable_clk; + } + } + + ret = mdev->funcs->disable_irq(mdev); +
Re: [PATCH] drm/komeda: Adds power management support
Hi Liviu, On Thu, Jun 20, 2019 at 12:15:22AM +0800, Liviu Dudau wrote: > Hi Lowry, > > On Mon, Jun 17, 2019 at 06:55:49AM +0100, Lowry Li (Arm Technology China) > wrote: > > Adds runtime and system power management support in KMS kernel driver. > > > > Depends on: > > - https://patchwork.freedesktop.org/series/61650/ > > - https://patchwork.freedesktop.org/series/60083/ > > > > Signed-off-by: Lowry Li (Arm Technology China) > > --- > > drivers/gpu/drm/arm/display/komeda/komeda_crtc.c | 2 + > > drivers/gpu/drm/arm/display/komeda/komeda_dev.c | 30 + > > drivers/gpu/drm/arm/display/komeda/komeda_dev.h | 2 + > > drivers/gpu/drm/arm/display/komeda/komeda_drv.c | 54 > > ++-- > > 4 files changed, 85 insertions(+), 3 deletions(-) > > > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > index 66c5e0d..1b4ea8a 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > > @@ -257,6 +257,7 @@ void komeda_crtc_handle_event(struct komeda_crtc > > *kcrtc, > > komeda_crtc_atomic_enable(struct drm_crtc *crtc, > > struct drm_crtc_state *old) > > { > > + pm_runtime_get_sync(crtc->dev->dev); > > komeda_crtc_prepare(to_kcrtc(crtc)); > > drm_crtc_vblank_on(crtc); > > komeda_crtc_do_flush(crtc, old); > > @@ -330,6 +331,7 @@ void komeda_crtc_handle_event(struct komeda_crtc > > *kcrtc, > > > > drm_crtc_vblank_off(crtc); > > komeda_crtc_unprepare(kcrtc); > > + pm_runtime_put(crtc->dev->dev); > > } > > > > static void > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > index 405c64d..edd0943 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > > @@ -308,3 +308,33 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > > > > devm_kfree(dev, mdev); > > } > > + > > +int komeda_dev_resume(struct komeda_dev *mdev) > > +{ > > + int ret = 0; > > + > > + if (mdev->iommu && mdev->funcs->connect_iommu) { > > + ret = mdev->funcs->connect_iommu(mdev); > > + if (ret < 0) { > > + DRM_ERROR("connect iommu failed.\n"); > > + return ret; > > + } > > + } > > + > > + return mdev->funcs->enable_irq(mdev); > > +} > > + > > +int komeda_dev_suspend(struct komeda_dev *mdev) > > +{ > > + int ret = 0; > > + > > + if (mdev->iommu && mdev->funcs->disconnect_iommu) { > > + ret = mdev->funcs->disconnect_iommu(mdev); > > + if (ret < 0) { > > + DRM_ERROR("disconnect iommu failed.\n"); > > + return ret; > > + } > > + } > > + > > + return mdev->funcs->disable_irq(mdev); > > +} > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > > index d1c86b6..096f9f7 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > > @@ -207,4 +207,6 @@ struct komeda_dev { > > > > struct komeda_dev *dev_to_mdev(struct device *dev); > > > > +int komeda_dev_resume(struct komeda_dev *mdev); > > +int komeda_dev_suspend(struct komeda_dev *mdev); > > #endif /*_KOMEDA_DEV_H_*/ > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > > b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > > index cfa5068..aa4cef1 100644 > > --- a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > > @@ -8,6 +8,7 @@ > > #include > > #include > > #include > > +#include > > #include > > #include "komeda_dev.h" > > #include "komeda_kms.h" > > @@ -32,6 +33,9 @@ static void komeda_unbind(struct device *dev) > > return; > > > > komeda_kms_detach(mdrv->kms); > > + > > + pm_runtime_disable(dev); > > + > > komeda_dev_destroy(mdrv->mdev); > > > > dev_set_drvdata(dev, NULL); > > @@ -52,6 +56,9 @@ static int komeda_bind(struct device *dev) > > err = PTR_ERR(mdrv->mdev); > > goto free_mdrv; > > } > > + dev_set_drvdata(dev, mdrv); > > + > > + pm_runtime_enable(dev); > > > > mdrv->kms = komeda_kms_attach(mdrv->mdev); > > if (IS_ERR(mdrv->kms)) { > > @@ -59,11 +66,10 @@ static int komeda_bind(struct device *dev) > > goto destroy_mdev; > > } > > > > - dev_set_drvdata(dev, mdrv); > > - > > return 0; > > > > destroy_mdev: > > + pm_runtime_disable(dev); > > komeda_dev_destroy(mdrv->mdev); > > > > free_mdrv: > > @@ -134,13 +140,55 @@ static int komeda_platform_remove(struct > > platform_device *pdev) > > > > MODULE_DEVICE_TABLE(of, komeda_of_match); > > > > +static int komeda_rt_pm_suspend(struct device *dev) > > +{ > > + dev_info(dev, "%s\n", __func__); > > + return
Re: [PATCH] drm/komeda: Adds power management support
Hi Lowry, On Mon, Jun 17, 2019 at 06:55:49AM +0100, Lowry Li (Arm Technology China) wrote: > Adds runtime and system power management support in KMS kernel driver. > > Depends on: > - https://patchwork.freedesktop.org/series/61650/ > - https://patchwork.freedesktop.org/series/60083/ > > Signed-off-by: Lowry Li (Arm Technology China) > --- > drivers/gpu/drm/arm/display/komeda/komeda_crtc.c | 2 + > drivers/gpu/drm/arm/display/komeda/komeda_dev.c | 30 + > drivers/gpu/drm/arm/display/komeda/komeda_dev.h | 2 + > drivers/gpu/drm/arm/display/komeda/komeda_drv.c | 54 > ++-- > 4 files changed, 85 insertions(+), 3 deletions(-) > > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > index 66c5e0d..1b4ea8a 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c > @@ -257,6 +257,7 @@ void komeda_crtc_handle_event(struct komeda_crtc *kcrtc, > komeda_crtc_atomic_enable(struct drm_crtc *crtc, > struct drm_crtc_state *old) > { > + pm_runtime_get_sync(crtc->dev->dev); > komeda_crtc_prepare(to_kcrtc(crtc)); > drm_crtc_vblank_on(crtc); > komeda_crtc_do_flush(crtc, old); > @@ -330,6 +331,7 @@ void komeda_crtc_handle_event(struct komeda_crtc *kcrtc, > > drm_crtc_vblank_off(crtc); > komeda_crtc_unprepare(kcrtc); > + pm_runtime_put(crtc->dev->dev); > } > > static void > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > index 405c64d..edd0943 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c > @@ -308,3 +308,33 @@ void komeda_dev_destroy(struct komeda_dev *mdev) > > devm_kfree(dev, mdev); > } > + > +int komeda_dev_resume(struct komeda_dev *mdev) > +{ > + int ret = 0; > + > + if (mdev->iommu && mdev->funcs->connect_iommu) { > + ret = mdev->funcs->connect_iommu(mdev); > + if (ret < 0) { > + DRM_ERROR("connect iommu failed.\n"); > + return ret; > + } > + } > + > + return mdev->funcs->enable_irq(mdev); > +} > + > +int komeda_dev_suspend(struct komeda_dev *mdev) > +{ > + int ret = 0; > + > + if (mdev->iommu && mdev->funcs->disconnect_iommu) { > + ret = mdev->funcs->disconnect_iommu(mdev); > + if (ret < 0) { > + DRM_ERROR("disconnect iommu failed.\n"); > + return ret; > + } > + } > + > + return mdev->funcs->disable_irq(mdev); > +} > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > index d1c86b6..096f9f7 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h > @@ -207,4 +207,6 @@ struct komeda_dev { > > struct komeda_dev *dev_to_mdev(struct device *dev); > > +int komeda_dev_resume(struct komeda_dev *mdev); > +int komeda_dev_suspend(struct komeda_dev *mdev); > #endif /*_KOMEDA_DEV_H_*/ > diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > index cfa5068..aa4cef1 100644 > --- a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > +++ b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c > @@ -8,6 +8,7 @@ > #include > #include > #include > +#include > #include > #include "komeda_dev.h" > #include "komeda_kms.h" > @@ -32,6 +33,9 @@ static void komeda_unbind(struct device *dev) > return; > > komeda_kms_detach(mdrv->kms); > + > + pm_runtime_disable(dev); > + > komeda_dev_destroy(mdrv->mdev); > > dev_set_drvdata(dev, NULL); > @@ -52,6 +56,9 @@ static int komeda_bind(struct device *dev) > err = PTR_ERR(mdrv->mdev); > goto free_mdrv; > } > + dev_set_drvdata(dev, mdrv); > + > + pm_runtime_enable(dev); > > mdrv->kms = komeda_kms_attach(mdrv->mdev); > if (IS_ERR(mdrv->kms)) { > @@ -59,11 +66,10 @@ static int komeda_bind(struct device *dev) > goto destroy_mdev; > } > > - dev_set_drvdata(dev, mdrv); > - > return 0; > > destroy_mdev: > + pm_runtime_disable(dev); > komeda_dev_destroy(mdrv->mdev); > > free_mdrv: > @@ -134,13 +140,55 @@ static int komeda_platform_remove(struct > platform_device *pdev) > > MODULE_DEVICE_TABLE(of, komeda_of_match); > > +static int komeda_rt_pm_suspend(struct device *dev) > +{ > + dev_info(dev, "%s\n", __func__); > + return 0; > +} > + > +static int komeda_rt_pm_resume(struct device *dev) > +{ > + dev_info(dev, "%s\n", __func__); > + return 0; > +} Useful only for debugging? I think you've missed an opportunity here to turn off clocks and disable interrupts. > + > +static int
[PATCH] drm/komeda: Adds power management support
Adds runtime and system power management support in KMS kernel driver. Depends on: - https://patchwork.freedesktop.org/series/61650/ - https://patchwork.freedesktop.org/series/60083/ Signed-off-by: Lowry Li (Arm Technology China) --- drivers/gpu/drm/arm/display/komeda/komeda_crtc.c | 2 + drivers/gpu/drm/arm/display/komeda/komeda_dev.c | 30 + drivers/gpu/drm/arm/display/komeda/komeda_dev.h | 2 + drivers/gpu/drm/arm/display/komeda/komeda_drv.c | 54 ++-- 4 files changed, 85 insertions(+), 3 deletions(-) diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c index 66c5e0d..1b4ea8a 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_crtc.c @@ -257,6 +257,7 @@ void komeda_crtc_handle_event(struct komeda_crtc *kcrtc, komeda_crtc_atomic_enable(struct drm_crtc *crtc, struct drm_crtc_state *old) { + pm_runtime_get_sync(crtc->dev->dev); komeda_crtc_prepare(to_kcrtc(crtc)); drm_crtc_vblank_on(crtc); komeda_crtc_do_flush(crtc, old); @@ -330,6 +331,7 @@ void komeda_crtc_handle_event(struct komeda_crtc *kcrtc, drm_crtc_vblank_off(crtc); komeda_crtc_unprepare(kcrtc); + pm_runtime_put(crtc->dev->dev); } static void diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c index 405c64d..edd0943 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.c @@ -308,3 +308,33 @@ void komeda_dev_destroy(struct komeda_dev *mdev) devm_kfree(dev, mdev); } + +int komeda_dev_resume(struct komeda_dev *mdev) +{ + int ret = 0; + + if (mdev->iommu && mdev->funcs->connect_iommu) { + ret = mdev->funcs->connect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("connect iommu failed.\n"); + return ret; + } + } + + return mdev->funcs->enable_irq(mdev); +} + +int komeda_dev_suspend(struct komeda_dev *mdev) +{ + int ret = 0; + + if (mdev->iommu && mdev->funcs->disconnect_iommu) { + ret = mdev->funcs->disconnect_iommu(mdev); + if (ret < 0) { + DRM_ERROR("disconnect iommu failed.\n"); + return ret; + } + } + + return mdev->funcs->disable_irq(mdev); +} diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h index d1c86b6..096f9f7 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_dev.h +++ b/drivers/gpu/drm/arm/display/komeda/komeda_dev.h @@ -207,4 +207,6 @@ struct komeda_dev { struct komeda_dev *dev_to_mdev(struct device *dev); +int komeda_dev_resume(struct komeda_dev *mdev); +int komeda_dev_suspend(struct komeda_dev *mdev); #endif /*_KOMEDA_DEV_H_*/ diff --git a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c index cfa5068..aa4cef1 100644 --- a/drivers/gpu/drm/arm/display/komeda/komeda_drv.c +++ b/drivers/gpu/drm/arm/display/komeda/komeda_drv.c @@ -8,6 +8,7 @@ #include #include #include +#include #include #include "komeda_dev.h" #include "komeda_kms.h" @@ -32,6 +33,9 @@ static void komeda_unbind(struct device *dev) return; komeda_kms_detach(mdrv->kms); + + pm_runtime_disable(dev); + komeda_dev_destroy(mdrv->mdev); dev_set_drvdata(dev, NULL); @@ -52,6 +56,9 @@ static int komeda_bind(struct device *dev) err = PTR_ERR(mdrv->mdev); goto free_mdrv; } + dev_set_drvdata(dev, mdrv); + + pm_runtime_enable(dev); mdrv->kms = komeda_kms_attach(mdrv->mdev); if (IS_ERR(mdrv->kms)) { @@ -59,11 +66,10 @@ static int komeda_bind(struct device *dev) goto destroy_mdev; } - dev_set_drvdata(dev, mdrv); - return 0; destroy_mdev: + pm_runtime_disable(dev); komeda_dev_destroy(mdrv->mdev); free_mdrv: @@ -134,13 +140,55 @@ static int komeda_platform_remove(struct platform_device *pdev) MODULE_DEVICE_TABLE(of, komeda_of_match); +static int komeda_rt_pm_suspend(struct device *dev) +{ + dev_info(dev, "%s\n", __func__); + return 0; +} + +static int komeda_rt_pm_resume(struct device *dev) +{ + dev_info(dev, "%s\n", __func__); + return 0; +} + +static int __maybe_unused komeda_pm_suspend(struct device *dev) +{ + struct komeda_drv *mdrv = dev_get_drvdata(dev); + struct drm_device *drm = >kms->base; + int res; + + dev_info(dev, "%s\n", __func__); + res = drm_mode_config_helper_suspend(drm); + + komeda_dev_suspend(mdrv->mdev); + + return res; +} + +static int __maybe_unused komeda_pm_resume(struct device *dev) +{ + struct