* [PATCH] spi: atmel: use managed resource for gpio chip select
From: Nicolas Ferre @ 2016-11-07 13:54 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAMuHMdUQLkHn4=3U6TNjgTN--RUHZHsbwNu9dLdFrBJA0sx4aw@mail.gmail.com>
Le 21/09/2016 ? 10:20, Geert Uytterhoeven a ?crit :
> Hi Nicolas,
>
> On Wed, Sep 21, 2016 at 9:55 AM, Nicolas Ferre <nicolas.ferre@atmel.com> wrote:
>> Use the managed gpio CS pin request so that we avoid having trouble
>> in the cleanup code.
>> In fact, if module was configured with DT, cleanup code released
>> invalid pin. Since resource wasn't freed, module cannot be reinserted.
>>
>> Reported-by: Alexander Morozov <linux@meltdown.ru>
>> Signed-off-by: Nicolas Ferre <nicolas.ferre@atmel.com>
>> ---
>> drivers/spi/spi-atmel.c | 5 ++---
>> 1 file changed, 2 insertions(+), 3 deletions(-)
>>
>> diff --git a/drivers/spi/spi-atmel.c b/drivers/spi/spi-atmel.c
>> index 8feac599e9ab..4e3f2345844a 100644
>> --- a/drivers/spi/spi-atmel.c
>> +++ b/drivers/spi/spi-atmel.c
>> @@ -1248,7 +1248,8 @@ static int atmel_spi_setup(struct spi_device *spi)
>> return -ENOMEM;
>>
>> if (as->use_cs_gpios) {
>> - ret = gpio_request(npcs_pin, dev_name(&spi->dev));
>> + ret = devm_gpio_request(&spi->dev,
>> + npcs_pin, dev_name(&spi->dev));
>
> Note that spi_master.setup() can be called multiple times during the lifetime
> of the spi_device.
Sure, this is what I read in include/linux/spi/spi.h "It's always safe
to call this unless transfers are pending on the device whose settings
are being modified."
It also means that the whole memory allocation for devices that is done
a few lines above this gpio request is also completely wrong... This
function needs a serious refactoring.
Thanks for the heads-up.
Best regards,
>> if (ret) {
>> kfree(asd);
>> return ret;
>> @@ -1471,13 +1472,11 @@ static int atmel_spi_transfer_one_message(struct spi_master *master,
>> static void atmel_spi_cleanup(struct spi_device *spi)
>> {
>> struct atmel_spi_device *asd = spi->controller_state;
>> - unsigned gpio = (unsigned long) spi->controller_data;
>>
>> if (!asd)
>> return;
>>
>> spi->controller_state = NULL;
>> - gpio_free(gpio);
>> kfree(asd);
>> }
>
> Gr{oetje,eeting}s,
>
> Geert
>
> --
> Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert at linux-m68k.org
>
> In personal conversations with technical people, I call myself a hacker. But
> when I'm talking to journalists I just say "programmer" or something like that.
> -- Linus Torvalds
>
--
Nicolas Ferre
^ permalink raw reply
* [PATCH 1/6] clk: stm32f4: Add PLL_I2S & PLL_SAI for STM32F429/469 boards
From: Daniel Thompson @ 2016-11-07 13:53 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-2-git-send-email-gabriel.fernandez@st.com>
On 07/11/16 13:05, gabriel.fernandez at st.com wrote:
> From: Gabriel Fernandez <gabriel.fernandez@st.com>
>
> This patch introduces PLL_I2S and PLL_SAI.
> Vco clock of these PLLs can be modify by DT (only n multiplicator,
> m divider is still fixed by the boot-loader).
> Each PLL has 3 dividers. PLL should be off when we modify the rate.
>
> Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
> ---
> drivers/clk/clk-stm32f4.c | 371 ++++++++++++++++++++++++++++++++++++++++++++--
> 1 file changed, 359 insertions(+), 12 deletions(-)
>
> diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
> index c2661e2..7641acd 100644
> --- a/drivers/clk/clk-stm32f4.c
> +++ b/drivers/clk/clk-stm32f4.c
> @@ -28,6 +28,7 @@
> ...
> +static const struct clk_div_table pll_divp_table[] = {
> + { 0, 2 }, { 1, 4 }, { 2, 6 }, { 3, 8 },
> +};
> +
> /*
> * Decode current PLL state and (statically) model the state we inherit from
> * the bootloader.
> */
This comment isn't right. For a start the model is no longer static.
> @@ -615,18 +944,24 @@ struct stm32f4_clk_data {
> const struct stm32f4_gate_data *gates_data;
> const u64 *gates_map;
> int gates_num;
> + const struct stm32f4_pll_data *pll_data;
> + int pll_num;
pll_num is unused.
Daniel.
^ permalink raw reply
* [PATCH] serial: sirf: Simplify a test
From: Arnd Bergmann @ 2016-11-07 13:50 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20161101070333.12255-1-christophe.jaillet@wanadoo.fr>
On Tuesday, November 1, 2016 8:03:33 AM CET Christophe JAILLET wrote:
> 'dmaengine_prep_dma_cyclic()' does not return an error pointer, so the test
> can be simplified to be more consistent.
>
> Signed-off-by: Christophe JAILLET <christophe.jaillet@wanadoo.fr>
The change looks correct in principle. It would be good to automate looking
for other instances of this bug. How did you find it? Do you have e.g. a
coccinelle script or did you just stumble over the issue by accident?
There is one problem with your patch:
> drivers/tty/serial/sirfsoc_uart.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/drivers/tty/serial/sirfsoc_uart.c b/drivers/tty/serial/sirfsoc_uart.c
> index b186c9c4f850..666ca3156961 100644
> --- a/drivers/tty/serial/sirfsoc_uart.c
> +++ b/drivers/tty/serial/sirfsoc_uart.c
> @@ -609,7 +609,7 @@ static void sirfsoc_uart_start_next_rx_dma(struct uart_port *port)
> sirfport->rx_dma_items.dma_addr, SIRFSOC_RX_DMA_BUF_SIZE,
> SIRFSOC_RX_DMA_BUF_SIZE / 2,
> DMA_DEV_TO_MEM, DMA_PREP_INTERRUPT);
> - if (IS_ERR_OR_NULL(sirfport->rx_dma_items.desc)) {
> + if (!sirfport->rx_dma_items.desc) {
> dev_err(port->dev, "DMA slave single fail\n");
> return;
> }
The serial driver is for the sirf platform, which uses the sirf-dma
dmaengine driver, and that particular driver has an incorrect
dma_prep_cyclic implementation, so I think we also need this fix:
diff --git a/drivers/dma/sirf-dma.c b/drivers/dma/sirf-dma.c
index 8f62edad51be..220c611c89ae 100644
--- a/drivers/dma/sirf-dma.c
+++ b/drivers/dma/sirf-dma.c
@@ -775,7 +775,7 @@ sirfsoc_dma_prep_cyclic(struct dma_chan *chan, dma_addr_t addr,
* BUFB
*/
if (buf_len != 2 * period_len)
- return ERR_PTR(-EINVAL);
+ return NULL;
/* Get free descriptor */
spin_lock_irqsave(&schan->lock, iflags);
Arnd
^ permalink raw reply related
* [PATCH v4 0/3] ASoC/ARM: tegra: apalis t30/tk1/colibri t30: sgtl5000 audio
From: Thierry Reding @ 2016-11-07 13:42 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1471355726.4197.6.camel@toradex.com>
On Tue, Aug 16, 2016 at 01:55:28PM +0000, Marcel Ziswiler wrote:
> On Sun, 2016-06-19 at 02:59 +0200, Marcel Ziswiler wrote:
> > This series adds/integrates Freescale SGTL5000 analogue audio codec
> > support.
> >
> > Changes in v4:
> > - simple-audio-card does still not allow for more advanced use cases
> > ? like Tegra SoCs
> > - further platform drivers have been accepted since my last attempt
> > ? (e.g. rt5677 one)
> > - relevance for one further board the new Toradex Apalis TK1
> > - drop unused sound/jack.h include
> > - in tegra_sgtl5000_driver_remove() pass return value of
> > ? snd_soc_unregister_card() on to caller
> > - no longer set owner property in platform_driver to THIS_MODULE
> > - re-based/resend
> >
> > Changes in v3:
> > - revert to not using simple-audio-card being incompatible with tegra
> > - rebased to for-next
> >
> > Changes in v2:
> > - using simple-audio-card as suggested by Fabio
> >
> > Marcel Ziswiler (3):
> > ? ASoC: tegra: add tegra sgtl5000 machine driver
> > ? ARM: tegra: apalis/colibri t30: integrate audio
> > ? ARM: tegra: enable sgtl5000 audio
> >
> > ?.../bindings/sound/nvidia,tegra-audio-sgtl5000.txt |??42 ++++
> > ?arch/arm/boot/dts/tegra30-apalis.dtsi??????????????|??49 +++++
> > ?arch/arm/boot/dts/tegra30-colibri.dtsi?????????????|??49 +++++
> > ?arch/arm/configs/tegra_defconfig???????????????????|???1 +
> > ?sound/soc/tegra/Kconfig????????????????????????????|??11 ++
> > ?sound/soc/tegra/Makefile???????????????????????????|???2 +
> > ?sound/soc/tegra/tegra_sgtl5000.c???????????????????| 212
> > +++++++++++++++++++++
> > ?7 files changed, 366 insertions(+)
> > ?create mode 100644
> > Documentation/devicetree/bindings/sound/nvidia,tegra-audio-
> > sgtl5000.txt
> > ?create mode 100644 sound/soc/tegra/tegra_sgtl5000.c
>
> With Mark finally having pulled the first patch of this series (https:/
> /lkml.org/lkml/2016/8/15/297) I'm wondering whether the second and
> third patch are now being pulled via tegra tree? Or should I rather re-
> submit those as a new v5 patch set?
Both patches applied now, thanks.
Thierry
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20161107/2eb5a3a1/attachment-0001.sig>
^ permalink raw reply
* [PATCH] ARM: tegra: nyan: Enable GPU node and related supply
From: Thierry Reding @ 2016-11-07 13:29 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20160918141311.17140-1-contact@paulk.fr>
On Sun, Sep 18, 2016 at 04:13:11PM +0200, Paul Kocialkowski wrote:
> This enables the GPU node for tegra124 nyan boards, which is required to
> get graphics acceleration with nouveau on these devices.
>
> Signed-off-by: Paul Kocialkowski <contact@paulk.fr>
> ---
> arch/arm/boot/dts/tegra124-nyan.dtsi | 8 +++++++-
> 1 file changed, 7 insertions(+), 1 deletion(-)
Applied, thanks.
Thierry
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20161107/edbcbb97/attachment.sig>
^ permalink raw reply
* [PATCH] ARM: tegra: nyan: Mark all USB ports as host
From: Thierry Reding @ 2016-11-07 13:28 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <20160918102852.6593-1-contact@paulk.fr>
On Sun, Sep 18, 2016 at 12:28:52PM +0200, Paul Kocialkowski wrote:
> Nyan boards only have host USB ports (2 external, 1 internal), there is
> no OTG-enabled connector.
>
> Signed-off-by: Paul Kocialkowski <contact@paulk.fr>
> ---
> arch/arm/boot/dts/tegra124-nyan.dtsi | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
Where is this information coming from? I don't have one of the Nyans
myself, but one of the Tegra132 devices I have, which I think was
derived from one of the Nyans uses one of the external host ports as
forced recovery port, for which it would need OTG.
I suspect that the way to get U-Boot onto the Nyans is via tegrarcm?
In that case I think one of the ports must be OTG.
Thierry
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20161107/7889311c/attachment.sig>
^ permalink raw reply
* [PATCH v1 03/11] drivers: soc: hisi: Add support for Hisilicon Djtag driver
From: Arnd Bergmann @ 2016-11-07 13:26 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478101374-18778-4-git-send-email-anurup.m@huawei.com>
On Wednesday, November 2, 2016 11:42:46 AM CET Anurup M wrote:
> From: Tan Xiaojun <tanxiaojun@huawei.com>
>
> The Hisilicon Djtag is an independent component which connects
> with some other components in the SoC by Debug Bus. This driver
> can be configured to access the registers of connecting components
> (like L3 cache) during real time debugging.
The formatting of the text seems odd, please remove the leading spaces.
> drivers/soc/Kconfig | 1 +
> drivers/soc/Makefile | 1 +
> drivers/soc/hisilicon/Kconfig | 12 +
> drivers/soc/hisilicon/Makefile | 1 +
> drivers/soc/hisilicon/djtag.c | 639 ++++++++++++++++++++++++++++++++++++
> include/linux/soc/hisilicon/djtag.h | 38 +++
Do you expect other drivers to be added that reference this interface?
If not, or if you are unsure, just put all of it under drivers/perf
so we don't introduce a global API that has only one user.
> +
> +#include <linux/bitops.h>
> +#include <linux/init.h>
> +#include <linux/list.h>
> +#include <linux/module.h>
> +#include <linux/of.h>
> +#include <linux/of_address.h>
> +#include <linux/of_device.h>
> +#include <linux/platform_device.h>
> +#include <linux/slab.h>
> +#include <linux/spinlock.h>
> +
> +#include <asm-generic/delay.h>
Never include files from asm-generic directly except from
an architecture specific asm/*.h header file.
> +DEFINE_IDR(djtag_hosts_idr);
make this static
> +static void djtag_read32_relaxed(void __iomem *regs_base, u32 off, u32 *value)
> +{
> + void __iomem *reg_addr = regs_base + off;
> +
> + *value = readl_relaxed(reg_addr);
> +}
> +
> +static void djtag_write32(void __iomem *regs_base, u32 off, u32 val)
> +{
> + void __iomem *reg_addr = regs_base + off;
> +
> + writel(val, reg_addr);
> +}
This looks like an odd combination of interfaces.
Why can the reads be "relaxed" when the writes can not?
Generally speaking, I'd advise to always use non-relaxed accessors
unless there is a strong performance reason, and in that case there
should be a comment explaining the use at each of the callers
of a relaxed accessor.
> + /* ensure the djtag operation is done */
> + do {
> + djtag_read32_relaxed(regs_base, SC_DJTAG_MSTR_START_EN_EX, &rd);
> +
> + if (!(rd & DJTAG_MSTR_START_EN_EX))
> + break;
> +
> + udelay(1);
> + } while (timeout--);
This one is obviously not performance critical at all, so use a non-relaxed
accessor. Same for the other two in this function.
Are these functions ever called from atomic context? If yes, please document
from what context they can be called, otherwise please consider changing
the udelay calls into sleeping waits.
> +int hisi_djtag_writel(struct hisi_djtag_client *client, u32 offset, u32 mod_sel,
> + u32 mod_mask, u32 val)
> +{
> + void __iomem *reg_map = client->host->sysctl_reg_map;
> + unsigned long flags;
> + int ret = 0;
> +
> + spin_lock_irqsave(&client->host->lock, flags);
> + ret = client->host->djtag_readwrite(reg_map, offset, mod_sel, mod_mask,
> + true, val, 0, NULL);
> + if (ret)
> + pr_err("djtag_writel: error! ret=%d\n", ret);
> + spin_unlock_irqrestore(&client->host->lock, flags);
> +
> + return ret;
> +}
> +EXPORT_SYMBOL_GPL(hisi_djtag_writel);
That would of course imply changing the spinlock to a mutex here as well.
> +static const struct of_device_id djtag_of_match[] = {
> + /* for hip05(D02) cpu die */
> + { .compatible = "hisilicon,hip05-cpu-djtag-v1",
> + .data = (void *)djtag_readwrite_v1 },
> + /* for hip05(D02) io die */
> + { .compatible = "hisilicon,hip05-io-djtag-v1",
> + .data = (void *)djtag_readwrite_v1 },
> + /* for hip06(D03) cpu die */
> + { .compatible = "hisilicon,hip06-cpu-djtag-v1",
> + .data = (void *)djtag_readwrite_v1 },
> + /* for hip06(D03) io die */
> + { .compatible = "hisilicon,hip06-io-djtag-v2",
> + .data = (void *)djtag_readwrite_v2 },
> + /* for hip07(D05) cpu die */
> + { .compatible = "hisilicon,hip07-cpu-djtag-v2",
> + .data = (void *)djtag_readwrite_v2 },
> + /* for hip07(D05) io die */
> + { .compatible = "hisilicon,hip07-io-djtag-v2",
> + .data = (void *)djtag_readwrite_v2 },
> + {},
> +};
If these are backwards compatible, just mark them as compatible in DT,
e.g. hip06 can use
compatible = "hisilicon,hip06-cpu-djtag-v1", "hisilicon,hip05-cpu-djtag-v1";
so you can tell the difference if you need to, but the driver only has to
list the oldest one here.
What is the difference between the cpu and io djtag interfaces?
I think you can also drop the '(void *)'.
> +static void djtag_register_devices(struct hisi_djtag_host *host)
> +{
> + struct device_node *node;
> + struct hisi_djtag_client *client;
> +
> + if (!host->of_node)
> + return;
> +
> + for_each_available_child_of_node(host->of_node, node) {
> + if (of_node_test_and_set_flag(node, OF_POPULATED))
> + continue;
> + client = hisi_djtag_of_register_device(host, node);
> + list_add(&client->next, &host->client_list);
> + }
> +}
Can you explain your thoughts behind creating a new bus type
and adding the child devices manually rather than using
platform_device structures with of_platform_populate()?
Do you expect to see other implementations of this bus type
with incompatible bus drivers?
Arnd
^ permalink raw reply
* [PATCH 3/3] ARM: gr8: evb: Add i2s codec
From: Maxime Ripard @ 2016-11-07 13:08 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <cover.9296840e0b7438e0ae63b4ec0d64957640b64a78.1478524066.git-series.maxime.ripard@free-electrons.com>
The GR8-EVB comes with a wm8978 codec connected to the i2s bus.
Add a card in order to have it working
Signed-off-by: Maxime Ripard <maxime.ripard@free-electrons.com>
---
arch/arm/boot/dts/ntc-gr8-evb.dts | 14 ++++++++++++++
1 file changed, 14 insertions(+), 0 deletions(-)
diff --git a/arch/arm/boot/dts/ntc-gr8-evb.dts b/arch/arm/boot/dts/ntc-gr8-evb.dts
index 12b4317a4383..5291e425caf9 100644
--- a/arch/arm/boot/dts/ntc-gr8-evb.dts
+++ b/arch/arm/boot/dts/ntc-gr8-evb.dts
@@ -76,6 +76,20 @@
default-brightness-level = <8>;
};
+ i2s {
+ compatible = "simple-audio-card";
+ simple-audio-card,name = "gr8-evb-wm8978";
+ simple-audio-card,format = "i2s";
+ simple-audio-card,mclk-fs = <512>;
+
+ simple-audio-card,cpu {
+ sound-dai = <&i2s0>;
+ };
+
+ simple-audio-card,codec {
+ sound-dai = <&wm8978>;
+ };
+ };
panel {
compatible = "allwinner,sun4i-a10-sub-evb-5-lcd";
--
git-series 0.8.11
^ permalink raw reply related
* [PATCH 2/3] ASoC: wm8978: Adjust clock indices so that simple card works
From: Maxime Ripard @ 2016-11-07 13:08 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <cover.9296840e0b7438e0ae63b4ec0d64957640b64a78.1478524066.git-series.maxime.ripard@free-electrons.com>
Using simple-card with the wm8978 doesn't work because simple card calls
set_sysclk on the clock index 0, which is not the MCLK in the WM8978.
Adjust the clock definition so that the clock 0 is the MCLK.
Signed-off-by: Maxime Ripard <maxime.ripard@free-electrons.com>
---
sound/soc/codecs/wm8978.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/sound/soc/codecs/wm8978.h b/sound/soc/codecs/wm8978.h
index 6ae43495b7cf..0dcf6868dff6 100644
--- a/sound/soc/codecs/wm8978.h
+++ b/sound/soc/codecs/wm8978.h
@@ -78,8 +78,8 @@ enum wm8978_clk_id {
};
enum wm8978_sysclk_src {
+ WM8978_MCLK = 0,
WM8978_PLL,
- WM8978_MCLK
};
#endif /* __WM8978_H__ */
--
git-series 0.8.11
^ permalink raw reply related
* [PATCH 1/3] ASoC: sunxi: i2s: Implement set_sysclk
From: Maxime Ripard @ 2016-11-07 13:08 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <cover.9296840e0b7438e0ae63b4ec0d64957640b64a78.1478524066.git-series.maxime.ripard@free-electrons.com>
In our i2s driver, we were previously trying to guess which oversample the
user wanted to use by looking at the rate and trying to max it.
However, the cards, and especially simple-card with its mclk-fs property
will already provide the expected oversample ratio by using the set_sysclk
callback.
We can thus implement it and remove the logic to deal with the runtime
guess.
Signed-off-by: Maxime Ripard <maxime.ripard@free-electrons.com>
---
sound/soc/sunxi/sun4i-i2s.c | 53 +++++++++++++++++++++++++++-----------
1 file changed, 38 insertions(+), 15 deletions(-)
diff --git a/sound/soc/sunxi/sun4i-i2s.c b/sound/soc/sunxi/sun4i-i2s.c
index a7653114e895..f24d19526603 100644
--- a/sound/soc/sunxi/sun4i-i2s.c
+++ b/sound/soc/sunxi/sun4i-i2s.c
@@ -93,6 +93,8 @@ struct sun4i_i2s {
struct clk *mod_clk;
struct regmap *regmap;
+ unsigned int mclk_freq;
+
struct snd_dmaengine_dai_dma_data capture_dma_data;
struct snd_dmaengine_dai_dma_data playback_dma_data;
};
@@ -158,14 +160,24 @@ static int sun4i_i2s_get_mclk_div(struct sun4i_i2s *i2s,
}
static int sun4i_i2s_oversample_rates[] = { 128, 192, 256, 384, 512, 768 };
+static bool sun4i_i2s_oversample_is_valid(unsigned int oversample)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(sun4i_i2s_oversample_rates); i++)
+ if (sun4i_i2s_oversample_rates[i] == oversample)
+ return true;
+
+ return false;
+}
static int sun4i_i2s_set_clk_rate(struct sun4i_i2s *i2s,
unsigned int rate,
unsigned int word_size)
{
- unsigned int clk_rate;
+ unsigned int oversample_rate, clk_rate;
int bclk_div, mclk_div;
- int ret, i;
+ int ret;
switch (rate) {
case 176400:
@@ -197,21 +209,18 @@ static int sun4i_i2s_set_clk_rate(struct sun4i_i2s *i2s,
if (ret)
return ret;
- /* Always favor the highest oversampling rate */
- for (i = (ARRAY_SIZE(sun4i_i2s_oversample_rates) - 1); i >= 0; i--) {
- unsigned int oversample_rate = sun4i_i2s_oversample_rates[i];
-
- bclk_div = sun4i_i2s_get_bclk_div(i2s, oversample_rate,
- word_size);
- mclk_div = sun4i_i2s_get_mclk_div(i2s, oversample_rate,
- clk_rate,
- rate);
+ oversample_rate = i2s->mclk_freq / rate;
+ if (!sun4i_i2s_oversample_is_valid(oversample_rate))
+ return -EINVAL;
- if ((bclk_div >= 0) && (mclk_div >= 0))
- break;
- }
+ bclk_div = sun4i_i2s_get_bclk_div(i2s, oversample_rate,
+ word_size);
+ if (bclk_div < 0)
+ return -EINVAL;
- if ((bclk_div < 0) || (mclk_div < 0))
+ mclk_div = sun4i_i2s_get_mclk_div(i2s, oversample_rate,
+ clk_rate, rate);
+ if (mclk_div < 0)
return -EINVAL;
regmap_write(i2s->regmap, SUN4I_I2S_CLK_DIV_REG,
@@ -481,9 +490,23 @@ static void sun4i_i2s_shutdown(struct snd_pcm_substream *substream,
regmap_write(i2s->regmap, SUN4I_I2S_CTRL_REG, 0);
}
+static int sun4i_i2s_set_sysclk(struct snd_soc_dai *dai, int clk_id,
+ unsigned int freq, int dir)
+{
+ struct sun4i_i2s *i2s = snd_soc_dai_get_drvdata(dai);
+
+ if (clk_id != 0)
+ return -EINVAL;
+
+ i2s->mclk_freq = freq;
+
+ return 0;
+}
+
static const struct snd_soc_dai_ops sun4i_i2s_dai_ops = {
.hw_params = sun4i_i2s_hw_params,
.set_fmt = sun4i_i2s_set_fmt,
+ .set_sysclk = sun4i_i2s_set_sysclk,
.shutdown = sun4i_i2s_shutdown,
.startup = sun4i_i2s_startup,
.trigger = sun4i_i2s_trigger,
--
git-series 0.8.11
^ permalink raw reply related
* [PATCH 0/3] ARM: gr8: evb: Enable the i2s codec
From: Maxime Ripard @ 2016-11-07 13:08 UTC (permalink / raw)
To: linux-arm-kernel
The GR8-EVB comes with a wm8978 codec connected to the SoC through an I2S
bus.
A few patches were needed for it to work with simple-card, those are the
very first patches.
The last one will add that card to the relevant device tree so that we can
use it.
Let me know what you think,
Maxime
Maxime Ripard (3):
ASoC: sunxi: i2s: Implement set_sysclk
ASoC: wm8978: Adjust clock indices so that simple card works
ARM: gr8: evb: Add i2s codec
arch/arm/boot/dts/ntc-gr8-evb.dts | 14 ++++++++-
sound/soc/codecs/wm8978.h | 2 +-
sound/soc/sunxi/sun4i-i2s.c | 53 ++++++++++++++++++++++----------
3 files changed, 53 insertions(+), 16 deletions(-)
base-commit: ff9ed64af60bd87cc1c1225e595a33fe248b02bf
--
git-series 0.8.11
^ permalink raw reply
* [PATCH] iommu/dma-iommu: properly respect configured address space size
From: Marek Szyprowski @ 2016-11-07 13:06 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CGME20161107130625eucas1p2dd23c07010b4f3eddb6c6540ed802246@eucas1p2.samsung.com>
When one called iommu_dma_init_domain() with size smaller than device's
DMA mask, the alloc_iova() will not respect it and always assume that all
IOVA addresses will be allocated from the the (base ... dev->dma_mask) range.
This patch fixes this issue by taking the configured address space size
parameter into account (if it is smaller than the device's dma_mask).
Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com>
---
drivers/iommu/dma-iommu.c | 4 +++-
1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/iommu/dma-iommu.c b/drivers/iommu/dma-iommu.c
index c5ab8667e6f2..8b4b72654359 100644
--- a/drivers/iommu/dma-iommu.c
+++ b/drivers/iommu/dma-iommu.c
@@ -212,11 +212,13 @@ static struct iova *__alloc_iova(struct iommu_domain *domain, size_t size,
if (domain->geometry.force_aperture)
dma_limit = min(dma_limit, domain->geometry.aperture_end);
+
+ dma_limit = min(dma_limit >> shift, (dma_addr_t)iovad->dma_32bit_pfn);
/*
* Enforce size-alignment to be safe - there could perhaps be an
* attribute to control this per-device, or at least per-domain...
*/
- return alloc_iova(iovad, length, dma_limit >> shift, true);
+ return alloc_iova(iovad, length, dma_limit, true);
}
/* The IOVA allocator knows what we mapped, so just unmap whatever that was */
--
1.9.1
^ permalink raw reply related
* [PATCH 6/6] arm: dts: stm32f4: Add external I2S clock
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch adds an external I2S clock in the DT.
The I2S clock could be derived from an external I2S clock or by I2S pll.
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
arch/arm/boot/dts/stm32f429.dtsi | 8 +++++++-
1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/arch/arm/boot/dts/stm32f429.dtsi b/arch/arm/boot/dts/stm32f429.dtsi
index 2700449..14da6ce 100644
--- a/arch/arm/boot/dts/stm32f429.dtsi
+++ b/arch/arm/boot/dts/stm32f429.dtsi
@@ -68,6 +68,12 @@
compatible = "fixed-clock";
clock-frequency = <32000>;
};
+
+ clk_i2s_ckin: i2s-ckin {
+ #clock-cells = <0>;
+ compatible = "fixed-clock";
+ clock-frequency = <0>;
+ };
};
soc {
@@ -356,7 +362,7 @@
#clock-cells = <2>;
compatible = "st,stm32f42xx-rcc", "st,stm32-rcc";
reg = <0x40023800 0x400>;
- clocks = <&clk_hse>;
+ clocks = <&clk_hse>, <&clk_i2s_ckin>;
st,syscfg = <&pwrcfg>;
};
--
1.9.1
^ permalink raw reply related
* [PATCH 5/6] clk: stm32f4: Add SAI clocks
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch introduces SAI clocks for stm32f4 socs.
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
drivers/clk/clk-stm32f4.c | 17 +++++++++++++++++
1 file changed, 17 insertions(+)
diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
index b7cb359..c305659 100644
--- a/drivers/clk/clk-stm32f4.c
+++ b/drivers/clk/clk-stm32f4.c
@@ -217,6 +217,7 @@ enum {
PLL_VCO_I2S, PLL_VCO_SAI,
CLK_LCD,
CLK_I2S,
+ CLK_SAI1, CLK_SAI2,
END_PRIMARY_CLK
};
@@ -970,6 +971,9 @@ static struct clk_hw *stm32_register_cclk(struct device *dev, const char *name,
static const char *i2s_parents[2] = { "plli2s-r", NULL };
+static const char *sai_parents[4] = { "pllsai-q-div", "plli2s-q-div", NULL,
+ "no-clock" };
+
struct stm32f4_clk_data {
const struct stm32f4_gate_data *gates_data;
const u64 *gates_map;
@@ -1063,6 +1067,19 @@ static void __init stm32f4_rcc_init(struct device_node *np)
i2s_parents, ARRAY_SIZE(i2s_parents), 0,
base + STM32F4_RCC_CFGR, 23, 1, 0, NULL,
&stm32f4_clk_lock);
+
+ sai_parents[2] = i2s_in_clk;
+
+ clks[CLK_SAI1] = clk_hw_register_mux_table(NULL, "sai1-clk",
+ sai_parents, ARRAY_SIZE(sai_parents), 0,
+ base + STM32F4_RCC_DCKCFGR, 20, 1, 0, NULL,
+ &stm32f4_clk_lock);
+
+ clks[CLK_SAI2] = clk_hw_register_mux_table(NULL, "sai2-clk",
+ sai_parents, ARRAY_SIZE(sai_parents), 0,
+ base + STM32F4_RCC_DCKCFGR, 22, 1, 0, NULL,
+ &stm32f4_clk_lock);
+
sys_parents[1] = hse_clk;
clk_register_mux_table(
NULL, "sys", sys_parents, ARRAY_SIZE(sys_parents), 0,
--
1.9.1
^ permalink raw reply related
* [PATCH 4/6] clk: stm32f4: Add I2S clock
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch introduces I2S clock for stm32f4 soc.
The I2S clock could be derived from an external clock or from pll-i2s
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
drivers/clk/clk-stm32f4.c | 12 +++++++++++-
1 file changed, 11 insertions(+), 1 deletion(-)
diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
index 5fa5d51..b7cb359 100644
--- a/drivers/clk/clk-stm32f4.c
+++ b/drivers/clk/clk-stm32f4.c
@@ -216,6 +216,7 @@ enum {
SYSTICK, FCLK, CLK_LSI, CLK_LSE, CLK_HSE_RTC, CLK_RTC,
PLL_VCO_I2S, PLL_VCO_SAI,
CLK_LCD,
+ CLK_I2S,
END_PRIMARY_CLK
};
@@ -967,6 +968,8 @@ static struct clk_hw *stm32_register_cclk(struct device *dev, const char *name,
static const char *sdmux_parents[2] = { "pll48", "sys" };
+static const char *i2s_parents[2] = { "plli2s-r", NULL };
+
struct stm32f4_clk_data {
const struct stm32f4_gate_data *gates_data;
const u64 *gates_map;
@@ -1005,7 +1008,7 @@ struct stm32f4_clk_data {
static void __init stm32f4_rcc_init(struct device_node *np)
{
- const char *hse_clk;
+ const char *hse_clk, *i2s_in_clk;
int n;
const struct of_device_id *match;
const struct stm32f4_clk_data *data;
@@ -1038,6 +1041,7 @@ static void __init stm32f4_rcc_init(struct device_node *np)
stm32f4_gate_map = data->gates_map;
hse_clk = of_clk_get_parent_name(np, 0);
+ i2s_in_clk = of_clk_get_parent_name(np, 1);
clk_register_fixed_rate_with_accuracy(NULL, "hsi", NULL, 0,
16000000, 160000);
@@ -1053,6 +1057,12 @@ static void __init stm32f4_rcc_init(struct device_node *np)
clks[PLL_VCO_SAI] = stm32f4_rcc_register_pll(pllsrc,
&data->pll_data[2], &stm32f4_clk_lock);
+ i2s_parents[1] = i2s_in_clk;
+
+ clks[CLK_I2S] = clk_hw_register_mux_table(NULL, "i2s",
+ i2s_parents, ARRAY_SIZE(i2s_parents), 0,
+ base + STM32F4_RCC_CFGR, 23, 1, 0, NULL,
+ &stm32f4_clk_lock);
sys_parents[1] = hse_clk;
clk_register_mux_table(
NULL, "sys", sys_parents, ARRAY_SIZE(sys_parents), 0,
--
1.9.1
^ permalink raw reply related
* [PATCH 3/6] clk: stm32f4: Add post divisor for I2S & SAI PLLs and Add lcd-tft clock
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch adds post dividers of I2S & SAI PLLs.
These dividers are managed by a dedicated register (RCC_DCKCFGR).
The PLL should be off before a set rate.
This patch also introduces the lcd-tft clock.
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
drivers/clk/clk-stm32f4.c | 27 +++++++++++++++++++++++++--
1 file changed, 25 insertions(+), 2 deletions(-)
diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
index dda15bc..5fa5d51 100644
--- a/drivers/clk/clk-stm32f4.c
+++ b/drivers/clk/clk-stm32f4.c
@@ -215,6 +215,7 @@ struct stm32f4_gate_data {
enum {
SYSTICK, FCLK, CLK_LSI, CLK_LSE, CLK_HSE_RTC, CLK_RTC,
PLL_VCO_I2S, PLL_VCO_SAI,
+ CLK_LCD,
END_PRIMARY_CLK
};
@@ -599,6 +600,9 @@ static struct clk_hw *clk_register_pll_div(const char *name,
static const struct clk_div_table pll_divp_table[] = {
{ 0, 2 }, { 1, 4 }, { 2, 6 }, { 3, 8 },
};
+static const struct clk_div_table pll_lcd_div_table[] = {
+ { 0, 2 }, { 1, 4 }, { 2, 8 }, { 3, 16 },
+};
/*
* Decode current PLL state and (statically) model the state we inherit from
@@ -659,16 +663,35 @@ static struct clk_hw *stm32f4_rcc_register_pll(const char *pllsrc,
clk_register_pll_div(data->p_name, data->vco_name, 0, reg,
16, 2, 0, pll_divp_table, pll_hw, lock);
- if (data->q_name)
+ if (data->q_name) {
clk_register_pll_div(data->q_name, data->vco_name, 0, reg,
24, 4, CLK_DIVIDER_ONE_BASED, NULL,
pll_hw, lock);
- if (data->r_name)
+ if (data->pll_num == PLL_I2S)
+ clk_register_pll_div("plli2s-q-div", data->q_name,
+ 0, base + STM32F4_RCC_DCKCFGR,
+ 0, 5, 0, NULL, pll_hw, &stm32f4_clk_lock);
+
+ if (data->pll_num == PLL_SAI)
+ clk_register_pll_div("pllsai-q-div", data->q_name,
+ 0, base + STM32F4_RCC_DCKCFGR,
+ 8, 5, 0, NULL, pll_hw, &stm32f4_clk_lock);
+ }
+
+ if (data->r_name) {
clk_register_pll_div(data->r_name, data->vco_name, 0, reg,
28, 3, CLK_DIVIDER_ONE_BASED, NULL, pll_hw,
lock);
+ if (data->pll_num == PLL_SAI)
+ clks[CLK_LCD] = clk_register_pll_div("lcd-tft",
+ data->r_name, CLK_SET_RATE_PARENT,
+ base + STM32F4_RCC_DCKCFGR, 16, 2, 0,
+ pll_lcd_div_table, pll_hw,
+ &stm32f4_clk_lock);
+ }
+
return pll_hw;
}
--
1.9.1
^ permalink raw reply related
* [PATCH 2/6] clk: stm32f4: SDIO & 48Mhz clock management for STM32F469 board
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
In the stm32f469 soc, the 48Mhz clock could be derived from pll-q or
from pll-sai-p.
The SDIO clock could be also derived from 48Mhz or from sys clock.
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
drivers/clk/clk-stm32f4.c | 18 +++++++++++++++++-
1 file changed, 17 insertions(+), 1 deletion(-)
diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
index 7641acd..dda15bc 100644
--- a/drivers/clk/clk-stm32f4.c
+++ b/drivers/clk/clk-stm32f4.c
@@ -199,7 +199,7 @@ struct stm32f4_gate_data {
{ STM32F4_RCC_APB2ENR, 8, "adc1", "apb2_div" },
{ STM32F4_RCC_APB2ENR, 9, "adc2", "apb2_div" },
{ STM32F4_RCC_APB2ENR, 10, "adc3", "apb2_div" },
- { STM32F4_RCC_APB2ENR, 11, "sdio", "pll48" },
+ { STM32F4_RCC_APB2ENR, 11, "sdio", "sdmux" },
{ STM32F4_RCC_APB2ENR, 12, "spi1", "apb2_div" },
{ STM32F4_RCC_APB2ENR, 13, "spi4", "apb2_div" },
{ STM32F4_RCC_APB2ENR, 14, "syscfg", "apb2_div" },
@@ -940,6 +940,10 @@ static struct clk_hw *stm32_register_cclk(struct device *dev, const char *name,
"no-clock", "lse", "lsi", "hse-rtc"
};
+static const char *pll48_parents[2] = { "pll-q", "pllsai-p" };
+
+static const char *sdmux_parents[2] = { "pll48", "sys" };
+
struct stm32f4_clk_data {
const struct stm32f4_gate_data *gates_data;
const u64 *gates_map;
@@ -1109,6 +1113,18 @@ static void __init stm32f4_rcc_init(struct device_node *np)
goto fail;
}
+ if (of_device_is_compatible(np, "st,stm32f469-rcc")) {
+ clk_hw_register_mux_table(NULL, "pll48",
+ pll48_parents, ARRAY_SIZE(pll48_parents), 0,
+ base + STM32F4_RCC_DCKCFGR, 27, 1, 0, NULL,
+ &stm32f4_clk_lock);
+
+ clk_hw_register_mux_table(NULL, "sdmux",
+ sdmux_parents, ARRAY_SIZE(sdmux_parents), 0,
+ base + STM32F4_RCC_DCKCFGR, 28, 1, 0, NULL,
+ &stm32f4_clk_lock);
+ }
+
of_clk_add_hw_provider(np, stm32f4_rcc_lookup_clk, NULL);
return;
fail:
--
1.9.1
^ permalink raw reply related
* [PATCH 1/6] clk: stm32f4: Add PLL_I2S & PLL_SAI for STM32F429/469 boards
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478523943-23142-1-git-send-email-gabriel.fernandez@st.com>
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch introduces PLL_I2S and PLL_SAI.
Vco clock of these PLLs can be modify by DT (only n multiplicator,
m divider is still fixed by the boot-loader).
Each PLL has 3 dividers. PLL should be off when we modify the rate.
Signed-off-by: Gabriel Fernandez <gabriel.fernandez@st.com>
---
drivers/clk/clk-stm32f4.c | 371 ++++++++++++++++++++++++++++++++++++++++++++--
1 file changed, 359 insertions(+), 12 deletions(-)
diff --git a/drivers/clk/clk-stm32f4.c b/drivers/clk/clk-stm32f4.c
index c2661e2..7641acd 100644
--- a/drivers/clk/clk-stm32f4.c
+++ b/drivers/clk/clk-stm32f4.c
@@ -28,6 +28,7 @@
#include <linux/regmap.h>
#include <linux/mfd/syscon.h>
+#define STM32F4_RCC_CR 0x00
#define STM32F4_RCC_PLLCFGR 0x04
#define STM32F4_RCC_CFGR 0x08
#define STM32F4_RCC_AHB1ENR 0x30
@@ -37,6 +38,9 @@
#define STM32F4_RCC_APB2ENR 0x44
#define STM32F4_RCC_BDCR 0x70
#define STM32F4_RCC_CSR 0x74
+#define STM32F4_RCC_PLLI2SCFGR 0x84
+#define STM32F4_RCC_PLLSAICFGR 0x88
+#define STM32F4_RCC_DCKCFGR 0x8c
struct stm32f4_gate_data {
u8 offset;
@@ -208,7 +212,11 @@ struct stm32f4_gate_data {
{ STM32F4_RCC_APB2ENR, 26, "ltdc", "apb2_div" },
};
-enum { SYSTICK, FCLK, CLK_LSI, CLK_LSE, CLK_HSE_RTC, CLK_RTC, END_PRIMARY_CLK };
+enum {
+ SYSTICK, FCLK, CLK_LSI, CLK_LSE, CLK_HSE_RTC, CLK_RTC,
+ PLL_VCO_I2S, PLL_VCO_SAI,
+ END_PRIMARY_CLK
+};
/*
* This bitmask tells us which bit offsets (0..192) on STM32F4[23]xxx
@@ -324,23 +332,344 @@ static struct clk *clk_register_apb_mul(struct device *dev, const char *name,
return clk;
}
+enum {
+ PLL,
+ PLL_I2S,
+ PLL_SAI,
+};
+
+struct stm32f4_pll {
+ spinlock_t *lock;
+ struct clk_hw hw;
+ u8 offset;
+ u8 bit_idx;
+ u8 bit_rdy_idx;
+ u8 status;
+ u8 n_start;
+};
+
+struct stm32f4_pll_data {
+ u8 pll_num;
+ u8 n_start;
+ const char *vco_name;
+ const char *p_name;
+ const char *q_name;
+ const char *r_name;
+};
+
+static const struct stm32f4_pll_data stm32f429_pll[] = {
+ { PLL, 192, "vco", "pll", "pll48", NULL, },
+ { PLL_I2S, 192, "vco-i2s", NULL, "plli2s-q", "plli2s-r", },
+ { PLL_SAI, 49, "vco-sai", NULL, "pllsai-q", "pllsai-r", },
+};
+
+static const struct stm32f4_pll_data stm32f469_pll[] = {
+ { PLL, 50, "vco", "pll", "pll-q", NULL, },
+ { PLL_I2S, 50, "vco-i2s", NULL, "plli2s-q", "plli2s-r", },
+ { PLL_SAI, 50, "vco-sai", "pllsai-p", "pllsai-q", "pllsai-r", },
+};
+
+#define to_stm32f4_pll(_hw) container_of(_hw, struct stm32f4_pll, hw)
+
+static int stm32f4_pll_is_enabled(struct clk_hw *hw)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+
+ return pll->status;
+}
+
+static int __stm32f4_pll_enable(struct clk_hw *hw)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long reg;
+ int ret = 0;
+
+ if (stm32f4_pll_is_enabled(hw))
+ return 0;
+
+ reg = readl(base + STM32F4_RCC_CR) | (1 << pll->bit_idx);
+ writel(reg, base + STM32F4_RCC_CR);
+
+ ret = readl_relaxed_poll_timeout_atomic(base + STM32F4_RCC_CR, reg,
+ reg & (1 << pll->bit_rdy_idx), 0, 10000);
+
+ pll->status = 1;
+
+ return ret;
+}
+
+static int stm32f4_pll_enable(struct clk_hw *hw)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ int ret = 0;
+ unsigned long flags = 0;
+
+ if (pll->lock)
+ spin_lock_irqsave(pll->lock, flags);
+
+ ret = __stm32f4_pll_enable(hw);
+
+ if (pll->lock)
+ spin_unlock_irqrestore(pll->lock, flags);
+
+ return ret;
+}
+
+static void __stm32f4_pll_disable(struct clk_hw *hw)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long reg;
+
+ reg = readl(base + STM32F4_RCC_CR) & ~(1 << pll->bit_idx);
+
+ writel(reg, base + STM32F4_RCC_CR);
+
+ pll->status = 0;
+}
+
+static void stm32f4_pll_disable(struct clk_hw *hw)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long flags = 0;
+
+ if (pll->lock)
+ spin_lock_irqsave(pll->lock, flags);
+
+ __stm32f4_pll_disable(hw);
+
+ if (pll->lock)
+ spin_unlock_irqrestore(pll->lock, flags);
+}
+
+static unsigned long stm32f4_pll_recalc(struct clk_hw *hw,
+ unsigned long parent_rate)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long pllcfgr = readl(base + STM32F4_RCC_PLLCFGR);
+ unsigned long pllm = pllcfgr & 0x3f;
+ unsigned long plln = (readl(base + pll->offset) >> 6) & 0x1ff;
+
+ return (parent_rate / pllm) * plln;
+}
+
+static long stm32f4_pll_round_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long *prate)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long pllcfgr = readl(base + STM32F4_RCC_PLLCFGR);
+ unsigned long m = pllcfgr & 0x3f;
+ unsigned long n;
+
+ n = (rate * m) / *prate;
+
+ if (n < pll->n_start)
+ n = pll->n_start;
+ else if (n > 432)
+ n = 432;
+
+ return (*prate / m) * n;
+}
+
+static int stm32f4_pll_set_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long parent_rate)
+{
+ struct stm32f4_pll *pll = to_stm32f4_pll(hw);
+ unsigned long pllcfgr = readl(base + STM32F4_RCC_PLLCFGR);
+ unsigned long m = pllcfgr & 0x3f;
+ unsigned long n;
+ unsigned long val;
+ int pll_state;
+
+ pll_state = stm32f4_pll_is_enabled(hw);
+
+ if (pll_state)
+ stm32f4_pll_disable(hw);
+
+ n = (rate * m) / parent_rate;
+
+ val = readl(base + pll->offset) & ~(0x1ff << 6);
+
+ writel(val | ((n & 0x1ff) << 6), base + pll->offset);
+
+ if (pll_state)
+ stm32f4_pll_enable(hw);
+
+ return 0;
+}
+
+static const struct clk_ops stm32f4_pll_gate_ops = {
+ .enable = stm32f4_pll_enable,
+ .disable = stm32f4_pll_disable,
+ .is_enabled = stm32f4_pll_is_enabled,
+ .recalc_rate = stm32f4_pll_recalc,
+ .round_rate = stm32f4_pll_round_rate,
+ .set_rate = stm32f4_pll_set_rate,
+};
+
+struct stm32f4_pll_div {
+ struct clk_divider div;
+ struct clk_hw *hw_pll;
+};
+
+#define to_pll_div_clk(_div) container_of(_div, struct stm32f4_pll_div, div)
+
+static unsigned long stm32f4_pll_div_recalc_rate(struct clk_hw *hw,
+ unsigned long parent_rate)
+{
+ return clk_divider_ops.recalc_rate(hw, parent_rate);
+}
+
+static long stm32f4_pll_div_round_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long *prate)
+{
+ return clk_divider_ops.round_rate(hw, rate, prate);
+}
+
+static int stm32f4_pll_div_set_rate(struct clk_hw *hw, unsigned long rate,
+ unsigned long parent_rate)
+{
+ int pll_state, ret;
+
+ struct clk_divider *div = to_clk_divider(hw);
+ struct stm32f4_pll_div *pll_div = to_pll_div_clk(div);
+
+ pll_state = stm32f4_pll_is_enabled(pll_div->hw_pll);
+
+ if (pll_state)
+ stm32f4_pll_disable(pll_div->hw_pll);
+
+ ret = clk_divider_ops.set_rate(hw, rate, parent_rate);
+
+ if (pll_state)
+ stm32f4_pll_enable(pll_div->hw_pll);
+
+ return ret;
+}
+
+const struct clk_ops stm32f4_pll_div_ops = {
+ .recalc_rate = stm32f4_pll_div_recalc_rate,
+ .round_rate = stm32f4_pll_div_round_rate,
+ .set_rate = stm32f4_pll_div_set_rate,
+};
+
+static struct clk_hw *clk_register_pll_div(const char *name,
+ const char *parent_name, unsigned long flags,
+ void __iomem *reg, u8 shift, u8 width,
+ u8 clk_divider_flags, const struct clk_div_table *table,
+ struct clk_hw *pll_hw, spinlock_t *lock)
+{
+ struct stm32f4_pll_div *pll_div;
+ struct clk_hw *hw;
+ struct clk_init_data init;
+ int ret;
+
+ /* allocate the divider */
+ pll_div = kzalloc(sizeof(*pll_div), GFP_KERNEL);
+ if (!pll_div)
+ return ERR_PTR(-ENOMEM);
+
+ init.name = name;
+ init.ops = &stm32f4_pll_div_ops;
+ init.flags = flags;
+ init.parent_names = (parent_name ? &parent_name : NULL);
+ init.num_parents = (parent_name ? 1 : 0);
+
+ /* struct clk_divider assignments */
+ pll_div->div.reg = reg;
+ pll_div->div.shift = shift;
+ pll_div->div.width = width;
+ pll_div->div.flags = clk_divider_flags;
+ pll_div->div.lock = lock;
+ pll_div->div.table = table;
+ pll_div->div.hw.init = &init;
+
+ pll_div->hw_pll = pll_hw;
+
+ /* register the clock */
+ hw = &pll_div->div.hw;
+ ret = clk_hw_register(NULL, hw);
+ if (ret) {
+ kfree(pll_div);
+ hw = ERR_PTR(ret);
+ }
+
+ return hw;
+}
+
+static const struct clk_div_table pll_divp_table[] = {
+ { 0, 2 }, { 1, 4 }, { 2, 6 }, { 3, 8 },
+};
+
/*
* Decode current PLL state and (statically) model the state we inherit from
* the bootloader.
*/
-static void stm32f4_rcc_register_pll(const char *hse_clk, const char *hsi_clk)
+
+static struct clk_hw *stm32f4_rcc_register_pll(const char *pllsrc,
+ const struct stm32f4_pll_data *data, spinlock_t *lock)
{
- unsigned long pllcfgr = readl(base + STM32F4_RCC_PLLCFGR);
+ struct stm32f4_pll *pll;
+ struct clk_init_data init = { NULL };
+ void __iomem *reg;
+ struct clk_hw *pll_hw;
+ int ret;
+
+ pll = kzalloc(sizeof(*pll), GFP_KERNEL);
+ if (!pll)
+ return ERR_PTR(-ENOMEM);
+
+ init.name = data->vco_name;
+ init.ops = &stm32f4_pll_gate_ops;
+ init.flags = CLK_IGNORE_UNUSED;
+ init.parent_names = &pllsrc;
+ init.num_parents = 1;
+
+ pll->hw.init = &init;
+
+ switch (data->pll_num) {
+ case PLL:
+ pll->offset = STM32F4_RCC_PLLCFGR;
+ pll->bit_idx = 24;
+ pll->bit_rdy_idx = 25;
+ break;
+ case PLL_I2S:
+ pll->offset = STM32F4_RCC_PLLI2SCFGR;
+ pll->bit_idx = 26;
+ pll->bit_rdy_idx = 27;
+ break;
+ case PLL_SAI:
+ pll->offset = STM32F4_RCC_PLLSAICFGR;
+ pll->bit_idx = 28;
+ pll->bit_rdy_idx = 29;
+ break;
+ };
+
+ pll->n_start = data->n_start;
+ pll->status = (readl(base + STM32F4_RCC_CR) >> pll->bit_idx) & 0x1;
+ reg = base + pll->offset;
+
+ pll_hw = &pll->hw;
+ ret = clk_hw_register(NULL, pll_hw);
+ if (ret) {
+ kfree(pll);
+ return ERR_PTR(ret);
+ }
+
+ if (data->p_name)
+ clk_register_pll_div(data->p_name, data->vco_name, 0, reg,
+ 16, 2, 0, pll_divp_table, pll_hw, lock);
+
+ if (data->q_name)
+ clk_register_pll_div(data->q_name, data->vco_name, 0, reg,
+ 24, 4, CLK_DIVIDER_ONE_BASED, NULL,
+ pll_hw, lock);
- unsigned long pllm = pllcfgr & 0x3f;
- unsigned long plln = (pllcfgr >> 6) & 0x1ff;
- unsigned long pllp = BIT(((pllcfgr >> 16) & 3) + 1);
- const char *pllsrc = pllcfgr & BIT(22) ? hse_clk : hsi_clk;
- unsigned long pllq = (pllcfgr >> 24) & 0xf;
+ if (data->r_name)
+ clk_register_pll_div(data->r_name, data->vco_name, 0, reg,
+ 28, 3, CLK_DIVIDER_ONE_BASED, NULL, pll_hw,
+ lock);
- clk_register_fixed_factor(NULL, "vco", pllsrc, 0, plln, pllm);
- clk_register_fixed_factor(NULL, "pll", "vco", 0, 1, pllp);
- clk_register_fixed_factor(NULL, "pll48", "vco", 0, 1, pllq);
+ return pll_hw;
}
/*
@@ -615,18 +944,24 @@ struct stm32f4_clk_data {
const struct stm32f4_gate_data *gates_data;
const u64 *gates_map;
int gates_num;
+ const struct stm32f4_pll_data *pll_data;
+ int pll_num;
};
static const struct stm32f4_clk_data stm32f429_clk_data = {
.gates_data = stm32f429_gates,
.gates_map = stm32f42xx_gate_map,
.gates_num = ARRAY_SIZE(stm32f429_gates),
+ .pll_data = stm32f429_pll,
+ .pll_num = ARRAY_SIZE(stm32f429_pll),
};
static const struct stm32f4_clk_data stm32f469_clk_data = {
.gates_data = stm32f469_gates,
.gates_map = stm32f46xx_gate_map,
.gates_num = ARRAY_SIZE(stm32f469_gates),
+ .pll_data = stm32f469_pll,
+ .pll_num = ARRAY_SIZE(stm32f469_pll),
};
static const struct of_device_id stm32f4_of_match[] = {
@@ -647,6 +982,8 @@ static void __init stm32f4_rcc_init(struct device_node *np)
int n;
const struct of_device_id *match;
const struct stm32f4_clk_data *data;
+ unsigned long pllcfgr;
+ const char *pllsrc;
base = of_iomap(np, 0);
if (!base) {
@@ -677,7 +1014,17 @@ static void __init stm32f4_rcc_init(struct device_node *np)
clk_register_fixed_rate_with_accuracy(NULL, "hsi", NULL, 0,
16000000, 160000);
- stm32f4_rcc_register_pll(hse_clk, "hsi");
+ pllcfgr = readl(base + STM32F4_RCC_PLLCFGR);
+ pllsrc = pllcfgr & BIT(22) ? hse_clk : "hsi";
+
+ stm32f4_rcc_register_pll(pllsrc, &data->pll_data[0],
+ &stm32f4_clk_lock);
+
+ clks[PLL_VCO_I2S] = stm32f4_rcc_register_pll(pllsrc,
+ &data->pll_data[1], &stm32f4_clk_lock);
+
+ clks[PLL_VCO_SAI] = stm32f4_rcc_register_pll(pllsrc,
+ &data->pll_data[2], &stm32f4_clk_lock);
sys_parents[1] = hse_clk;
clk_register_mux_table(
--
1.9.1
^ permalink raw reply related
* [PATCH 0/6] Add STM32F4 missing clocks
From: gabriel.fernandez at st.com @ 2016-11-07 13:05 UTC (permalink / raw)
To: linux-arm-kernel
From: Gabriel Fernandez <gabriel.fernandez@st.com>
This patch-set adds:
- I2S & SAI PLLs
- SDIO & 48 Mhz clocks
- LCD-TFT clock
- I2S & SAI clocks
Gabriel Fernandez (6):
clk: stm32f4: Add PLL_I2S & PLL_SAI for STM32F429/469 boards
clk: stm32f4: SDIO & 48Mhz clock management for STM32F469 board
clk: stm32f4: Add post divisor for I2S & SAI PLLs and Add lcd-tft
clock
clk: stm32f4: Add I2S clock
clk: stm32f4: Add SAI clocks
arm: dts: stm32f4: Add external I2S clock
arch/arm/boot/dts/stm32f429.dtsi | 8 +-
drivers/clk/clk-stm32f4.c | 441 +++++++++++++++++++++++++++++++++++++--
2 files changed, 434 insertions(+), 15 deletions(-)
--
1.9.1
^ permalink raw reply
* [PATCH 1/3] ipmi/bt-bmc: change compatible node to 'aspeed, ast2400-ibt-bmc'
From: Arnd Bergmann @ 2016-11-07 13:02 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <ebeba60f-429f-fb84-b9da-c27d11d23094@kaod.org>
On Wednesday, November 2, 2016 3:28:01 PM CET C?dric Le Goater wrote:
> On 11/02/2016 02:56 PM, Joel Stanley wrote:
> > On Wed, Nov 2, 2016 at 11:45 PM, Arnd Bergmann <arnd@arndb.de> wrote:
> >> On Wednesday 02 November 2016, C?dric Le Goater wrote:
> >>> The Aspeed SoCs have two BT interfaces : one is IPMI compliant and the
> >>> other is H8S/2168 compliant.
> >>>
> >>> The current ipmi/bt-bmc driver implements the IPMI version and we
> >>> should reflect its nature in the compatible node name using
> >>> 'aspeed,ast2400-ibt-bmc' instead of 'aspeed,ast2400-bt-bmc'. The
> >>> latter should be used for a H8S interface driver if it is implemented
> >>> one day.
> >>>
> >>> Signed-off-by: C?dric Le Goater <clg@kaod.org>
> >>
> >> We generally try to avoid changing the compatible strings after the
> >> fact, but it's probably ok in this case.
>
> As the device tree changes are not merged yet, we thought we had some
> more time to fine tune the naming.
Ok, I see. No problem then.
> >> I don't understand who decides which of the two interfaces is used:
> >> is it the same register set that can be driven by either one or the
> >> other driver, or do you expect to have two drivers that can both
> >> be active in the same system and talk to different hardware once
> >> you get there?
> >
> > It's the second case. The H8S BT has a different register layout so it
> > would require a different driver.
>
> yes.
>
> > We don't yet have a driver for the other BT device, but there was
> > recent talk of using it as an alternate (non-ipmi channel) between the
> > BMC and the host. Before that discussion I wasn't aware that the H8S
> > BT existed. I suggested we fix this up before it hits a final release.
> >
> > C?dric, do you think ast2400-ibt-bmc or ast2400-ipmi-bt-bmc does a
> > better job of describing the hardware here?
>
> The specs refer to the two interfaces as BT (non IPMI) and iBT (IPMI).
> I think we can keep the same naming.
Ok
> > While we're modifying the binding, should we add a compat string for
> > the ast2500?
>
> Well, if the change in this patch is fine for all, may be we can add
> the ast2500 compat string in a followup patch ?
Sounds good to me.
Arnd
^ permalink raw reply
* [PATCH] phy: rockchip-inno-usb2: correct 480MHz output clock stable time
From: William Wu @ 2016-11-07 13:00 UTC (permalink / raw)
To: linux-arm-kernel
We found that the system crashed due to 480MHz output clock of
USB2 PHY was unstable after clock had been enabled by gpu module.
Theoretically, 1 millisecond is a critical value for 480MHz
output clock stable time, so we try to change the delay time
to 1.2 millisecond to avoid this issue.
Signed-off-by: William Wu <wulf@rock-chips.com>
---
drivers/phy/phy-rockchip-inno-usb2.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/phy/phy-rockchip-inno-usb2.c b/drivers/phy/phy-rockchip-inno-usb2.c
index ecfd7d1..8f2d2b6 100644
--- a/drivers/phy/phy-rockchip-inno-usb2.c
+++ b/drivers/phy/phy-rockchip-inno-usb2.c
@@ -267,7 +267,7 @@ static int rockchip_usb2phy_clk480m_enable(struct clk_hw *hw)
return ret;
/* waitting for the clk become stable */
- mdelay(1);
+ udelay(1200);
}
return 0;
--
2.0.0
^ permalink raw reply related
* [PATCH] ARM: tegra: nyan: Enable GPU node and related supply
From: Jon Hunter @ 2016-11-07 13:00 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <CAAVeFuLb5gU70B0jP0YNPB58NcuR_D0e--6zn3dG7VOmZafLRA@mail.gmail.com>
Thierry,
On 07/11/16 12:51, Alexandre Courbot wrote:
> On Wed, Sep 21, 2016 at 4:57 PM, Jon Hunter <jonathanh@nvidia.com> wrote:
>>
>> On 20/09/16 19:17, Paul Kocialkowski wrote:
>>> * PGP Signed by an unknown key
>>>
>>> Le mardi 20 septembre 2016 ? 13:24 +0100, Jon Hunter a ?crit :
>>>> On 18/09/16 15:13, Paul Kocialkowski wrote:
>>>>>
>>>>> This enables the GPU node for tegra124 nyan boards, which is required to
>>>>> get graphics acceleration with nouveau on these devices.
>>>>>
>>>>> Signed-off-by: Paul Kocialkowski <contact@paulk.fr>
>>>>> ---
>>>>> arch/arm/boot/dts/tegra124-nyan.dtsi | 8 +++++++-
>>>>> 1 file changed, 7 insertions(+), 1 deletion(-)
>>>>>
>>>>> diff --git a/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>>> b/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>>> index dab9509..225ca77 100644
>>>>> --- a/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>>> +++ b/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>>> @@ -42,6 +42,12 @@
>>>>> };
>>>>> };
>>>>>
>>>>> + gpu at 0,57000000 {
>>>>> + status = "okay";
>>>>> +
>>>>> + vdd-supply = <&vdd_gpu>;
>>>>> + };
>>>>> +
>>>>> serial at 70006000 {
>>>>> /* Debug connector on the bottom of the board near SD card.
>>>>> */
>>>>> status = "okay";
>>>>> @@ -214,7 +220,7 @@
>>>>> regulator-always-on;
>>>>> };
>>>>>
>>>>> - sd6 {
>>>>> + vdd_gpu: sd6 {
>>>>> regulator-name = "+VDD_GPU_AP";
>>>>> regulator-min-microvolt = <650000>;
>>>>> regulator-max-microvolt =
>>>>> <1200000>;
>>>>>
>>>>
>>>> Looks good to me. I see the following error when booting but looking at the
>>>> code appears to be benign. Thierry, Alex, is this normal/okay?
>>>
>>> I have the same messages and asked Alexandre about them the other day. He told
>>> me that it looks normal.
>>
>> Ok great. Hopefully, Alex can ACK then.
>
> Apologies for the (very) delayed reply.
>
> Yes, the messages you are seeing are part of the normal probe sequence
> on Tegra. So this looks good to me.
>
> Acked-by: Alexandre Courbot <acourbot@nvidia.com>
Can you pick this one up for v4.10 as well?
Cheers
Jon
--
nvpublic
^ permalink raw reply
* [PATCH V4 5/6] ARM: tegra: Add Tegra20 GMI support
From: Thierry Reding @ 2016-11-07 12:56 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478507405-13204-6-git-send-email-mirza.krak@gmail.com>
On Mon, Nov 07, 2016 at 09:30:04AM +0100, Mirza Krak wrote:
> From: Mirza Krak <mirza.krak@gmail.com>
>
> Add a device node for the GMI controller found on Tegra20.
>
> Signed-off-by: Mirza Krak <mirza.krak@gmail.com>
> Tested-by: Marcel Ziswiler <marcel.ziswiler@toradex.com>
> Tested-on: Colibri T20/T30 on EvalBoard V3.x and GMI-Memory Board
> Acked-by: Jon Hunter <jonathanh@nvidia.com>
> ---
>
> Changes in v2:
> - added address-cells, size-cells and ranges properties
>
> Changes in v3:
> - fixed range address which is not the same as Tegra30.
>
> Changes in v4:
> - removed extra newline and a initial space in resets property.
>
> arch/arm/boot/dts/tegra20.dtsi | 13 +++++++++++++
> 1 file changed, 13 insertions(+)
Applied, thanks.
Thierry
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20161107/f7d7603a/attachment.sig>
^ permalink raw reply
* [PATCH V4 4/6] ARM: tegra: Add Tegra30 GMI support
From: Thierry Reding @ 2016-11-07 12:56 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <1478507405-13204-5-git-send-email-mirza.krak@gmail.com>
On Mon, Nov 07, 2016 at 09:30:03AM +0100, Mirza Krak wrote:
> From: Mirza Krak <mirza.krak@gmail.com>
>
> Add a device node for the GMI controller found on Tegra30.
>
> Signed-off-by: Mirza Krak <mirza.krak@gmail.com>
> Tested-by: Marcel Ziswiler <marcel.ziswiler@toradex.com>
> Tested-on: Colibri T20/T30 on EvalBoard V3.x and GMI-Memory Board
> Acked-by: Jon Hunter <jonathanh@nvidia.com>
> ---
>
> Changes in v2:
> - added address-cells, size-cells and ranges properties
>
> Changes in v3:
> - no changes
>
> Changes in v4:
> - no changes
>
> arch/arm/boot/dts/tegra30.dtsi | 13 +++++++++++++
> 1 file changed, 13 insertions(+)
Applied, thanks.
Thierry
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 801 bytes
Desc: not available
URL: <http://lists.infradead.org/pipermail/linux-arm-kernel/attachments/20161107/5923a048/attachment.sig>
^ permalink raw reply
* [PATCH] ARM: tegra: nyan: Enable GPU node and related supply
From: Alexandre Courbot @ 2016-11-07 12:51 UTC (permalink / raw)
To: linux-arm-kernel
In-Reply-To: <e95335ae-ad19-b8cd-634b-63c6a0b88e01@nvidia.com>
On Wed, Sep 21, 2016 at 4:57 PM, Jon Hunter <jonathanh@nvidia.com> wrote:
>
> On 20/09/16 19:17, Paul Kocialkowski wrote:
>> * PGP Signed by an unknown key
>>
>> Le mardi 20 septembre 2016 ? 13:24 +0100, Jon Hunter a ?crit :
>>> On 18/09/16 15:13, Paul Kocialkowski wrote:
>>>>
>>>> This enables the GPU node for tegra124 nyan boards, which is required to
>>>> get graphics acceleration with nouveau on these devices.
>>>>
>>>> Signed-off-by: Paul Kocialkowski <contact@paulk.fr>
>>>> ---
>>>> arch/arm/boot/dts/tegra124-nyan.dtsi | 8 +++++++-
>>>> 1 file changed, 7 insertions(+), 1 deletion(-)
>>>>
>>>> diff --git a/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>> b/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>> index dab9509..225ca77 100644
>>>> --- a/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>> +++ b/arch/arm/boot/dts/tegra124-nyan.dtsi
>>>> @@ -42,6 +42,12 @@
>>>> };
>>>> };
>>>>
>>>> + gpu at 0,57000000 {
>>>> + status = "okay";
>>>> +
>>>> + vdd-supply = <&vdd_gpu>;
>>>> + };
>>>> +
>>>> serial at 70006000 {
>>>> /* Debug connector on the bottom of the board near SD card.
>>>> */
>>>> status = "okay";
>>>> @@ -214,7 +220,7 @@
>>>> regulator-always-on;
>>>> };
>>>>
>>>> - sd6 {
>>>> + vdd_gpu: sd6 {
>>>> regulator-name = "+VDD_GPU_AP";
>>>> regulator-min-microvolt = <650000>;
>>>> regulator-max-microvolt =
>>>> <1200000>;
>>>>
>>>
>>> Looks good to me. I see the following error when booting but looking at the
>>> code appears to be benign. Thierry, Alex, is this normal/okay?
>>
>> I have the same messages and asked Alexandre about them the other day. He told
>> me that it looks normal.
>
> Ok great. Hopefully, Alex can ACK then.
Apologies for the (very) delayed reply.
Yes, the messages you are seeing are part of the normal probe sequence
on Tegra. So this looks good to me.
Acked-by: Alexandre Courbot <acourbot@nvidia.com>
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox