aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/exynos/exynos_drm_fimd.c
diff options
context:
space:
mode:
authorSean Paul <seanpaul@chromium.org>2014-01-30 16:19:27 -0500
committerInki Dae <daeinki@gmail.com>2014-03-23 11:36:36 -0400
commitaf65c804877078a58cb02cc0f2ce4198401402fc (patch)
tree1894a3b77ee5098bafe60f69694ca5d122a1be36 /drivers/gpu/drm/exynos/exynos_drm_fimd.c
parenta43b933bcbbd6c7e2660b672a311345cea9524c1 (diff)
drm/exynos: Consolidate suspend/resume in drm_drv
This patch removes all of the suspend/resume logic from the individual drivers and consolidates it in drm_drv. This consolidation reduces the number of functions which enable/disable the hardware to just one -- the dpms callback. This ensures that we always power up/down in a consistent manner. Signed-off-by: Sean Paul <seanpaul@chromium.org> Signed-off-by: Inki Dae <inki.dae@samsung.com>
Diffstat (limited to 'drivers/gpu/drm/exynos/exynos_drm_fimd.c')
-rw-r--r--drivers/gpu/drm/exynos/exynos_drm_fimd.c86
1 files changed, 9 insertions, 77 deletions
diff --git a/drivers/gpu/drm/exynos/exynos_drm_fimd.c b/drivers/gpu/drm/exynos/exynos_drm_fimd.c
index 1efdcac4510d..f78fbf4682b4 100644
--- a/drivers/gpu/drm/exynos/exynos_drm_fimd.c
+++ b/drivers/gpu/drm/exynos/exynos_drm_fimd.c
@@ -732,6 +732,8 @@ static int fimd_poweron(struct exynos_drm_manager *mgr)
732 732
733 ctx->suspended = false; 733 ctx->suspended = false;
734 734
735 pm_runtime_get_sync(ctx->dev);
736
735 ret = clk_prepare_enable(ctx->bus_clk); 737 ret = clk_prepare_enable(ctx->bus_clk);
736 if (ret < 0) { 738 if (ret < 0) {
737 DRM_ERROR("Failed to prepare_enable the bus clk [%d]\n", ret); 739 DRM_ERROR("Failed to prepare_enable the bus clk [%d]\n", ret);
@@ -785,32 +787,24 @@ static int fimd_poweroff(struct exynos_drm_manager *mgr)
785 clk_disable_unprepare(ctx->lcd_clk); 787 clk_disable_unprepare(ctx->lcd_clk);
786 clk_disable_unprepare(ctx->bus_clk); 788 clk_disable_unprepare(ctx->bus_clk);
787 789
790 pm_runtime_put_sync(ctx->dev);
791
788 ctx->suspended = true; 792 ctx->suspended = true;
789 return 0; 793 return 0;
790} 794}
791 795
792static void fimd_dpms(struct exynos_drm_manager *mgr, int mode) 796static void fimd_dpms(struct exynos_drm_manager *mgr, int mode)
793{ 797{
794 struct fimd_context *ctx = mgr->ctx; 798 DRM_DEBUG_KMS("%s, %d\n", __FILE__, mode);
795
796 DRM_DEBUG_KMS("%d\n", mode);
797 799
798 switch (mode) { 800 switch (mode) {
799 case DRM_MODE_DPMS_ON: 801 case DRM_MODE_DPMS_ON:
800 /* 802 fimd_poweron(mgr);
801 * enable fimd hardware only if suspended status.
802 *
803 * P.S. fimd_dpms function would be called at booting time so
804 * clk_enable could be called double time.
805 */
806 if (ctx->suspended)
807 pm_runtime_get_sync(ctx->dev);
808 break; 803 break;
809 case DRM_MODE_DPMS_STANDBY: 804 case DRM_MODE_DPMS_STANDBY:
810 case DRM_MODE_DPMS_SUSPEND: 805 case DRM_MODE_DPMS_SUSPEND:
811 case DRM_MODE_DPMS_OFF: 806 case DRM_MODE_DPMS_OFF:
812 if (!ctx->suspended) 807 fimd_poweroff(mgr);
813 pm_runtime_put_sync(ctx->dev);
814 break; 808 break;
815 default: 809 default:
816 DRM_DEBUG_KMS("unspecified mode %d\n", mode); 810 DRM_DEBUG_KMS("unspecified mode %d\n", mode);
@@ -929,7 +923,6 @@ static int fimd_probe(struct platform_device *pdev)
929 exynos_drm_manager_register(&fimd_manager); 923 exynos_drm_manager_register(&fimd_manager);
930 924
931 pm_runtime_enable(dev); 925 pm_runtime_enable(dev);
932 pm_runtime_get_sync(dev);
933 926
934 for (win = 0; win < WINDOWS_NR; win++) 927 for (win = 0; win < WINDOWS_NR; win++)
935 fimd_clear_win(ctx, win); 928 fimd_clear_win(ctx, win);
@@ -939,84 +932,23 @@ static int fimd_probe(struct platform_device *pdev)
939 932
940static int fimd_remove(struct platform_device *pdev) 933static int fimd_remove(struct platform_device *pdev)
941{ 934{
942 struct device *dev = &pdev->dev;
943 struct exynos_drm_manager *mgr = platform_get_drvdata(pdev); 935 struct exynos_drm_manager *mgr = platform_get_drvdata(pdev);
944 struct fimd_context *ctx = mgr->ctx;
945 936
946 exynos_drm_manager_unregister(&fimd_manager); 937 exynos_drm_manager_unregister(&fimd_manager);
947 938
948 if (ctx->suspended) 939 fimd_dpms(mgr, DRM_MODE_DPMS_OFF);
949 goto out;
950
951 pm_runtime_set_suspended(dev);
952 pm_runtime_put_sync(dev);
953 940
954out: 941 pm_runtime_disable(&pdev->dev);
955 pm_runtime_disable(dev);
956
957 return 0;
958}
959
960#ifdef CONFIG_PM_SLEEP
961static int fimd_suspend(struct device *dev)
962{
963 struct exynos_drm_manager *mgr = get_fimd_manager(dev);
964
965 /*
966 * do not use pm_runtime_suspend(). if pm_runtime_suspend() is
967 * called here, an error would be returned by that interface
968 * because the usage_count of pm runtime is more than 1.
969 */
970 if (!pm_runtime_suspended(dev))
971 return fimd_poweroff(mgr);
972 942
973 return 0; 943 return 0;
974} 944}
975 945
976static int fimd_resume(struct device *dev)
977{
978 struct exynos_drm_manager *mgr = get_fimd_manager(dev);
979
980 /*
981 * if entered to sleep when lcd panel was on, the usage_count
982 * of pm runtime would still be 1 so in this case, fimd driver
983 * should be on directly not drawing on pm runtime interface.
984 */
985 if (pm_runtime_suspended(dev))
986 return 0;
987
988 return fimd_poweron(mgr);
989}
990#endif
991
992#ifdef CONFIG_PM_RUNTIME
993static int fimd_runtime_suspend(struct device *dev)
994{
995 struct exynos_drm_manager *mgr = get_fimd_manager(dev);
996
997 return fimd_poweroff(mgr);
998}
999
1000static int fimd_runtime_resume(struct device *dev)
1001{
1002 struct exynos_drm_manager *mgr = get_fimd_manager(dev);
1003
1004 return fimd_poweron(mgr);
1005}
1006#endif
1007
1008static const struct dev_pm_ops fimd_pm_ops = {
1009 SET_SYSTEM_SLEEP_PM_OPS(fimd_suspend, fimd_resume)
1010 SET_RUNTIME_PM_OPS(fimd_runtime_suspend, fimd_runtime_resume, NULL)
1011};
1012
1013struct platform_driver fimd_driver = { 946struct platform_driver fimd_driver = {
1014 .probe = fimd_probe, 947 .probe = fimd_probe,
1015 .remove = fimd_remove, 948 .remove = fimd_remove,
1016 .driver = { 949 .driver = {
1017 .name = "exynos4-fb", 950 .name = "exynos4-fb",
1018 .owner = THIS_MODULE, 951 .owner = THIS_MODULE,
1019 .pm = &fimd_pm_ops,
1020 .of_match_table = fimd_driver_dt_match, 952 .of_match_table = fimd_driver_dt_match,
1021 }, 953 },
1022}; 954};