From patchwork Tue Jan 27 12:16:57 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Luis Henriques X-Patchwork-Id: 433445 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from huckleberry.canonical.com (huckleberry.canonical.com [91.189.94.19]) by ozlabs.org (Postfix) with ESMTP id 8A90C14012A; Tue, 27 Jan 2015 23:26:20 +1100 (AEDT) Received: from localhost ([127.0.0.1] helo=huckleberry.canonical.com) by huckleberry.canonical.com with esmtp (Exim 4.76) (envelope-from ) id 1YG5Dk-0006qS-Qe; Tue, 27 Jan 2015 12:26:16 +0000 Received: from youngberry.canonical.com ([91.189.89.112]) by huckleberry.canonical.com with esmtp (Exim 4.76) (envelope-from ) id 1YG57g-0003uZ-Er for kernel-team@lists.ubuntu.com; Tue, 27 Jan 2015 12:20:00 +0000 Received: from av-217-129-142-138.netvisao.pt ([217.129.142.138] helo=localhost) by youngberry.canonical.com with esmtpsa (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1YG57g-0004hw-1M; Tue, 27 Jan 2015 12:20:00 +0000 From: Luis Henriques To: linux-kernel@vger.kernel.org, stable@vger.kernel.org, kernel-team@lists.ubuntu.com Subject: [PATCH 3.16.y-ckt 112/126] clk: at91: keep slow clk enabled to prevent system hang Date: Tue, 27 Jan 2015 12:16:57 +0000 Message-Id: <1422361031-19364-113-git-send-email-luis.henriques@canonical.com> X-Mailer: git-send-email 2.1.4 In-Reply-To: <1422361031-19364-1-git-send-email-luis.henriques@canonical.com> References: <1422361031-19364-1-git-send-email-luis.henriques@canonical.com> X-Extended-Stable: 3.16 Cc: Boris Brezillon , Michael Turquette X-BeenThere: kernel-team@lists.ubuntu.com X-Mailman-Version: 2.1.14 Precedence: list List-Id: Kernel team discussions List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Errors-To: kernel-team-bounces@lists.ubuntu.com Sender: kernel-team-bounces@lists.ubuntu.com 3.16.7-ckt5 -stable review patch. If anyone has any objections, please let me know. ------------------ From: Boris Brezillon commit dca1a4b5ff6e2c25adeff366eb06270dadeab3db upstream. All slow clk users are not properly claiming it (get + prepare + enable) before using it. If all users properly claiming this clock release it, the clock is disabled, but faulty users still depends on it, and the system hangs. This fix prevents the slow clock from being disabled, and should solve the hanging issue, but offending drivers should be patched to properly claim this clock. Signed-off-by: Boris Brezillon Reported-by: Bo Shen Signed-off-by: Michael Turquette Signed-off-by: Luis Henriques --- drivers/clk/at91/clk-slow.c | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) diff --git a/drivers/clk/at91/clk-slow.c b/drivers/clk/at91/clk-slow.c index 0300c46ee247..ef8d458cd74a 100644 --- a/drivers/clk/at91/clk-slow.c +++ b/drivers/clk/at91/clk-slow.c @@ -70,6 +70,7 @@ struct clk_sam9x5_slow { #define to_clk_sam9x5_slow(hw) container_of(hw, struct clk_sam9x5_slow, hw) +static struct clk *slow_clk; static int clk_slow_osc_prepare(struct clk_hw *hw) { @@ -357,6 +358,8 @@ at91_clk_register_sam9x5_slow(void __iomem *sckcr, clk = clk_register(NULL, &slowck->hw); if (IS_ERR(clk)) kfree(slowck); + else + slow_clk = clk; return clk; } @@ -433,6 +436,8 @@ at91_clk_register_sam9260_slow(struct at91_pmc *pmc, clk = clk_register(NULL, &slowck->hw); if (IS_ERR(clk)) kfree(slowck); + else + slow_clk = clk; return clk; } @@ -465,3 +470,25 @@ void __init of_at91sam9260_clk_slow_setup(struct device_node *np, of_clk_add_provider(np, of_clk_src_simple_get, clk); } + +/* + * FIXME: All slow clk users are not properly claiming it (get + prepare + + * enable) before using it. + * If all users properly claiming this clock decide that they don't need it + * anymore (or are removed), it is disabled while faulty users are still + * requiring it, and the system hangs. + * Prevent this clock from being disabled until all users are properly + * requesting it. + * Once this is done we should remove this function and the slow_clk variable. + */ +static int __init of_at91_clk_slow_retain(void) +{ + if (!slow_clk) + return 0; + + __clk_get(slow_clk); + clk_prepare_enable(slow_clk); + + return 0; +} +arch_initcall(of_at91_clk_slow_retain);