From patchwork Fri Jan 22 08:40:29 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "pi-cheng.chen" X-Patchwork-Id: 60125 Delivered-To: patch@linaro.org Received: by 10.112.130.2 with SMTP id oa2csp510336lbb; Fri, 22 Jan 2016 00:41:20 -0800 (PST) X-Received: by 10.66.102.8 with SMTP id fk8mr2672288pab.24.1453452070042; Fri, 22 Jan 2016 00:41:10 -0800 (PST) Return-Path: Received: from vger.kernel.org (vger.kernel.org. [209.132.180.67]) by mx.google.com with ESMTP id a90si8222641pfj.20.2016.01.22.00.41.09; Fri, 22 Jan 2016 00:41:10 -0800 (PST) Received-SPF: pass (google.com: best guess record for domain of devicetree-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) client-ip=209.132.180.67; Authentication-Results: mx.google.com; spf=pass (google.com: best guess record for domain of devicetree-owner@vger.kernel.org designates 209.132.180.67 as permitted sender) smtp.mailfrom=devicetree-owner@vger.kernel.org; dkim=neutral (body hash did not verify) header.i=@linaro.org Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1752733AbcAVIlJ (ORCPT + 6 others); Fri, 22 Jan 2016 03:41:09 -0500 Received: from mail-pf0-f180.google.com ([209.85.192.180]:35268 "EHLO mail-pf0-f180.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751818AbcAVIlH (ORCPT ); Fri, 22 Jan 2016 03:41:07 -0500 Received: by mail-pf0-f180.google.com with SMTP id 65so38545049pff.2 for ; Fri, 22 Jan 2016 00:41:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:cc:subject:date:message-id:in-reply-to:references; bh=P9W0mI7xYnBvzFRyZbemoTk/3COx/YcNQSujVEG5AEY=; b=hiv6EnU1M3lg/xBmiGWKzsan45dPKx3JC/RgNH6nGs8WPVMxTLHlzlfGbW7sOsSEgG pVlnLf/saOpXfT64VezH4aWwUkCY9PdRuANJWW+8RJv44Lbtab5sxUj8oeMrFMmSnnEo oWmb4/nZ+q5lRRjPrjOhtghV5MZVEEe4CnGHA= X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=P9W0mI7xYnBvzFRyZbemoTk/3COx/YcNQSujVEG5AEY=; b=ELuPhqKpZE/XhhJNcHog71ThH7y1wYVBKUWISb+LXACneOqsnKS0k41Ta+V2I7/KAn 84d7pJQ4UZ9yaDUxMhxlWmINyjMVz9iFxFQ8va3mdwAdl/eK4PkT77AkUM7DCixtYdy+ MtLtPobxVh4NAn9QgzzOOI8/dli5/Wr6INXhkMy/LqlsOxY0d9qPlqhPYKObqa7gCYIl ao3IUoV/s5HexXvUQ1eq+CFw2sqJxH4L7GYqziScZSbhNL9POJYHJ9NlPzwiaiJpTtMR Ntv/HFXM6in64kJ7wAVIq86gPZGlGmVpceW1OkOXz03u713fxJMO83cswnwteYJ/J44m rv4g== X-Gm-Message-State: AG10YORvuJjKmkXGm8yJlevZMQLcCCDa60CZHktqq24nEhbfvNQ/HcrImyuRdx3lRMMEpeSq X-Received: by 10.98.10.81 with SMTP id s78mr2650232pfi.119.1453452067268; Fri, 22 Jan 2016 00:41:07 -0800 (PST) Received: from localhost.localdomain ([124.219.30.17]) by smtp.googlemail.com with ESMTPSA id ty5sm7761114pac.48.2016.01.22.00.41.03 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 22 Jan 2016 00:41:06 -0800 (PST) From: Pi-Cheng Chen To: Nishanth Menon , Eduardo Valentin , Viresh Kumar , Rob Herring , Sascha Hauer Cc: Kevin Hilman , Matthias Brugger , linux-arm-kernel@lists.infradead.org, linux-mediatek@lists.infradead.org, linux-pm@vger.kernel.org, devicetree@vger.kernel.org, Stephen Boyd Subject: [PATCH 5/5] cpufreq: mt8173: Add notifier to handle OPP voltage adjustment Date: Fri, 22 Jan 2016 16:40:29 +0800 Message-Id: <1453452029-20843-6-git-send-email-pi-cheng.chen@linaro.org> X-Mailer: git-send-email 1.9.1 In-Reply-To: <1453452029-20843-1-git-send-email-pi-cheng.chen@linaro.org> References: <1453452029-20843-1-git-send-email-pi-cheng.chen@linaro.org> Sender: devicetree-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: devicetree@vger.kernel.org Add a notifier to receive OPP voltage adjustment event which is triggered by voltage change of OPP entries done by Mediatek SVS (Smart Voltage Scaling) engine. CC: Stephen Boyd Signed-off-by: Pi-Cheng Chen --- This patch is modify from the patch which adds[1] a notifier in cpufreq-dt to handle OPP voltage adjust event. This patch relies on the on the runtime voltage adjustment mechanism of OPP introduced in the same patchset. [1] https://lkml.org/lkml/2015/9/18/833 --- drivers/cpufreq/mt8173-cpufreq.c | 55 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 55 insertions(+) -- 1.9.1 -- To unsubscribe from this list: send the line "unsubscribe devicetree" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html diff --git a/drivers/cpufreq/mt8173-cpufreq.c b/drivers/cpufreq/mt8173-cpufreq.c index 1ede917..248f6e8 100644 --- a/drivers/cpufreq/mt8173-cpufreq.c +++ b/drivers/cpufreq/mt8173-cpufreq.c @@ -48,8 +48,11 @@ struct mtk_cpu_dvfs_info { struct clk *cpu_clk; struct clk *inter_clk; struct thermal_cooling_device *cdev; + struct mutex lock; + struct notifier_block opp_nb; struct list_head list_head; int intermediate_voltage; + unsigned long opp_freq; bool need_voltage_tracking; }; @@ -211,6 +214,33 @@ static int mtk_cpufreq_set_voltage(struct mtk_cpu_dvfs_info *info, int vproc) vproc + VOLT_TOL); } +static int mtk_cpufreq_opp_notifier(struct notifier_block *nb, + unsigned long event, void *data) +{ + struct dev_pm_opp *opp = data; + struct mtk_cpu_dvfs_info *info = container_of(nb, + struct mtk_cpu_dvfs_info, + opp_nb); + unsigned long freq, volt; + int ret = 0; + + if (event == OPP_EVENT_ADJUST_VOLTAGE) { + freq = dev_pm_opp_get_freq(opp); + + if (info->opp_freq == freq) { + volt = dev_pm_opp_get_voltage(opp); + mutex_lock(&info->lock); + ret = mtk_cpufreq_set_voltage(info, volt); + mutex_unlock(&info->lock); + if (ret) + dev_err(info->cpu_dev, + "failed to scale voltage: %d\n", ret); + } + } + + return notifier_from_errno(ret); +} + static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, unsigned int index) { @@ -245,6 +275,8 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, vproc = dev_pm_opp_get_voltage(opp); rcu_read_unlock(); + mutex_lock(&info->lock); + /* * If the new voltage or the intermediate voltage is higher than the * current voltage, scale up voltage first. @@ -256,6 +288,7 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, pr_err("cpu%d: failed to scale up voltage!\n", policy->cpu); mtk_cpufreq_set_voltage(info, old_vproc); + mutex_unlock(&info->lock); return ret; } } @@ -267,6 +300,7 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, policy->cpu); mtk_cpufreq_set_voltage(info, old_vproc); WARN_ON(1); + mutex_unlock(&info->lock); return ret; } @@ -277,6 +311,7 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, policy->cpu); clk_set_parent(cpu_clk, armpll); mtk_cpufreq_set_voltage(info, old_vproc); + mutex_unlock(&info->lock); return ret; } @@ -287,6 +322,7 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, policy->cpu); mtk_cpufreq_set_voltage(info, inter_vproc); WARN_ON(1); + mutex_unlock(&info->lock); return ret; } @@ -302,10 +338,14 @@ static int mtk_cpufreq_set_target(struct cpufreq_policy *policy, clk_set_parent(cpu_clk, info->inter_clk); clk_set_rate(armpll, old_freq_hz); clk_set_parent(cpu_clk, armpll); + mutex_unlock(&info->lock); return ret; } } + info->opp_freq = freq_hz; + mutex_unlock(&info->lock); + return 0; } @@ -343,6 +383,7 @@ static int mtk_cpu_dvfs_info_init(struct mtk_cpu_dvfs_info *info, int cpu) struct dev_pm_opp *opp; unsigned long rate; int ret; + struct srcu_notifier_head *opp_srcu_head; cpu_dev = get_cpu_device(cpu); if (!cpu_dev) { @@ -417,11 +458,25 @@ static int mtk_cpu_dvfs_info_init(struct mtk_cpu_dvfs_info *info, int cpu) info->intermediate_voltage = dev_pm_opp_get_voltage(opp); rcu_read_unlock(); + opp_srcu_head = dev_pm_opp_get_notifier(cpu_dev); + if (IS_ERR(opp_srcu_head)) { + ret = PTR_ERR(opp_srcu_head); + goto out_free_opp_table; + } + + info->opp_nb.notifier_call = mtk_cpufreq_opp_notifier; + ret = srcu_notifier_chain_register(opp_srcu_head, &info->opp_nb); + if (ret) + goto out_free_opp_table; + info->cpu_dev = cpu_dev; info->proc_reg = proc_reg; info->sram_reg = IS_ERR(sram_reg) ? NULL : sram_reg; info->cpu_clk = cpu_clk; info->inter_clk = inter_clk; + info->opp_freq = clk_get_rate(cpu_clk); + + mutex_init(&info->lock); /* * If SRAM regulator is present, software "voltage tracking" is needed