From patchwork Mon Aug 22 04:50:39 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Yang Ling X-Patchwork-Id: 9293001 X-Patchwork-Delegate: sboyd@codeaurora.org Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 08696607F0 for ; Mon, 22 Aug 2016 04:50:44 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id EF2A5284F1 for ; Mon, 22 Aug 2016 04:50:43 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id E34CB2886E; Mon, 22 Aug 2016 04:50:43 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.8 required=2.0 tests=BAYES_00, DKIM_ADSP_CUSTOM_MED, DKIM_SIGNED, FREEMAIL_FROM, RCVD_IN_DNSWL_HI, T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 736C3284F1 for ; Mon, 22 Aug 2016 04:50:42 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1753431AbcHVEum (ORCPT ); Mon, 22 Aug 2016 00:50:42 -0400 Received: from mail-pf0-f193.google.com ([209.85.192.193]:34004 "EHLO mail-pf0-f193.google.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751736AbcHVEul (ORCPT ); Mon, 22 Aug 2016 00:50:41 -0400 Received: by mail-pf0-f193.google.com with SMTP id g202so5591837pfb.1; Sun, 21 Aug 2016 21:50:41 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=date:from:to:cc:subject:message-id:mime-version:content-disposition :user-agent; bh=upW2vr8mnv5WEblHfoPvbhYidJWqLYNG5mLbTkRisNI=; b=UgI0X+XiJkvoGq/YioP+foklpz0LeJrS1hcHHQB57hkYt6ZjWgQ5ipvusccxKJ1Y8d azcd+S3uDHCKdSnlrPSF9575YoIiCvhiZKACiV8cuD4h4DbzMOryD0GyIEGVKd8vz+eh pAUGjeh//YZloPTO9OnptiGGMtgDkIaDYDDOksuTrMQ123V2PIp+3MTCBbzXqzY6SH90 2TUDMV677VHb3xjDybm+DPyWzqqlCOel98dN1pLlXU9xbGP4c3wB7qvj40NDk+DegURF IiDcSKC48fmk5D8ZEvTfYtlJgrUQMpG0uERbWAEy4wRwLrqz34tB3tYY5kalGM9fSuhv dbwg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:date:from:to:cc:subject:message-id:mime-version :content-disposition:user-agent; bh=upW2vr8mnv5WEblHfoPvbhYidJWqLYNG5mLbTkRisNI=; b=ZlwovwKd4mrc3+vvIxh78ke/afBDEsLs5Gk0QH/DmNnWtvGxd+XIHg/MCTxY3kSIe3 GjItpuJg/XM3lUbN6usolO/u10lcK3aU1tDDPp0nh/jZuCcs64TcI5NflaVZwkpiGqF3 roQzl+pUsJHgi6nHo8Z0oPHo9dedyHWPR7emerCE9MPppbd0V5oVWFUZS3wLeOllQT+6 qj34umsePRa0/DvYV5ATpMqkblYdCU7V1lETF753Ls3+AJn+AWzxB/CcoX7lNJNH1MQZ 5GzwD1gsdwP2IO8TKRPpFioy46ABfdt256sIXk5P9JOEpsv4vyfHY6ydSA6RyXCGAvu5 1+GA== X-Gm-Message-State: AEkoousRfqMgKlsDX+4KlLv+lrYmylFkvsecAcDNGeT1dQX6NQ8vxO6itHhV7AhgtztTuw== X-Received: by 10.98.98.193 with SMTP id w184mr39364389pfb.120.1471841440722; Sun, 21 Aug 2016 21:50:40 -0700 (PDT) Received: from ly-pc ([114.221.236.83]) by smtp.gmail.com with ESMTPSA id d9sm28533631pan.7.2016.08.21.21.50.37 (version=TLS1_2 cipher=AES128-SHA bits=128/128); Sun, 21 Aug 2016 21:50:39 -0700 (PDT) Date: Mon, 22 Aug 2016 12:50:39 +0800 From: Yang Ling To: keguang.zhang@gmail.com, mturquette@baylibre.com, sboyd@codeaurora.org Cc: linux-mips@linux-mips.org, linux-clk@vger.kernel.org, linux-kernel@vger.kernel.org Subject: [PATCH v2] CLK: Add Loongson1C clock support Message-ID: <20160822045034.GA6545@ly-pc> MIME-Version: 1.0 Content-Disposition: inline User-Agent: Mutt/1.5.21 (2010-09-15) Sender: linux-clk-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-clk@vger.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP This patch adds clock support to Loongson1C SoC. Signed-off-by: Yang Ling --- V2: Use loongson1 generic clock interface. --- drivers/clk/loongson1/Makefile | 1 + drivers/clk/loongson1/clk-loongson1c.c | 102 +++++++++++++++++++++++++++++++++ 2 files changed, 103 insertions(+) create mode 100644 drivers/clk/loongson1/clk-loongson1c.c diff --git a/drivers/clk/loongson1/Makefile b/drivers/clk/loongson1/Makefile index 5a162a1..b7f6a16 100644 --- a/drivers/clk/loongson1/Makefile +++ b/drivers/clk/loongson1/Makefile @@ -1,2 +1,3 @@ obj-y += clk.o obj-$(CONFIG_LOONGSON1_LS1B) += clk-loongson1b.o +obj-$(CONFIG_LOONGSON1_LS1C) += clk-loongson1c.o diff --git a/drivers/clk/loongson1/clk-loongson1c.c b/drivers/clk/loongson1/clk-loongson1c.c new file mode 100644 index 0000000..7e7e5ff --- /dev/null +++ b/drivers/clk/loongson1/clk-loongson1c.c @@ -0,0 +1,102 @@ +/* + * Copyright (c) 2016 Yang Ling + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License as published by the + * Free Software Foundation; either version 2 of the License, or (at your + * option) any later version. + */ + +#include +#include + +#include +#include "clk.h" + +#define OSC (24 * 1000000) +#define DIV_APB 1 + +static DEFINE_SPINLOCK(_lock); + +static unsigned long ls1x_pll_recalc_rate(struct clk_hw *hw, + unsigned long parent_rate) +{ + u32 pll, rate; + + pll = __raw_readl(LS1X_CLK_PLL_FREQ); + rate = ((pll >> 8) & 0xff) + ((pll >> 16) & 0xff); + rate *= OSC; + rate >>= 2; + + return rate; +} + +static const struct clk_ops ls1x_pll_clk_ops = { + .enable = ls1x_pll_clk_enable, + .disable = ls1x_pll_clk_disable, + .recalc_rate = ls1x_pll_recalc_rate, +}; + +static const char *const cpu_parents[] = { "cpu_clk_div", "osc_clk", }; +static const char *const ahb_parents[] = { "ahb_clk_div", "osc_clk", }; +static const char *const dc_parents[] = { "dc_clk_div", "osc_clk", }; + +static const struct clk_div_table ahb_div_table[] = { + [0] = { .val = 0, .div = 2 }, + [1] = { .val = 1, .div = 4 }, + [2] = { .val = 2, .div = 3 }, + [3] = { .val = 3, .div = 3 }, +}; + +void __init ls1x_clk_init(void) +{ + struct clk *clk; + + clk = clk_register_fixed_rate(NULL, "osc_clk", NULL, 0, OSC); + clk_register_clkdev(clk, "osc_clk", NULL); + + /* clock derived from 24 MHz OSC clk */ + clk = clk_register_pll(NULL, "pll_clk", "osc_clk", + &ls1x_pll_clk_ops, 0); + clk_register_clkdev(clk, "pll_clk", NULL); + + clk = clk_register_divider(NULL, "cpu_clk_div", "pll_clk", + CLK_GET_RATE_NOCACHE, LS1X_CLK_PLL_DIV, + DIV_CPU_SHIFT, DIV_CPU_WIDTH, + CLK_DIVIDER_ONE_BASED | + CLK_DIVIDER_ROUND_CLOSEST, &_lock); + clk_register_clkdev(clk, "cpu_clk_div", NULL); + clk = clk_register_fixed_factor(NULL, "cpu_clk", "cpu_clk_div", + 0, 1, 1); + clk_register_clkdev(clk, "cpu_clk", NULL); + + clk = clk_register_divider(NULL, "dc_clk_div", "pll_clk", + 0, LS1X_CLK_PLL_DIV, DIV_DC_SHIFT, + DIV_DC_WIDTH, CLK_DIVIDER_ONE_BASED, &_lock); + clk_register_clkdev(clk, "dc_clk_div", NULL); + clk = clk_register_fixed_factor(NULL, "dc_clk", "dc_clk_div", 0, 1, 1); + clk_register_clkdev(clk, "dc_clk", NULL); + + clk = clk_register_divider_table(NULL, "ahb_clk_div", "cpu_clk_div", + 0, LS1X_CLK_PLL_FREQ, DIV_DDR_SHIFT, + DIV_DDR_WIDTH, CLK_DIVIDER_ALLOW_ZERO, + ahb_div_table, &_lock); + clk_register_clkdev(clk, "ahb_clk_div", NULL); + clk = clk_register_fixed_factor(NULL, "ahb_clk", "ahb_clk_div", + 0, 1, 1); + clk_register_clkdev(clk, "ahb_clk", NULL); + clk_register_clkdev(clk, "ls1x-dma", NULL); + clk_register_clkdev(clk, "stmmaceth", NULL); + + /* clock derived from AHB clk */ + clk = clk_register_fixed_factor(NULL, "apb_clk", "ahb_clk", 0, 1, + DIV_APB); + clk_register_clkdev(clk, "apb_clk", NULL); + clk_register_clkdev(clk, "ls1x-ac97", NULL); + clk_register_clkdev(clk, "ls1x-i2c", NULL); + clk_register_clkdev(clk, "ls1x-nand", NULL); + clk_register_clkdev(clk, "ls1x-pwmtimer", NULL); + clk_register_clkdev(clk, "ls1x-spi", NULL); + clk_register_clkdev(clk, "ls1x-wdt", NULL); + clk_register_clkdev(clk, "serial8250", NULL); +}