Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f89b001d authored by Avinash Philip's avatar Avinash Philip
Browse files

drver:soc:llcc_perfmon: qdss clk node control



qdss clock needs to be enabled on llcc_perfmon counter to function.
Enable/disable clock on Start/Stop llcc_perfmon commands.

Change-Id: I73a13b7de023187b3fbdf256be7594502e46f4f9
Signed-off-by: default avatarAvinash Philip <avinashp@codeaurora.org>
parent 2e5dbc89
Loading
Loading
Loading
Loading
+22 −1
Original line number Diff line number Diff line
@@ -26,6 +26,7 @@
#include <linux/regmap.h>
#include <linux/soc/qcom/llcc-qcom.h>
#include <linux/module.h>
#include <linux/clk.h>
#include "llcc_events.h"
#include "llcc_perfmon.h"

@@ -79,6 +80,7 @@ struct event_port_ops {
 * @mutex:		mutex to protect this structure
 * @hrtimer:		hrtimer instance for timer functionality
 * @expires:		timer expire time in nano seconds
 * @clk:		clock node to enable qdss
 */
struct llcc_perfmon_private {
	struct regmap *llcc_map;
@@ -94,6 +96,7 @@ struct llcc_perfmon_private {
	struct mutex mutex;
	struct hrtimer hrtimer;
	ktime_t expires;
	struct clk *clock;
};

static inline void llcc_bcast_write(struct llcc_perfmon_private *llcc_priv,
@@ -514,14 +517,24 @@ static ssize_t perfmon_start_store(struct device *dev,
	struct llcc_perfmon_private *llcc_priv = dev_get_drvdata(dev);
	uint32_t val = 0, mask;
	unsigned long start;
	int ret;

	if (kstrtoul(buf, 10, &start))
		return -EINVAL;

	mutex_lock(&llcc_priv->mutex);
	if (start) {
		if (!llcc_priv->configured_counters)
		if (!llcc_priv->configured_counters) {
			pr_err("start failed. perfmon not configured\n");
			mutex_unlock(&llcc_priv->mutex);
			return -EINVAL;
		}

		ret = clk_prepare_enable(llcc_priv->clock);
		if (ret) {
			mutex_unlock(&llcc_priv->mutex);
			return -EINVAL;
		}

		val = MANUAL_MODE | MONITOR_EN;
		if (llcc_priv->expires) {
@@ -545,6 +558,8 @@ static ssize_t perfmon_start_store(struct device *dev,
	mask = PERFMON_MODE_MONITOR_MODE_MASK | PERFMON_MODE_MONITOR_EN_MASK;
	llcc_bcast_modify(llcc_priv, PERFMON_MODE, val, mask);

	if (!start)
		clk_disable_unprepare(llcc_priv->clock);

	mutex_unlock(&llcc_priv->mutex);
	return count;
@@ -1148,6 +1163,12 @@ static int llcc_perfmon_probe(struct platform_device *pdev)
		return result;
	}

	llcc_priv->clock = devm_clk_get(&pdev->dev, "qdss_clk");
	if (IS_ERR(llcc_priv->clock)) {
		pr_err("failed to get clock node\n");
		return PTR_ERR(llcc_priv->clock);
	}

	result = sysfs_create_group(&pdev->dev.kobj, &llcc_perfmon_group);
	if (result) {
		pr_err("Unable to create sysfs version group\n");