lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite for Android: free password hash cracker in your pocket
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <8ae988c2-68f5-603e-843b-9cd70e4d4349@amlogic.com>
Date:   Mon, 14 Oct 2019 21:42:32 +0800
From:   Jian Hu <jian.hu@...ogic.com>
To:     Jerome Brunet <jbrunet@...libre.com>,
        Stephen Boyd <sboyd@...nel.org>
CC:     Neil Armstrong <narmstrong@...libre.com>,
        Jianxin Pan <jianxin.pan@...ogic.com>,
        Kevin Hilman <khilman@...libre.com>,
        Martin Blumenstingl <martin.blumenstingl@...glemail.com>,
        Michael Turquette <mturquette@...libre.com>,
        Qiufang Dai <qiufang.dai@...ogic.com>,
        <linux-clk@...r.kernel.org>, <linux-amlogic@...ts.infradead.org>,
        <linux-arm-kernel@...ts.infradead.org>,
        <linux-kernel@...r.kernel.org>, <devicetree@...r.kernel.org>
Subject: Re: [PATCH 2/2] clk: meson: a1: add support for Amlogic A1 clock
 driver

Hi, Jerome

sorry, it's my problem.

I did not discribe clearly the issue.

On 2019/10/11 15:39, Jerome Brunet wrote:
> 
> On Tue 08 Oct 2019 at 10:03, Jian Hu <jian.hu@...ogic.com> wrote:
> 
>> Hi, Jerome
>>
>> PLL clocks and peripheral clocks rely on each other.
>>
>> for fixed_pll, we can describe its parent like this:
>>
>> xtal-->xtal_fixpll-->fixed_dco-->fixed_pll
>>
>> xtal fixpll is belong to peripheral region.
>> fixed_pll/fclk_div2/fclk_div3 is belong to PLL region.
>>
>> if PLL clocks probe first, it will fail to get xtal_fixpll.
>> we can not get fixed_dco's parent clock.
>>
>> if peripheral clocks probe first, it will fail to get
>> fixed_pll clocks. A lot of peripheral clocks parent are fclk_div2/3/5/7.
>> and we can not get fclk_div2/3/5/7 clocks.
> 
> What does "fail" mean ?
> I intended to get clock using devm_clk_get API in each driver, In this 
scene,it will get failed because of the clock not being reigstered. In 
fact, we could not use devm_clk_get.
>>
>> I can think of two solutions:
>> 1) Do not describe xtal_fixpll, xtal_hifipll.
>>     that is to say, do not decribe the SYS_OSCIN_CTRL register.
>>
>> 2) Put peripheral and pll clock driver in one driver.
> 
> Those are work arounds. Actually fixing the problem is usually
> preferable.
> 
>   So if rephrase your problem:
> 
>   * We have 2 clock controllers (A and B)
>   * Clock are passed between the controllers using DT
>   * We have a PLL in controller B which is used by clocks in
>     controller A.
>   * the PLL parent clock is in controller A.
> 
Yeah, it is the scene.
> => So if I understand correctly you are saying that it will "fail"
> because there is a circular dependency between controller A and B, right
> ?
> 
> Do you have evidence that your problem comes from this circular
> dependency ?
> 
I have realized the peripheral driver and PLL drivers,

PLL driver probes first, Peripheral clock driver is the second.

In addition,for A1 SoC, it will not work using meson_clk_pll_ops,

