Commit 50b1131e authored by Dmitry Baryshkov's avatar Dmitry Baryshkov
Browse files

drm/msm/dp: rewrite dss_module_power to use bulk clock functions



In order to simplify DP code, drop hand-coded loops over clock arrays,
replacing them with clk_bulk_* functions.

Signed-off-by: default avatarDmitry Baryshkov <dmitry.baryshkov@linaro.org>
Reviewed-by: default avatarStephen Boyd <swboyd@chromium.org>
Patchwork: https://patchwork.freedesktop.org/patch/474717/
Link: https://lore.kernel.org/r/20220217055529.499829-6-dmitry.baryshkov@linaro.org


Signed-off-by: default avatarDmitry Baryshkov <dmitry.baryshkov@linaro.org>
parent fc18ea98
Loading
Loading
Loading
Loading
+0 −1
Original line number Diff line number Diff line
@@ -119,7 +119,6 @@ msm-$(CONFIG_DRM_MSM_GPU_STATE) += adreno/a6xx_gpu_state.o

msm-$(CONFIG_DRM_MSM_DP)+= dp/dp_aux.o \
	dp/dp_catalog.o \
	dp/dp_clk_util.o \
	dp/dp_ctrl.o \
	dp/dp_display.o \
	dp/dp_drm.o \
+0 −87
Original line number Diff line number Diff line
// SPDX-License-Identifier: GPL-2.0-only
/* Copyright (c) 2012-2015, 2017-2018, The Linux Foundation.
 * All rights reserved.
 */

#include <linux/clk.h>
#include <linux/clk/clk-conf.h>
#include <linux/err.h>
#include <linux/delay.h>
#include <linux/of.h>

#include <drm/drm_print.h>

#include "dp_clk_util.h"

void msm_dss_put_clk(struct dss_clk *clk_arry, int num_clk)
{
	int i;

	for (i = num_clk - 1; i >= 0; i--) {
		if (clk_arry[i].clk)
			clk_put(clk_arry[i].clk);
		clk_arry[i].clk = NULL;
	}
}

int msm_dss_get_clk(struct device *dev, struct dss_clk *clk_arry, int num_clk)
{
	int i, rc = 0;

	for (i = 0; i < num_clk; i++) {
		clk_arry[i].clk = clk_get(dev, clk_arry[i].clk_name);
		rc = PTR_ERR_OR_ZERO(clk_arry[i].clk);
		if (rc) {
			DEV_ERR("%pS->%s: '%s' get failed. rc=%d\n",
				__builtin_return_address(0), __func__,
				clk_arry[i].clk_name, rc);
			goto error;
		}
	}

	return rc;

error:
	for (i--; i >= 0; i--) {
		if (clk_arry[i].clk)
			clk_put(clk_arry[i].clk);
		clk_arry[i].clk = NULL;
	}

	return rc;
}

int msm_dss_enable_clk(struct dss_clk *clk_arry, int num_clk, int enable)
{
	int i, rc = 0;

	if (enable) {
		for (i = 0; i < num_clk; i++) {
			DEV_DBG("%pS->%s: enable '%s'\n",
				__builtin_return_address(0), __func__,
				clk_arry[i].clk_name);
			rc = clk_prepare_enable(clk_arry[i].clk);
			if (rc)
				DEV_ERR("%pS->%s: %s en fail. rc=%d\n",
					__builtin_return_address(0),
					__func__,
					clk_arry[i].clk_name, rc);

			if (rc && i) {
				msm_dss_enable_clk(&clk_arry[i - 1],
					i - 1, false);
				break;
			}
		}
	} else {
		for (i = num_clk - 1; i >= 0; i--) {
			DEV_DBG("%pS->%s: disable '%s'\n",
				__builtin_return_address(0), __func__,
				clk_arry[i].clk_name);

			clk_disable_unprepare(clk_arry[i].clk);
		}
	}

	return rc;
}
+0 −29
Original line number Diff line number Diff line
/* SPDX-License-Identifier: GPL-2.0-only */
/* Copyright (c) 2012, 2017-2018, The Linux Foundation. All rights reserved.
 */

#ifndef __DP_CLK_UTIL_H__
#define __DP_CLK_UTIL_H__

#include <linux/platform_device.h>
#include <linux/types.h>

#define DEV_DBG(fmt, args...)   pr_debug(fmt, ##args)
#define DEV_INFO(fmt, args...)  pr_info(fmt, ##args)
#define DEV_WARN(fmt, args...)  pr_warn(fmt, ##args)
#define DEV_ERR(fmt, args...)   pr_err(fmt, ##args)

struct dss_clk {
	struct clk *clk; /* clk handle */
	char clk_name[32];
};

struct dss_module_power {
	unsigned int num_clk;
	struct dss_clk *clk_config;
};

int msm_dss_get_clk(struct device *dev, struct dss_clk *clk_arry, int num_clk);
void msm_dss_put_clk(struct dss_clk *clk_arry, int num_clk);
int msm_dss_enable_clk(struct dss_clk *clk_arry, int num_clk, int enable);
#endif /* __DP_CLK_UTIL_H__ */
+2 −2
Original line number Diff line number Diff line
@@ -1321,9 +1321,9 @@ static void dp_ctrl_set_clock_rate(struct dp_ctrl_private *ctrl,
			enum dp_pm_type module, char *name, unsigned long rate)
{
	u32 num = ctrl->parser->mp[module].num_clk;
	struct dss_clk *cfg = ctrl->parser->mp[module].clk_config;
	struct clk_bulk_data *cfg = ctrl->parser->mp[module].clocks;

	while (num && strcmp(cfg->clk_name, name)) {
	while (num && strcmp(cfg->id, name)) {
		num--;
		cfg++;
	}
+15 −21
Original line number Diff line number Diff line
@@ -162,11 +162,11 @@ static int dp_parser_init_clk_data(struct dp_parser *parser)
	}

	core_power->num_clk = core_clk_count;
	core_power->clk_config = devm_kzalloc(dev,
			sizeof(struct dss_clk) * core_power->num_clk,
	core_power->clocks = devm_kcalloc(dev,
			core_power->num_clk, sizeof(struct clk_bulk_data),
			GFP_KERNEL);
	if (!core_power->clk_config)
		return -EINVAL;
	if (!core_power->clocks)
		return -ENOMEM;

	/* Initialize the CTRL power module */
	if (ctrl_clk_count == 0) {
@@ -175,12 +175,12 @@ static int dp_parser_init_clk_data(struct dp_parser *parser)
	}

	ctrl_power->num_clk = ctrl_clk_count;
	ctrl_power->clk_config = devm_kzalloc(dev,
			sizeof(struct dss_clk) * ctrl_power->num_clk,
	ctrl_power->clocks = devm_kcalloc(dev,
			ctrl_power->num_clk, sizeof(struct clk_bulk_data),
			GFP_KERNEL);
	if (!ctrl_power->clk_config) {
	if (!ctrl_power->clocks) {
		ctrl_power->num_clk = 0;
		return -EINVAL;
		return -ENOMEM;
	}

	/* Initialize the STREAM power module */
@@ -190,12 +190,12 @@ static int dp_parser_init_clk_data(struct dp_parser *parser)
	}

	stream_power->num_clk = stream_clk_count;
	stream_power->clk_config = devm_kzalloc(dev,
			sizeof(struct dss_clk) * stream_power->num_clk,
	stream_power->clocks = devm_kcalloc(dev,
			stream_power->num_clk, sizeof(struct clk_bulk_data),
			GFP_KERNEL);
	if (!stream_power->clk_config) {
	if (!stream_power->clocks) {
		stream_power->num_clk = 0;
		return -EINVAL;
		return -ENOMEM;
	}

	return 0;
@@ -234,21 +234,15 @@ static int dp_parser_clock(struct dp_parser *parser)
		}
		if (dp_parser_check_prefix("core", clk_name) &&
				core_clk_index < core_clk_count) {
			struct dss_clk *clk =
				&core_power->clk_config[core_clk_index];
			strlcpy(clk->clk_name, clk_name, sizeof(clk->clk_name));
			core_power->clocks[core_clk_index].id = devm_kstrdup(dev, clk_name, GFP_KERNEL);
			core_clk_index++;
		} else if (dp_parser_check_prefix("stream", clk_name) &&
				stream_clk_index < stream_clk_count) {
			struct dss_clk *clk =
				&stream_power->clk_config[stream_clk_index];
			strlcpy(clk->clk_name, clk_name, sizeof(clk->clk_name));
			stream_power->clocks[stream_clk_index].id = devm_kstrdup(dev, clk_name, GFP_KERNEL);
			stream_clk_index++;
		} else if (dp_parser_check_prefix("ctrl", clk_name) &&
			   ctrl_clk_index < ctrl_clk_count) {
			struct dss_clk *clk =
				&ctrl_power->clk_config[ctrl_clk_index];
			strlcpy(clk->clk_name, clk_name, sizeof(clk->clk_name));
			ctrl_power->clocks[ctrl_clk_index].id = devm_kstrdup(dev, clk_name, GFP_KERNEL);
			ctrl_clk_index++;
		}
	}
Loading