it needs strictly sequence,so maybe another ops is required.hifi pll 
will be sent with sys pll and CPU clock driver.
> AFAIK, CCF will orphan the clock and continue if the parent is not
> available. Later, when the parent comes up, the orphan will be
> reparented.
> 
> IOW, the problem you are reporting should already be covered by CCF.
> 
>>
>> And  which sulution is better above two?
> 
> Neither, I'm afraid
> 
>>
>> Or maybe other good ideas for it?
> 
> My bet would be that an important clocks (maybe more than 1) is being
> gated during the init process.
> 
> Maybe you should try the command line parameter "clk_ignore_unused"
> until you get things running with your 2 controllers.
> 
>>
>> On 2019/9/29 17:38, Jian Hu wrote:
>>>
>>>
>>> On 2019/9/27 21:32, Jerome Brunet wrote:
>>>>
>>>> On Fri 27 Sep 2019 at 11:52, Jian Hu <jian.hu@...ogic.com> wrote:
>>>>
>>>>> Hi, Jerome
>>>>>
>>>>> Thank you for review.
>>>>>
>>>>> On 2019/9/25 23:09, Jerome Brunet wrote:
>>>>>> On Wed 25 Sep 2019 at 19:44, Jian Hu <jian.hu@...ogic.com> wrote:
>>>>>>
>>>>>>> The Amlogic A1 clock includes three parts:
>>>>>>> peripheral clocks, pll clocks, CPU clocks.
>>>>>>> sys pll and CPU clocks will be sent in next patch.
>>>>>>>
>>>>>>> Unlike the previous series, there is no EE/AO domain
>>>>>>> in A1 CLK controllers.
>>>>>>>
>>>>>>> Signed-off-by: Jian Hu <jian.hu@...ogic.com>
>>>>>>> Signed-off-by: Jianxin Pan <jianxin.pan@...ogic.com>
>>>>>>> ---
>>>>>>>     arch/arm64/Kconfig.platforms |    1 +
>>>>>>>     drivers/clk/meson/Kconfig    |   10 +
>>>>>>>     drivers/clk/meson/Makefile   |    1 +
>>>>>>>     drivers/clk/meson/a1.c       | 2617
>>>>>>> ++++++++++++++++++++++++++++++++++++++++++
>>>>>>>     drivers/clk/meson/a1.h       |  172 +++
>>>>>>>     5 files changed, 2801 insertions(+)
>>>>>>>     create mode 100644 drivers/clk/meson/a1.c
>>>>>>>     create mode 100644 drivers/clk/meson/a1.h
>>>>>>>
>> [...]
>>>>>>> diff --git a/drivers/clk/meson/a1.c b/drivers/clk/meson/a1.c
>>>>>>> new file mode 100644
>>>>>>> index 0000000..26edae0f
>>>>>>> --- /dev/null
>>>>>>> +++ b/drivers/clk/meson/a1.c
>>>>>>> @@ -0,0 +1,2617 @@
>>>>>>> +// SPDX-License-Identifier: (GPL-2.0+ OR MIT)
>>>>>>> +/*
>>>>>>> + * Copyright (c) 2019 Amlogic, Inc. All rights reserved.
>>>>>>> + */
>>>>>>> +
>>>>>>> +#include <linux/clk-provider.h>
>>>>>>> +#include <linux/init.h>
>>>>>>> +#include <linux/of_device.h>
>>>>>>> +#include <linux/platform_device.h>
>>>>>>> +#include <linux/of_address.h>
>>>>>>> +#include "clk-mpll.h"
>>>>>>> +#include "clk-pll.h"
>>>>>>> +#include "clk-regmap.h"
>>>>>>> +#include "vid-pll-div.h"
>>>>>>> +#include "clk-dualdiv.h"
>>>>>>> +#include "meson-eeclk.h"
>>>>>>> +#include "a1.h"
>>>>>>> +
>>>>>>> +/* PLLs clock in gates, its parent is xtal */
>>>>>>> +static struct clk_regmap a1_xtal_clktree = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 0,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_clktree",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>
>>>>>> Is CCF even expected to touch this ever ? what about RO ops ?
>>>>>> Please review your other clocks with this in mind
>>>>>>
>>>>> the clock should not be changed at runtime.clk_regmap_gate_ro_ops
>>>>> is a good idea. Set RO ops and remove the CLK_IS_CRITICAL flag.
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_xtal_fixpll = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 1,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_fixpll",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_xtal_usb_phy = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 2,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_usb_phy",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>
>>>>>> How is an USB clock critical to the system ?
>>>>>> Please review your other clocks with comment in mind ...
>>>>> the usb clock does not affect the system,
>>>>> remove the CLK_IS_CRITICAL flag
>>>>>>
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_xtal_usb_ctrl = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 3,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_usb_ctrl",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>> the usb clock does not affect the system,
>>>>> remove the CLK_IS_CRITICAL flag
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_xtal_hifipll = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 4,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_hifipll",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>> CLK_IS_CRITICAL is need to lock hifi pll.
>>>>
>>>> That's not how CCF works, this falg is not ok here.
>>>> CCF will enable this clock before calling enable on your hifi pll
>>>>
>>> ok, I will remove it.
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_xtal_syspll = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 5,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_syspll",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>> when CPU clock is at fixed clock, sys pll
>>>>> will be disabled, xtal_syspll will be disabled too.
>>>>> when setting sys pll, call clk_set_rate to lock
>>>>> sys pll, add RO ops to avoid disabling the clock
>>>>
>>>> Again not Ok.
>>>> If you mechanism to lock the PLL is properly implemented in the enable
>>>> callback of the sys pll, still kind of work around are not needed
>>>>
>>>> This has worked on the pll we had so far.
>>>>
>>> ok, I will remove it.
>>>>>
>>>>>>> +static struct clk_regmap a1_xtal_dds = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = SYS_OSCIN_CTRL,
>>>>>>> +        .bit_idx = 6,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "xtal_dds",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_data = &(const struct clk_parent_data) {
>>>>>>> +            .fw_name = "xtal",
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>> CLK_IS_CRITICAL is need to lock dds
>>>>>>> +
>>>>>>> +/* fixed pll = 1536M
>>>>>>> + *
>>>>>>> + * fixed pll ----- fclk_div2 = 768M
>>>>>>> + *           |
>>>>>>> + *           ----- fclk_div3 = 512M
>>>>>>> + *           |
>>>>>>> + *           ----- fclk_div5 = 307.2M
>>>>>>> + *           |
>>>>>>> + *           ----- fclk_div7 = 219.4M
>>>>>>> + */
>>>>>>
>>>>>> The framework will make those calculation ... you can remove this
>>>>>>
>>>>> ok, I will remote the comment.
>>>>>>> +static struct clk_regmap a1_fixed_pll_dco = {
>>>>>>> +    .data = &(struct meson_clk_pll_data){
>>>>>>> +        .en = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +            .shift   = 28,
>>>>>>> +            .width   = 1,
>>>>>>> +        },
>>>>>>> +        .m = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +            .shift   = 0,
>>>>>>> +            .width   = 8,
>>>>>>> +        },
>>>>>>> +        .n = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +            .shift   = 10,
>>>>>>> +            .width   = 5,
>>>>>>> +        },
>>>>>>> +        .frac = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL1,
>>>>>>> +            .shift   = 0,
>>>>>>> +            .width   = 19,
>>>>>>> +        },
>>>>>>> +        .l = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +            .shift   = 31,
>>>>>>> +            .width   = 1,
>>>>>>> +        },
>>>>>>> +        .rst = {
>>>>>>> +            .reg_off = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +            .shift   = 29,
>>>>>>> +            .width   = 1,
>>>>>>> +        },
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fixed_pll_dco",
>>>>>>> +        .ops = &meson_clk_pll_ro_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_xtal_fixpll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_fixed_pll = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +        .bit_idx = 20,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data) {
>>>>>>> +        .name = "fixed_pll",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fixed_pll_dco.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        .flags = CLK_IGNORE_UNUSED,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static const struct pll_params_table a1_hifi_pll_params_table[] = {
>>>>>>> +    PLL_PARAMS(128, 5), /* DCO = 614.4M */
>>>>>>> +};
>>>>>>> +
>>>>>>> +static const struct reg_sequence a1_hifi_init_regs[] = {
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL1,    .def = 0x01800000 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL2,    .def = 0x00001100 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL3,    .def = 0x10022200 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL4,    .def = 0x00301000 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL0, .def = 0x01f19480 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL0, .def = 0x11f19480, .delay_us =
>>>>>>> 10 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL0,    .def = 0x15f11480, .delay_us
>>>>>>> = 40 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL2,    .def = 0x00001140 },
>>>>>>> +    { .reg = ANACTRL_HIFIPLL_CTRL2,    .def = 0x00001100 },
>>>>>>> +};
>>>>>>> +
>>>>>>> +/*
>>>>>>> + * The Meson A1 HIFI PLL is 614.4M, it requires
>>>>>>> + * a strict register sequence to enable the PLL.
>>>>>>> + * set meson_clk_pcie_pll_ops as its ops
>>>>>>> + */
>>>>>>
>>>>>> Could you elaborate on this ? What need to be done to enable the clock
>>>>>> ?
>>>>>> Also the HIFI PLL used to be able to do a *LOT* of different rate which
>>>>>> might be desirable for audio use case. Why is this one restricted to
>>>>>> one
>>>>>> particular rate ?
>>>>>>
>>>>> The audio working frequency are 44.1khz, 48khz and 192khz.
>>>>>
>>>>> 614.4M can meet the three frequency.
>>>>>
>>>>> after the hifi pll, there are two dividers in Audio clock.
>>>>>
>>>>> 614.4M/3200 = 192khz
>>>>>
>>>>> 614.4M/12800 = 48khz
>>>>>
>>>>> 614,4M/13932 = 44.0999khz
>>>>
>>>> It does not really answer my question though.
>>>> You are locking a use case here, which is 32 bit sample width
>>>>
>>>> We have other constraint with the upstream audio driver, and we usually
>>>> looking for base frequency that a multiple of 768 (24*32).
>>>>
>>>> If you need your PLL to be set to a particular rate for a use case, the
>>>> correct way is "assigned-rate" in DT
>>>>
>>>> so the question still stands, the HIFI pll before was pretty easy to set
>>>> at a wide variety of rate (same as GP0) ... is it not the case anymore ?
>>>> If yes, could you decribe the constraints.
>>>>
>>>> All this took us a long time to figure out on our own, which is why I'd
>>>> prefer to get the proper constraints in from the beginning this time
>>>>
>>> ok, I will verify it and  describe the constraints about it
>>>>
>>>>>
>>>>>>> +static struct clk_regmap a1_hifi_pll = {
>>>>>>> +    .data = &(struct meson_clk_pll_data){
>>>>>>> +        .en = {
>>>>>>> +            .reg_off = ANACTRL_HIFIPLL_CTRL0,
>>>>>>> +            .shift   = 28,
>>>>>>> +            .width   = 1,
>>>>>>> +        },
>>>>>>> +        .m = {
>>>>>>> +            .reg_off = ANACTRL_HIFIPLL_CTRL0,
>>>>>>> +            .shift   = 0,
>>>>>>> +            .width   = 8,
>>>>>>> +        },
>>>>>>> +        .n = {
>>>>>>> +            .reg_off = ANACTRL_HIFIPLL_CTRL0,
>>>>>>> +            .shift   = 10,
>>>>>>> +            .width   = 5,
>>>>>>> +        },
>>>>>>> +        .frac = {
>>>>>>> +            .reg_off = ANACTRL_HIFIPLL_CTRL1,
>>>>>>> +            .shift   = 0,
>>>>>>> +            .width   = 19,
>>>>>>> +        },
>>>>>>> +        .l = {
>>>>>>> +            .reg_off = ANACTRL_HIFIPLL_STS,
>>>>>>> +            .shift   = 31,
>>>>>>> +            .width   = 1,
>>>>>>> +        },
>>>>>>> +        .table = a1_hifi_pll_params_table,
>>>>>>> +        .init_regs = a1_hifi_init_regs,
>>>>>>> +        .init_count = ARRAY_SIZE(a1_hifi_init_regs),
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "hifi_pll",
>>>>>>> +        .ops = &meson_clk_pcie_pll_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_xtal_hifipll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_fixed_factor a1_fclk_div2_div = {
>>>>>>> +    .mult = 1,
>>>>>>> +    .div = 2,
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div2_div",
>>>>>>> +        .ops = &clk_fixed_factor_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fixed_pll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_fclk_div2 = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +        .bit_idx = 21,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div2",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fclk_div2_div.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        /*
>>>>>>> +         * add CLK_IS_CRITICAL flag to avoid being disabled by clk
>>>>>>> core
>>>>>>> +         * or its children clocks.
>>>>>>> +         */
>>>>>>
>>>>>> The meaning of this flag is already documented in clk-provider.h
>>>>>> The reason why you need this flag is lot more interesting here ...
>>>>>>
>>>>>> Same below
>>>>> ok, I will replace new comments here.
>>>>>>
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_fixed_factor a1_fclk_div3_div = {
>>>>>>> +    .mult = 1,
>>>>>>> +    .div = 3,
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div3_div",
>>>>>>> +        .ops = &clk_fixed_factor_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fixed_pll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_fclk_div3 = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +        .bit_idx = 22,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div3",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fclk_div3_div.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        /*
>>>>>>> +         * add CLK_IS_CRITICAL flag to avoid being disabled by clk
>>>>>>> core
>>>>>>> +         * its children clocks.
>>>>>>> +         */
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_fixed_factor a1_fclk_div5_div = {
>>>>>>> +    .mult = 1,
>>>>>>> +    .div = 5,
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div5_div",
>>>>>>> +        .ops = &clk_fixed_factor_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fixed_pll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_fclk_div5 = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +        .bit_idx = 23,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div5",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fclk_div5_div.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        /*
>>>>>>> +         * add CLK_IS_CRITICAL flag to avoid being disabled by clk
>>>>>>> core
>>>>>>> +         * its children clocks.
>>>>>>> +         */
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_fixed_factor a1_fclk_div7_div = {
>>>>>>> +    .mult = 1,
>>>>>>> +    .div = 7,
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div7_div",
>>>>>>> +        .ops = &clk_fixed_factor_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fixed_pll.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>>>>>>> +static struct clk_regmap a1_fclk_div7 = {
>>>>>>> +    .data = &(struct clk_regmap_gate_data){
>>>>>>> +        .offset = ANACTRL_FIXPLL_CTRL0,
>>>>>>> +        .bit_idx = 23,
>>>>>>> +    },
>>>>>>> +    .hw.init = &(struct clk_init_data){
>>>>>>> +        .name = "fclk_div7",
>>>>>>> +        .ops = &clk_regmap_gate_ops,
>>>>>>> +        .parent_hws = (const struct clk_hw *[]) {
>>>>>>> +            &a1_fclk_div7_div.hw
>>>>>>> +        },
>>>>>>> +        .num_parents = 1,
>>>>>>> +        /*
>>>>>>> +         * add CLK_IS_CRITICAL flag to avoid being disabled by clk
>>>>>>> core
>>>>>>> +         * or its children clock.
>>>>>>> +         */
>>>>>>> +        .flags = CLK_IS_CRITICAL,
>>>>>>> +    },
>>>>>>> +};
>>>>>>> +
>> [...]
>>>>>>> -- 
>>>>>>> 1.9.1
>>>>>>
>>>>>> .
>>>>>>
>>>>
>>>> .
>>>>
> 
> .
> 

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