2013-03-27 21:09:28

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

* Pali Rohár <[email protected]> [130228 10:09]:
> --- /dev/null
> +++ b/drivers/char/hw_random/omap3-rom-asm.S
> @@ -0,0 +1,27 @@
> +/*
> + * Copyright (C) 2009 Nokia Corporation
> + *
> + * This program is free software; you can redistribute it and/or modify
> + * it under the terms of the GNU General Public License version 2 as
> + * published by the Free Software Foundation.
> + *
> + */
> +
> +#include <linux/linkage.h>
> +#include <asm/assembler.h>
> +
> +ENTRY(omap3_rng_call_rom_asm)
> + .arch_extension sec
> + stmfd sp!, {r4-r12, lr}
> + stmfd sp!, {r0-r3}
> + bl v7_flush_dcache_all
> + ldmfd sp!, {r0-r3}
> + mov r6, #0xff
> + mov r12, r0
> + smc #1
> + mov r12, r0
> + bl v7_flush_dcache_all
> + mov r0, #0
> + mcr p15, 0, r0, c7, c5, 0
> + mov r0, r12
> + ldmfd sp!, {r4-r12, pc}

This part should be in arch/arm/mach-omap2 because of the
direct calls to v7_flush_dcache_all. Then you can pass a pointer
to this function in platform_data for now, and set it up based
on the compatible flag with device tree from driver later on.

> --- /dev/null
> +++ b/drivers/char/hw_random/omap3-rom-drv.c
> @@ -0,0 +1,167 @@
> +/*
> + * omap3-rom-drv.c - RNG driver for TI OMAP3 CPU family
> + *
> + * Copyright (C) 2009 Nokia Corporation
> + * Author: Juha Yrjola <[email protected]>
> + *
> + * This file is licensed under the terms of the GNU General Public
> + * License version 2. This program is licensed "as is" without any
> + * warranty of any kind, whether express or implied.
> + */
> +
> +#include <linux/module.h>
> +#include <linux/init.h>
> +#include <linux/random.h>
> +#include <linux/hw_random.h>
> +#include <linux/timer.h>
> +#include <linux/clk.h>
> +#include <linux/err.h>
> +#include <linux/platform_device.h>
> +
> +#include "../../../arch/arm/mach-omap2/soc.h"

NAK for this, this must be private to arch/arm/mach-omap2.

Instead, just create a minimal include/linux/platform_data/omap3-rom.h,
and pass the function pointer in the pdata if passed.

> +static int omap3_rom_rng_probe(struct platform_device *pdev)
> +{
> + printk(KERN_INFO "%s: initializing\n", omap3_rom_rng_name);
> + if (!cpu_is_omap34xx()) {
> + printk(KERN_ERR "%s: currently supports only OMAP34xx CPUs\n",
> + omap3_rom_rng_name);
> + return -ENODEV;
> + }
> + if (omap_type() == OMAP2_DEVICE_TYPE_GP) {
> + printk(KERN_ERR "%s: GP OMAPs not supported\n",
> + omap3_rom_rng_name);
> + return -ENODEV;
> + }
> +
> + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> + rng_clk = clk_get_sys("omap_rng", "ick");
> + if (IS_ERR(rng_clk)) {
> + printk(KERN_ERR "%s: unable to get RNG clock\n",
> + omap3_rom_rng_name);
> + return IS_ERR(rng_clk);
> + }
> +
> + /* Leave the RNG in reset state. */
> + clk_prepare_enable(rng_clk);
> + omap3_rom_idle_rng(0);
> +
> + return hwrng_register(&omap3_rom_rng_ops);
> +}

You should replace the cpu_is_omap34xx() and omap_type() with
some flags that you pass in the pdata. These too can be then
deciphered based on the DT compatible flag later on. And then
you don't need to include soc.h.

Regards,

Tony


2013-03-27 22:03:50

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

On Wednesday 27 March 2013 22:09:18 Tony Lindgren wrote:
> * Pali Rohár <[email protected]> [130228 10:09]:
> > --- /dev/null
> > +++ b/drivers/char/hw_random/omap3-rom-asm.S
> > @@ -0,0 +1,27 @@
> > +/*
> > + * Copyright (C) 2009 Nokia Corporation
> > + *
> > + * This program is free software; you can redistribute it
> > and/or modify + * it under the terms of the GNU General
> > Public License version 2 as + * published by the Free
> > Software Foundation.
> > + *
> > + */
> > +
> > +#include <linux/linkage.h>
> > +#include <asm/assembler.h>
> > +
> > +ENTRY(omap3_rng_call_rom_asm)
> > + .arch_extension sec
> > + stmfd sp!, {r4-r12, lr}
> > + stmfd sp!, {r0-r3}
> > + bl v7_flush_dcache_all
> > + ldmfd sp!, {r0-r3}
> > + mov r6, #0xff
> > + mov r12, r0
> > + smc #1
> > + mov r12, r0
> > + bl v7_flush_dcache_all
> > + mov r0, #0
> > + mcr p15, 0, r0, c7, c5, 0
> > + mov r0, r12
> > + ldmfd sp!, {r4-r12, pc}
>
> This part should be in arch/arm/mach-omap2 because of the
> direct calls to v7_flush_dcache_all. Then you can pass a
> pointer to this function in platform_data for now, and set it
> up based on the compatible flag with device tree from driver
> later on.
>

Ok, I will move this file to arch/arm/mach-omap2/omap3-rom-rng.S
and pass function via platform_data to driver.

> > --- /dev/null
> > +++ b/drivers/char/hw_random/omap3-rom-drv.c
> > @@ -0,0 +1,167 @@
> > +/*
> > + * omap3-rom-drv.c - RNG driver for TI OMAP3 CPU family
> > + *
> > + * Copyright (C) 2009 Nokia Corporation
> > + * Author: Juha Yrjola <[email protected]>
> > + *
> > + * This file is licensed under the terms of the GNU
> > General Public + * License version 2. This program is
> > licensed "as is" without any + * warranty of any kind,
> > whether express or implied. + */
> > +
> > +#include <linux/module.h>
> > +#include <linux/init.h>
> > +#include <linux/random.h>
> > +#include <linux/hw_random.h>
> > +#include <linux/timer.h>
> > +#include <linux/clk.h>
> > +#include <linux/err.h>
> > +#include <linux/platform_device.h>
> > +
> > +#include "../../../arch/arm/mach-omap2/soc.h"
>
> NAK for this, this must be private to arch/arm/mach-omap2.
>
> Instead, just create a minimal
> include/linux/platform_data/omap3-rom.h, and pass the
> function pointer in the pdata if passed.
>
> > +static int omap3_rom_rng_probe(struct platform_device
> > *pdev) +{
> > + printk(KERN_INFO "%s: initializing\n",
> > omap3_rom_rng_name); + if (!cpu_is_omap34xx()) {
> > + printk(KERN_ERR "%s: currently supports only OMAP34xx
> > CPUs\n", + omap3_rom_rng_name);
> > + return -ENODEV;
> > + }
> > + if (omap_type() == OMAP2_DEVICE_TYPE_GP) {
> > + printk(KERN_ERR "%s: GP OMAPs not supported\n",
> > + omap3_rom_rng_name);
> > + return -ENODEV;
> > + }
> > +
> > + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> > + rng_clk = clk_get_sys("omap_rng", "ick");
> > + if (IS_ERR(rng_clk)) {
> > + printk(KERN_ERR "%s: unable to get RNG clock\n",
> > + omap3_rom_rng_name);
> > + return IS_ERR(rng_clk);
> > + }
> > +
> > + /* Leave the RNG in reset state. */
> > + clk_prepare_enable(rng_clk);
> > + omap3_rom_idle_rng(0);
> > +
> > + return hwrng_register(&omap3_rom_rng_ops);
> > +}
>
> You should replace the cpu_is_omap34xx() and omap_type() with
> some flags that you pass in the pdata. These too can be then
> deciphered based on the DT compatible flag later on. And then
> you don't need to include soc.h.
>
> Regards,
>
> Tony

I will remove above code for checking omap type from hw rand
driver, because same code is in omap part which creating
platform_device for this driver. So soc.h is not needed.

--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-03-27 22:25:34

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

* Pali Rohár <[email protected]> [130327 15:08]:
>
> I will remove above code for checking omap type from hw rand
> driver, because same code is in omap part which creating
> platform_device for this driver. So soc.h is not needed.

OK thanks,

Tony

2013-03-28 09:52:57

by Russell King - ARM Linux

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

On Wed, Mar 27, 2013 at 02:09:18PM -0700, Tony Lindgren wrote:
> > + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> > + rng_clk = clk_get_sys("omap_rng", "ick");

Why is this using clk_get_sys when it should be using clk_get() with the
platform device?

2013-03-28 17:24:44

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

On Thursday 28 March 2013 10:52:28 Russell King - ARM Linux
wrote:
> On Wed, Mar 27, 2013 at 02:09:18PM -0700, Tony Lindgren wrote:
> > > + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> > > + rng_clk = clk_get_sys("omap_rng", "ick");
>
> Why is this using clk_get_sys when it should be using
> clk_get() with the platform device?

Funcion clk_get() needs struct device* instead clk device name.
And I do not know how to get that pointer to device. With
clk_get_sys driver working.

--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-03-28 17:54:09

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

On Wednesday 27 March 2013 23:25:24 Tony Lindgren wrote:
> * Pali Rohár <[email protected]> [130327 15:08]:
> > I will remove above code for checking omap type from hw rand
> > driver, because same code is in omap part which creating
> > platform_device for this driver. So soc.h is not needed.
>
> OK thanks,
>
> Tony

Here is new version of patch:

diff --git a/arch/arm/mach-omap2/Makefile b/arch/arm/mach-omap2/Makefile
index 5423456..37c4e09 100644
--- a/arch/arm/mach-omap2/Makefile
+++ b/arch/arm/mach-omap2/Makefile
@@ -82,7 +82,7 @@ obj-$(CONFIG_OMAP_PM_NOOP) += omap-pm-noop.o
ifeq ($(CONFIG_PM),y)
obj-$(CONFIG_ARCH_OMAP2) += pm24xx.o
obj-$(CONFIG_ARCH_OMAP2) += sleep24xx.o
-obj-$(CONFIG_ARCH_OMAP3) += pm34xx.o sleep34xx.o
+obj-$(CONFIG_ARCH_OMAP3) += pm34xx.o sleep34xx.o omap3-rom-rng.o
obj-$(CONFIG_ARCH_OMAP4) += pm44xx.o omap-mpuss-lowpower.o
obj-$(CONFIG_SOC_OMAP5) += omap-mpuss-lowpower.o
obj-$(CONFIG_PM_DEBUG) += pm-debug.o
diff --git a/arch/arm/mach-omap2/devices.c b/arch/arm/mach-omap2/devices.c
index 1ec7f05..0b6260a1 100644
--- a/arch/arm/mach-omap2/devices.c
+++ b/arch/arm/mach-omap2/devices.c
@@ -486,6 +486,23 @@ static void omap_init_mcspi(void)
static inline void omap_init_mcspi(void) {}
#endif

+extern u32 *omap3_rom_rng_call(u32 id, u32 proc, u32 flags, u32 va_ptr);
+
+static struct platform_device omap3_rom_rng_device = {
+ .name = "omap3-rom-rng",
+ .id = -1,
+ .dev = {
+ .platform_data = omap3_rom_rng_call,
+ },
+};
+
+static void omap_init_rom_rng(void)
+{
+ if (!cpu_is_omap34xx() || omap_type() == OMAP2_DEVICE_TYPE_GP)
+ return;
+ platform_device_register(&omap3_rom_rng_device);
+}
+
/**
* omap_init_rng - bind the RNG hwmod to the RNG omap_device
*
@@ -767,6 +784,7 @@ static int __init omap2_init_devices(void)
}
omap_init_sti();
omap_init_rng();
+ omap_init_rom_rng();
omap_init_sham();
omap_init_aes();
omap_init_vout();
diff --git a/arch/arm/mach-omap2/omap3-rom-rng.S b/arch/arm/mach-omap2/omap3-rom-rng.S
new file mode 100644
index 0000000..5d7d886
--- /dev/null
+++ b/arch/arm/mach-omap2/omap3-rom-rng.S
@@ -0,0 +1,28 @@
+/*
+ * Copyright (C) 2009 Nokia Corporation
+ * Copyright (C) 2013 Pali Rohár <[email protected]>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ */
+
+#include <linux/linkage.h>
+#include <asm/assembler.h>
+
+ENTRY(omap3_rom_rng_call)
+ .arch_extension sec
+ stmfd sp!, {r4-r12, lr}
+ stmfd sp!, {r0-r3}
+ bl v7_flush_dcache_all
+ ldmfd sp!, {r0-r3}
+ mov r6, #0xff
+ mov r12, r0
+ smc #1
+ mov r12, r0
+ bl v7_flush_dcache_all
+ mov r0, #0
+ mcr p15, 0, r0, c7, c5, 0
+ mov r0, r12
+ ldmfd sp!, {r4-r12, pc}
diff --git a/drivers/char/hw_random/Kconfig b/drivers/char/hw_random/Kconfig
index c5a0262..2d51db6 100644
--- a/drivers/char/hw_random/Kconfig
+++ b/drivers/char/hw_random/Kconfig
@@ -153,6 +153,19 @@ config HW_RANDOM_OMAP

If unsure, say Y.

+config HW_RANDOM_OMAP3_ROM
+ tristate "OMAP3 ROM Random Number Generator support"
+ depends on HW_RANDOM && ARCH_OMAP3
+ default HW_RANDOM
+ ---help---
+ This driver provides kernel-side support for the Random Number
+ Generator hardware found on OMAP34xx processors.
+
+ To compile this driver as a module, choose M here: the
+ module will be called omap3-rom-rng.
+
+ If unsure, say Y.
+
config HW_RANDOM_OCTEON
tristate "Octeon Random Number Generator support"
depends on HW_RANDOM && CPU_CAVIUM_OCTEON
diff --git a/drivers/char/hw_random/Makefile b/drivers/char/hw_random/Makefile
index 1fd7eec..c53e018 100644
--- a/drivers/char/hw_random/Makefile
+++ b/drivers/char/hw_random/Makefile
@@ -15,6 +15,7 @@ n2-rng-y := n2-drv.o n2-asm.o
obj-$(CONFIG_HW_RANDOM_VIA) += via-rng.o
obj-$(CONFIG_HW_RANDOM_IXP4XX) += ixp4xx-rng.o
obj-$(CONFIG_HW_RANDOM_OMAP) += omap-rng.o
+obj-$(CONFIG_HW_RANDOM_OMAP3_ROM) += omap3-rom-rng.o
obj-$(CONFIG_HW_RANDOM_PASEMI) += pasemi-rng.o
obj-$(CONFIG_HW_RANDOM_VIRTIO) += virtio-rng.o
obj-$(CONFIG_HW_RANDOM_TX4939) += tx4939-rng.o
diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c
new file mode 100644
index 0000000..5343415
--- /dev/null
+++ b/drivers/char/hw_random/omap3-rom-rng.c
@@ -0,0 +1,165 @@
+/*
+ * omap3-rom-drv.c - RNG driver for TI OMAP3 CPU family
+ *
+ * Copyright (C) 2009 Nokia Corporation
+ * Author: Juha Yrjola <[email protected]>
+ *
+ * Copyright (C) 2013 Pali Rohár <[email protected]>
+ *
+ * This file is licensed under the terms of the GNU General Public
+ * License version 2. This program is licensed "as is" without any
+ * warranty of any kind, whether express or implied.
+ */
+
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/random.h>
+#include <linux/hw_random.h>
+#include <linux/timer.h>
+#include <linux/clk.h>
+#include <linux/err.h>
+#include <linux/platform_device.h>
+
+#define SEC_HAL_RNG_GENERATE 29
+#define RNG_RESET 0x01
+#define RNG_GEN_PRNG_HW_INIT 0x02
+#define RNG_GEN_HW 0x08
+
+static const char *omap3_rom_rng_name = "OMAP3 ROM RNG";
+
+static u32 (*omap3_rom_rng_call)(u32, u32, u32, u32);
+
+static int call_sec_rom(u32 appl_id, u32 proc_id, u32 flag, ...)
+{
+ va_list ap;
+ u32 ret;
+ u32 val;
+
+ va_start(ap, flag);
+ val = *(u32 *) &ap;
+ local_irq_disable();
+ local_fiq_disable();
+ ret = omap3_rom_rng_call(appl_id, proc_id, flag,
+ (u32) virt_to_phys((void *) val));
+ local_fiq_enable();
+ local_irq_enable();
+ va_end(ap);
+
+ return ret;
+}
+
+static struct timer_list idle_timer;
+static int rng_idle;
+static struct clk *rng_clk;
+
+static void omap3_rom_idle_rng(unsigned long data)
+{
+ int r;
+
+ r = call_sec_rom(SEC_HAL_RNG_GENERATE, 0, 0, 3, NULL, 0,
+ RNG_RESET);
+ if (r != 0) {
+ printk(KERN_ERR "%s: reset failed: %d\n",
+ omap3_rom_rng_name, r);
+ return;
+ }
+ clk_disable_unprepare(rng_clk);
+ rng_idle = 1;
+}
+
+static int omap3_rom_get_random(void *buf, unsigned int count)
+{
+ u32 r;
+ u32 ptr;
+
+ del_timer_sync(&idle_timer);
+ if (rng_idle) {
+ clk_prepare_enable(rng_clk);
+ r = call_sec_rom(SEC_HAL_RNG_GENERATE, 0, 0, 3, NULL, 0,
+ RNG_GEN_PRNG_HW_INIT);
+ if (r != 0) {
+ clk_disable_unprepare(rng_clk);
+ printk(KERN_ERR "%s: HW init failed: %d\n",
+ omap3_rom_rng_name, r);
+ return -EIO;
+ }
+ rng_idle = 0;
+ }
+
+ ptr = virt_to_phys(buf);
+ r = call_sec_rom(SEC_HAL_RNG_GENERATE, 0, 0, 3, ptr,
+ count, RNG_GEN_HW);
+ mod_timer(&idle_timer, jiffies + msecs_to_jiffies(500));
+ if (r != 0)
+ return -EINVAL;
+ return 0;
+}
+
+static int omap3_rom_rng_data_present(struct hwrng *rng, int wait)
+{
+ return 1;
+}
+
+static int omap3_rom_rng_data_read(struct hwrng *rng, u32 *data)
+{
+ int r;
+
+ r = omap3_rom_get_random(data, 4);
+ if (r < 0)
+ return r;
+ return 4;
+}
+
+static struct hwrng omap3_rom_rng_ops = {
+ .name = "omap3-rom",
+ .data_present = omap3_rom_rng_data_present,
+ .data_read = omap3_rom_rng_data_read,
+};
+
+static int omap3_rom_rng_probe(struct platform_device *pdev)
+{
+ printk(KERN_INFO "%s: initializing\n", omap3_rom_rng_name);
+
+ omap3_rom_rng_call = pdev->dev.platform_data;
+ if (!omap3_rom_rng_call) {
+ printk(KERN_ERR "%s: omap3_rom_rng_call is NULL\n",
+ omap3_rom_rng_name);
+ return -EINVAL;
+ }
+
+ setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
+ rng_clk = clk_get_sys("omap_rng", "ick");
+ if (IS_ERR(rng_clk)) {
+ printk(KERN_ERR "%s: unable to get RNG clock\n",
+ omap3_rom_rng_name);
+ return IS_ERR(rng_clk);
+ }
+
+ /* Leave the RNG in reset state. */
+ clk_prepare_enable(rng_clk);
+ omap3_rom_idle_rng(0);
+
+ return hwrng_register(&omap3_rom_rng_ops);
+}
+
+static int omap3_rom_rng_remove(struct platform_device *pdev)
+{
+ hwrng_unregister(&omap3_rom_rng_ops);
+ return 0;
+}
+
+static struct platform_driver omap3_rom_rng_driver = {
+ .driver = {
+ .name = "omap3-rom-rng",
+ .owner = THIS_MODULE,
+ },
+ .probe = omap3_rom_rng_probe,
+ .remove = omap3_rom_rng_remove,
+};
+
+module_platform_driver(omap3_rom_rng_driver);
+
+MODULE_ALIAS("platform:omap3-rom-rng");
+MODULE_AUTHOR("Juha Yrjola");
+MODULE_AUTHOR("Pali Rohár <[email protected]>");
+MODULE_LICENSE("GPL");

--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-03-28 21:44:23

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

* Pali Rohár <[email protected]> [130328 10:58]:
>
> Here is new version of patch:
>
> --- a/arch/arm/mach-omap2/devices.c
> +++ b/arch/arm/mach-omap2/devices.c
> @@ -486,6 +486,23 @@ static void omap_init_mcspi(void)
> static inline void omap_init_mcspi(void) {}
> #endif
>
> +extern u32 *omap3_rom_rng_call(u32 id, u32 proc, u32 flags, u32 va_ptr);
> +
> +static struct platform_device omap3_rom_rng_device = {
> + .name = "omap3-rom-rng",
> + .id = -1,
> + .dev = {
> + .platform_data = omap3_rom_rng_call,
> + },
> +};
> +
> +static void omap_init_rom_rng(void)
> +{
> + if (!cpu_is_omap34xx() || omap_type() == OMAP2_DEVICE_TYPE_GP)
> + return;
> + platform_device_register(&omap3_rom_rng_device);
> +}
> +
> /**
> * omap_init_rng - bind the RNG hwmod to the RNG omap_device
> *

This driver probably only works on Nokia boards because of the
different SMC call numbering. Until it's been verified on some
other HS omap34xx, I'd probably register this only from the
Nokia board-*.c file.

> --- /dev/null
> +++ b/drivers/char/hw_random/omap3-rom-rng.c
> +static int omap3_rom_rng_probe(struct platform_device *pdev)
> +{
> + printk(KERN_INFO "%s: initializing\n", omap3_rom_rng_name);
> +
> + omap3_rom_rng_call = pdev->dev.platform_data;
> + if (!omap3_rom_rng_call) {
> + printk(KERN_ERR "%s: omap3_rom_rng_call is NULL\n",
> + omap3_rom_rng_name);
> + return -EINVAL;
> + }
> +
> + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> + rng_clk = clk_get_sys("omap_rng", "ick");
> + if (IS_ERR(rng_clk)) {
> + printk(KERN_ERR "%s: unable to get RNG clock\n",
> + omap3_rom_rng_name);
> + return IS_ERR(rng_clk);
> + }

You can use regular clk_get if you add the alias to
struct omap_clk omap3xxx_clks table.

Regards,

Tony

2013-03-31 09:28:18

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

On Thursday 28 March 2013 22:44:11 Tony Lindgren wrote:
> * Pali Rohár <[email protected]> [130328 10:58]:
> > Here is new version of patch:
> >
> > --- a/arch/arm/mach-omap2/devices.c
> > +++ b/arch/arm/mach-omap2/devices.c
> > @@ -486,6 +486,23 @@ static void omap_init_mcspi(void)
> >
> > static inline void omap_init_mcspi(void) {}
> > #endif
> >
> > +extern u32 *omap3_rom_rng_call(u32 id, u32 proc, u32 flags,
> > u32 va_ptr); +
> > +static struct platform_device omap3_rom_rng_device = {
> > + .name = "omap3-rom-rng",
> > + .id = -1,
> > + .dev = {
> > + .platform_data = omap3_rom_rng_call,
> > + },
> > +};
> > +
> > +static void omap_init_rom_rng(void)
> > +{
> > + if (!cpu_is_omap34xx() || omap_type() ==
> > OMAP2_DEVICE_TYPE_GP) + return;
> > + platform_device_register(&omap3_rom_rng_device);
> > +}
> > +
> >
> > /**
> >
> > * omap_init_rng - bind the RNG hwmod to the RNG
> > omap_device *
>
> This driver probably only works on Nokia boards because of the
> different SMC call numbering. Until it's been verified on some
> other HS omap34xx, I'd probably register this only from the
> Nokia board-*.c file.
>

Freemangordon, can you look at this smc and errara 430973 code if
they could be merged? Really omap3_rom_rng_call function looks
like n900 specific.

Link: https://lkml.org/lkml/2013/3/28/398

> > --- /dev/null
> > +++ b/drivers/char/hw_random/omap3-rom-rng.c
> > +static int omap3_rom_rng_probe(struct platform_device
> > *pdev) +{
> > + printk(KERN_INFO "%s: initializing\n",
> > omap3_rom_rng_name); +
> > + omap3_rom_rng_call = pdev->dev.platform_data;
> > + if (!omap3_rom_rng_call) {
> > + printk(KERN_ERR "%s: omap3_rom_rng_call is NULL\n",
> > + omap3_rom_rng_name);
> > + return -EINVAL;
> > + }
> > +
> > + setup_timer(&idle_timer, omap3_rom_idle_rng, 0);
> > + rng_clk = clk_get_sys("omap_rng", "ick");
> > + if (IS_ERR(rng_clk)) {
> > + printk(KERN_ERR "%s: unable to get RNG clock\n",
> > + omap3_rom_rng_name);
> > + return IS_ERR(rng_clk);
> > + }
>
> You can use regular clk_get if you add the alias to
> struct omap_clk omap3xxx_clks table.
>
> Regards,
>
> Tony

Tony, can you show me how?

--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-04-01 16:25:49

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH] OMAP3 ROM Random Number Generator support

* Pali Rohár <[email protected]> [130331 02:32]:
> On Thursday 28 March 2013 22:44:11 Tony Lindgren wrote:
> >
> > You can use regular clk_get if you add the alias to
> > struct omap_clk omap3xxx_clks table.
>
> Tony, can you show me how?

Take a look at the omap3xxx_clks in cclock3xxx_data.c.
Note how some entries have things like "omap_hsmmc.0" and
"ick". By adding those your driver can request the clock
with clk_get(&pdev->dev, "ick").

Regards,

Tony

2013-09-18 20:07:49

by Pali Rohár

[permalink] [raw]
Subject: [PATCH 0/2] OMAP3 ROM Random Number Generator support

This two patches adding support for OMAP3 ROM Random Number Generator on Nokia N900.

Pali Rohár (2):
hwrng: OMAP3 ROM Random Number Generator support
RX-51: Add support for OMAP3 ROM Random Number Generator

arch/arm/mach-omap2/board-rx51.c | 10 +++
arch/arm/mach-omap2/omap-secure.c | 11 +++
arch/arm/mach-omap2/omap-secure.h | 1 +
drivers/char/hw_random/Kconfig | 13 +++
drivers/char/hw_random/Makefile | 1 +
drivers/char/hw_random/omap3-rom-rng.c | 145 ++++++++++++++++++++++++++++++++
6 files changed, 181 insertions(+)
create mode 100644 drivers/char/hw_random/omap3-rom-rng.c

--
1.7.10.4

2013-09-18 20:08:08

by Pali Rohár

[permalink] [raw]
Subject: [PATCH 1/2] hwrng: OMAP3 ROM Random Number Generator support

This driver provides kernel-side support for the Random Number
Generator hardware found on OMAP34xx processors.

Signed-off-by: Pali Rohár <[email protected]>
Signed-off-by: Juha Yrjola <[email protected]>
---
drivers/char/hw_random/Kconfig | 13 +++
drivers/char/hw_random/Makefile | 1 +
drivers/char/hw_random/omap3-rom-rng.c | 145 ++++++++++++++++++++++++++++++++
3 files changed, 159 insertions(+)
create mode 100644 drivers/char/hw_random/omap3-rom-rng.c

diff --git a/drivers/char/hw_random/Kconfig b/drivers/char/hw_random/Kconfig
index 0aa9d91..0a331c3 100644
--- a/drivers/char/hw_random/Kconfig
+++ b/drivers/char/hw_random/Kconfig
@@ -165,6 +165,19 @@ config HW_RANDOM_OMAP

If unsure, say Y.

+config HW_RANDOM_OMAP3_ROM
+ tristate "OMAP3 ROM Random Number Generator support"
+ depends on HW_RANDOM && ARCH_OMAP3
+ default HW_RANDOM
+ ---help---
+ This driver provides kernel-side support for the Random Number
+ Generator hardware found on OMAP34xx processors.
+
+ To compile this driver as a module, choose M here: the
+ module will be called omap3-rom-rng.
+
+ If unsure, say Y.
+
config HW_RANDOM_OCTEON
tristate "Octeon Random Number Generator support"
depends on HW_RANDOM && CAVIUM_OCTEON_SOC
diff --git a/drivers/char/hw_random/Makefile b/drivers/char/hw_random/Makefile
index bed467c..7c8aa80 100644
--- a/drivers/char/hw_random/Makefile
+++ b/drivers/char/hw_random/Makefile
@@ -15,6 +15,7 @@ n2-rng-y := n2-drv.o n2-asm.o
obj-$(CONFIG_HW_RANDOM_VIA) += via-rng.o
obj-$(CONFIG_HW_RANDOM_IXP4XX) += ixp4xx-rng.o
obj-$(CONFIG_HW_RANDOM_OMAP) += omap-rng.o
+obj-$(CONFIG_HW_RANDOM_OMAP3_ROM) += omap3-rom-rng.o
obj-$(CONFIG_HW_RANDOM_PASEMI) += pasemi-rng.o
obj-$(CONFIG_HW_RANDOM_VIRTIO) += virtio-rng.o
obj-$(CONFIG_HW_RANDOM_TX4939) += tx4939-rng.o
diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c
new file mode 100644
index 0000000..a9dbb2d
--- /dev/null
+++ b/drivers/char/hw_random/omap3-rom-rng.c
@@ -0,0 +1,145 @@
+/*
+ * omap3-rom-rng.c - RNG driver for TI OMAP3 CPU family
+ *
+ * Copyright (C) 2009 Nokia Corporation
+ * Author: Juha Yrjola <[email protected]>
+ *
+ * Copyright (C) 2013 Pali Rohár <[email protected]>
+ *
+ * This file is licensed under the terms of the GNU General Public
+ * License version 2. This program is licensed "as is" without any
+ * warranty of any kind, whether express or implied.
+ */
+
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/random.h>
+#include <linux/hw_random.h>
+#include <linux/timer.h>
+#include <linux/clk.h>
+#include <linux/err.h>
+#include <linux/platform_device.h>
+
+#define RNG_RESET 0x01
+#define RNG_GEN_PRNG_HW_INIT 0x02
+#define RNG_GEN_HW 0x08
+
+static const char *omap3_rom_rng_name = "OMAP3 ROM RNG";
+
+/* param1: ptr, param2: count, param3: flag */
+static u32 (*omap3_rom_rng_call)(u32, u32, u32);
+
+static struct timer_list idle_timer;
+static int rng_idle;
+static struct clk *rng_clk;
+
+static void omap3_rom_rng_idle(unsigned long data)
+{
+ int r;
+
+ r = omap3_rom_rng_call(0, 0, RNG_RESET);
+ if (r != 0) {
+ printk(KERN_ERR "%s: reset failed: %d\n",
+ omap3_rom_rng_name, r);
+ return;
+ }
+ clk_disable_unprepare(rng_clk);
+ rng_idle = 1;
+}
+
+static int omap3_rom_rng_get_random(void *buf, unsigned int count)
+{
+ u32 r;
+ u32 ptr;
+
+ del_timer_sync(&idle_timer);
+ if (rng_idle) {
+ clk_prepare_enable(rng_clk);
+ r = omap3_rom_rng_call(0, 0, RNG_GEN_PRNG_HW_INIT);
+ if (r != 0) {
+ clk_disable_unprepare(rng_clk);
+ printk(KERN_ERR "%s: HW init failed: %d\n",
+ omap3_rom_rng_name, r);
+ return -EIO;
+ }
+ rng_idle = 0;
+ }
+
+ ptr = virt_to_phys(buf);
+ r = omap3_rom_rng_call(ptr, count, RNG_GEN_HW);
+ mod_timer(&idle_timer, jiffies + msecs_to_jiffies(500));
+ if (r != 0)
+ return -EINVAL;
+ return 0;
+}
+
+static int omap3_rom_rng_data_present(struct hwrng *rng, int wait)
+{
+ return 1;
+}
+
+static int omap3_rom_rng_data_read(struct hwrng *rng, u32 *data)
+{
+ int r;
+
+ r = omap3_rom_rng_get_random(data, 4);
+ if (r < 0)
+ return r;
+ return 4;
+}
+
+static struct hwrng omap3_rom_rng_ops = {
+ .name = "omap3-rom",
+ .data_present = omap3_rom_rng_data_present,
+ .data_read = omap3_rom_rng_data_read,
+};
+
+static int omap3_rom_rng_probe(struct platform_device *pdev)
+{
+ printk(KERN_INFO "%s: initializing\n", omap3_rom_rng_name);
+
+ omap3_rom_rng_call = pdev->dev.platform_data;
+ if (!omap3_rom_rng_call) {
+ printk(KERN_ERR "%s: omap3_rom_rng_call is NULL\n",
+ omap3_rom_rng_name);
+ return -EINVAL;
+ }
+
+ setup_timer(&idle_timer, omap3_rom_rng_idle, 0);
+ rng_clk = clk_get(&pdev->dev, "ick");
+ if (IS_ERR(rng_clk)) {
+ printk(KERN_ERR "%s: unable to get RNG clock\n",
+ omap3_rom_rng_name);
+ return IS_ERR(rng_clk);
+ }
+
+ /* Leave the RNG in reset state. */
+ clk_prepare_enable(rng_clk);
+ omap3_rom_rng_idle(0);
+
+ return hwrng_register(&omap3_rom_rng_ops);
+}
+
+static int omap3_rom_rng_remove(struct platform_device *pdev)
+{
+ hwrng_unregister(&omap3_rom_rng_ops);
+ clk_disable_unprepare(rng_clk);
+ clk_put(rng_clk);
+ return 0;
+}
+
+static struct platform_driver omap3_rom_rng_driver = {
+ .driver = {
+ .name = "omap3-rom-rng",
+ .owner = THIS_MODULE,
+ },
+ .probe = omap3_rom_rng_probe,
+ .remove = omap3_rom_rng_remove,
+};
+
+module_platform_driver(omap3_rom_rng_driver);
+
+MODULE_ALIAS("platform:omap3-rom-rng");
+MODULE_AUTHOR("Juha Yrjola");
+MODULE_AUTHOR("Pali Rohár <[email protected]>");
+MODULE_LICENSE("GPL");
--
1.7.10.4

2013-09-18 20:08:15

by Pali Rohár

[permalink] [raw]
Subject: [PATCH 2/2] RX-51: Add support for OMAP3 ROM Random Number Generator

Signed-off-by: Pali Rohár <[email protected]>
---
arch/arm/mach-omap2/board-rx51.c | 10 ++++++++++
arch/arm/mach-omap2/omap-secure.c | 11 +++++++++++
arch/arm/mach-omap2/omap-secure.h | 1 +
3 files changed, 22 insertions(+)

diff --git a/arch/arm/mach-omap2/board-rx51.c b/arch/arm/mach-omap2/board-rx51.c
index db168c9..c2a3e39 100644
--- a/arch/arm/mach-omap2/board-rx51.c
+++ b/arch/arm/mach-omap2/board-rx51.c
@@ -93,6 +93,14 @@ static struct omap_musb_board_data musb_board_data = {
.power = 0,
};

+static struct platform_device omap3_rom_rng_device = {
+ .name = "omap_rng",
+ .id = -1,
+ .dev = {
+ .platform_data = rx51_secure_rng_call,
+ },
+};
+
static void __init rx51_init(void)
{
struct omap_sdrc_params *sdrc_params;
@@ -113,6 +121,8 @@ static void __init rx51_init(void)
/* set IBE to 1 */
rx51_secure_update_aux_cr(BIT(6), 0);
#endif
+ pr_info("RX-51: Registring OMAP3 HWRNG device\n");
+ platform_device_register(&omap3_rom_rng_device);
}

/* Ensure SDRC pins are mux'd for self-refresh */
diff --git a/arch/arm/mach-omap2/omap-secure.c b/arch/arm/mach-omap2/omap-secure.c
index 146a7c4..5ac122e 100644
--- a/arch/arm/mach-omap2/omap-secure.c
+++ b/arch/arm/mach-omap2/omap-secure.c
@@ -135,3 +135,14 @@ u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits)
FLAG_START_CRITICAL,
1, acr, 0, 0, 0);
}
+
+/**
+ * rx51_secure_rng_call: Routine for HW random generator
+ */
+u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag)
+{
+ return rx51_secure_dispatcher(RX51_PPA_HWRNG,
+ 0,
+ NO_FLAG,
+ 3, ptr, count, flag, 0);
+}
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index 51b59c6..f6cabb0 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -65,6 +65,7 @@ extern int omap_secure_ram_reserve_memblock(void);
extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
u32 arg1, u32 arg2, u32 arg3, u32 arg4);
extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
+extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);

#ifdef CONFIG_OMAP4_ERRATA_I688
extern int omap_barrier_reserve_memblock(void);
--
1.7.10.4

2013-09-18 20:22:48

by Joe Perches

[permalink] [raw]
Subject: Re: [PATCH 1/2] hwrng: OMAP3 ROM Random Number Generator support

On Wed, 2013-09-18 at 22:05 +0200, Pali Roh?r wrote:
> This driver provides kernel-side support for the Random Number
> Generator hardware found on OMAP34xx processors.

[]

> diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c

trivial note:

It produces smaller overall code to add
#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
before any #include and use

> +static void omap3_rom_rng_idle(unsigned long data)
> +{
> + int r;
> +
> + r = omap3_rom_rng_call(0, 0, RNG_RESET);
> + if (r != 0) {
> + printk(KERN_ERR "%s: reset failed: %d\n",
> + omap3_rom_rng_name, r);

pr_err("reset failed: %d\n", r);

> +static int omap3_rom_rng_get_random(void *buf, unsigned int count)
> +{
[]
> + if (r != 0) {
> + clk_disable_unprepare(rng_clk);
> + printk(KERN_ERR "%s: HW init failed: %d\n",
> + omap3_rom_rng_name, r);

pr_err("HW init failed: %d\n", r);

etc...

2013-09-18 20:39:59

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH 2/2] RX-51: Add support for OMAP3 ROM Random Number Generator

* Pali Rohár <[email protected]> [130918 13:15]:
> Signed-off-by: Pali Rohár <[email protected]>

Description please, then also add a note that this makes
sense to do as a platform device at least until we have
some ARM generic way to deal with SMC calls.

> arch/arm/mach-omap2/board-rx51.c | 10 ++++++++++
> arch/arm/mach-omap2/omap-secure.c | 11 +++++++++++
> arch/arm/mach-omap2/omap-secure.h | 1 +
> 3 files changed, 22 insertions(+)
>
> diff --git a/arch/arm/mach-omap2/board-rx51.c b/arch/arm/mach-omap2/board-rx51.c
> index db168c9..c2a3e39 100644
> --- a/arch/arm/mach-omap2/board-rx51.c
> +++ b/arch/arm/mach-omap2/board-rx51.c
> @@ -93,6 +93,14 @@ static struct omap_musb_board_data musb_board_data = {
> .power = 0,
> };
>
> +static struct platform_device omap3_rom_rng_device = {
> + .name = "omap_rng",
> + .id = -1,
> + .dev = {
> + .platform_data = rx51_secure_rng_call,
> + },
> +};
> +
> static void __init rx51_init(void)
> {
> struct omap_sdrc_params *sdrc_params;
> @@ -113,6 +121,8 @@ static void __init rx51_init(void)
> /* set IBE to 1 */
> rx51_secure_update_aux_cr(BIT(6), 0);
> #endif
> + pr_info("RX-51: Registring OMAP3 HWRNG device\n");
> + platform_device_register(&omap3_rom_rng_device);
> }
>
> /* Ensure SDRC pins are mux'd for self-refresh */

Maybe this should be in board-rx51-peripherals.c instead?

That way we can initialize the legacy platform devices
from there for DT based booting too and don't have to
move code around when moving to DT based booting.

Regards,

Tony

2013-09-18 20:50:34

by Aaro Koskinen

[permalink] [raw]
Subject: Re: [PATCH 1/2] hwrng: OMAP3 ROM Random Number Generator support

Hi,

On Wed, Sep 18, 2013 at 10:05:56PM +0200, Pali Roh?r wrote:
> + if (IS_ERR(rng_clk)) {
> + printk(KERN_ERR "%s: unable to get RNG clock\n",
> + omap3_rom_rng_name);
> + return IS_ERR(rng_clk);

This should be PTR_ERR().

A.

2013-09-20 13:26:12

by Pali Rohár

[permalink] [raw]
Subject: [PATCH v2 0/3] OMAP3 ROM Random Number Generator support

This patch series adding support for OMAP3 ROM Random Number Generator on Nokia N900.
In previous version I forgot to send patch which changing clk dev id to new driver name.

Pali Rohár (3):
omap2: Change clk dev id for rng to omap3-rom-rng
hwrng: OMAP3 ROM Random Number Generator support
RX-51: Add support for OMAP3 ROM Random Number Generator

arch/arm/mach-omap2/board-rx51-peripherals.c | 19 ++++
arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
arch/arm/mach-omap2/omap-secure.c | 11 ++
arch/arm/mach-omap2/omap-secure.h | 1 +
drivers/char/hw_random/Kconfig | 13 +++
drivers/char/hw_random/Makefile | 1 +
drivers/char/hw_random/omap3-rom-rng.c | 141 ++++++++++++++++++++++++++
7 files changed, 187 insertions(+), 1 deletion(-)
create mode 100644 drivers/char/hw_random/omap3-rom-rng.c

--
1.7.10.4

2013-09-20 13:26:20

by Pali Rohár

[permalink] [raw]
Subject: [PATCH v2 3/3] RX-51: Add support for OMAP3 ROM Random Number Generator

Adding this driver as platform device and only for RX-51 until somebody test if
it working also on other OMAP3 HS devices and until there will be generic ARM
way to deal with SMC calls.

Signed-off-by: Pali Rohár <[email protected]>
---
arch/arm/mach-omap2/board-rx51-peripherals.c | 19 +++++++++++++++++++
arch/arm/mach-omap2/omap-secure.c | 11 +++++++++++
arch/arm/mach-omap2/omap-secure.h | 1 +
3 files changed, 31 insertions(+)

diff --git a/arch/arm/mach-omap2/board-rx51-peripherals.c b/arch/arm/mach-omap2/board-rx51-peripherals.c
index c3270c0..497d260 100644
--- a/arch/arm/mach-omap2/board-rx51-peripherals.c
+++ b/arch/arm/mach-omap2/board-rx51-peripherals.c
@@ -57,6 +57,8 @@
#include "common-board-devices.h"
#include "gpmc.h"
#include "gpmc-onenand.h"
+#include "soc.h"
+#include "omap-secure.h"

#define SYSTEM_REV_B_USES_VAUX3 0x1699
#define SYSTEM_REV_S_USES_VAUX3 0x8
@@ -1289,6 +1291,22 @@ static void __init rx51_init_twl4030_hwmon(void)
platform_device_register(&madc_hwmon);
}

+static struct platform_device omap3_rom_rng_device = {
+ .name = "omap3-rom-rng",
+ .id = -1,
+ .dev = {
+ .platform_data = rx51_secure_rng_call,
+ },
+};
+
+static void __init rx51_init_omap3_rom_rng(void)
+{
+ if (omap_type() == OMAP2_DEVICE_TYPE_SEC) {
+ pr_info("RX-51: Registring OMAP3 HWRNG device\n");
+ platform_device_register(&omap3_rom_rng_device);
+ }
+}
+
void __init rx51_peripherals_init(void)
{
rx51_i2c_init();
@@ -1309,5 +1327,6 @@ void __init rx51_peripherals_init(void)

rx51_charger_init();
rx51_init_twl4030_hwmon();
+ rx51_init_omap3_rom_rng();
}

diff --git a/arch/arm/mach-omap2/omap-secure.c b/arch/arm/mach-omap2/omap-secure.c
index 146a7c4..5ac122e 100644
--- a/arch/arm/mach-omap2/omap-secure.c
+++ b/arch/arm/mach-omap2/omap-secure.c
@@ -135,3 +135,14 @@ u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits)
FLAG_START_CRITICAL,
1, acr, 0, 0, 0);
}
+
+/**
+ * rx51_secure_rng_call: Routine for HW random generator
+ */
+u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag)
+{
+ return rx51_secure_dispatcher(RX51_PPA_HWRNG,
+ 0,
+ NO_FLAG,
+ 3, ptr, count, flag, 0);
+}
diff --git a/arch/arm/mach-omap2/omap-secure.h b/arch/arm/mach-omap2/omap-secure.h
index 51b59c6..f6cabb0 100644
--- a/arch/arm/mach-omap2/omap-secure.h
+++ b/arch/arm/mach-omap2/omap-secure.h
@@ -65,6 +65,7 @@ extern int omap_secure_ram_reserve_memblock(void);
extern u32 rx51_secure_dispatcher(u32 idx, u32 process, u32 flag, u32 nargs,
u32 arg1, u32 arg2, u32 arg3, u32 arg4);
extern u32 rx51_secure_update_aux_cr(u32 set_bits, u32 clear_bits);
+extern u32 rx51_secure_rng_call(u32 ptr, u32 count, u32 flag);

#ifdef CONFIG_OMAP4_ERRATA_I688
extern int omap_barrier_reserve_memblock(void);
--
1.7.10.4

2013-09-20 13:26:37

by Pali Rohár

[permalink] [raw]
Subject: [PATCH v2 2/3] hwrng: OMAP3 ROM Random Number Generator support

This driver provides kernel-side support for the Random Number
Generator hardware found on OMAP34xx processors.

This driver comes from Maemo 2.6.28 kernel and was tested on Nokia RX-51.
It is platform device because it needs board specific function for smc calls.

Signed-off-by: Pali Rohár <[email protected]>
Signed-off-by: Juha Yrjola <[email protected]>
---
drivers/char/hw_random/Kconfig | 13 +++
drivers/char/hw_random/Makefile | 1 +
drivers/char/hw_random/omap3-rom-rng.c | 141 ++++++++++++++++++++++++++++++++
3 files changed, 155 insertions(+)
create mode 100644 drivers/char/hw_random/omap3-rom-rng.c

diff --git a/drivers/char/hw_random/Kconfig b/drivers/char/hw_random/Kconfig
index 0aa9d91..0a331c3 100644
--- a/drivers/char/hw_random/Kconfig
+++ b/drivers/char/hw_random/Kconfig
@@ -165,6 +165,19 @@ config HW_RANDOM_OMAP

If unsure, say Y.

+config HW_RANDOM_OMAP3_ROM
+ tristate "OMAP3 ROM Random Number Generator support"
+ depends on HW_RANDOM && ARCH_OMAP3
+ default HW_RANDOM
+ ---help---
+ This driver provides kernel-side support for the Random Number
+ Generator hardware found on OMAP34xx processors.
+
+ To compile this driver as a module, choose M here: the
+ module will be called omap3-rom-rng.
+
+ If unsure, say Y.
+
config HW_RANDOM_OCTEON
tristate "Octeon Random Number Generator support"
depends on HW_RANDOM && CAVIUM_OCTEON_SOC
diff --git a/drivers/char/hw_random/Makefile b/drivers/char/hw_random/Makefile
index bed467c..7c8aa80 100644
--- a/drivers/char/hw_random/Makefile
+++ b/drivers/char/hw_random/Makefile
@@ -15,6 +15,7 @@ n2-rng-y := n2-drv.o n2-asm.o
obj-$(CONFIG_HW_RANDOM_VIA) += via-rng.o
obj-$(CONFIG_HW_RANDOM_IXP4XX) += ixp4xx-rng.o
obj-$(CONFIG_HW_RANDOM_OMAP) += omap-rng.o
+obj-$(CONFIG_HW_RANDOM_OMAP3_ROM) += omap3-rom-rng.o
obj-$(CONFIG_HW_RANDOM_PASEMI) += pasemi-rng.o
obj-$(CONFIG_HW_RANDOM_VIRTIO) += virtio-rng.o
obj-$(CONFIG_HW_RANDOM_TX4939) += tx4939-rng.o
diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c
new file mode 100644
index 0000000..c853e9e
--- /dev/null
+++ b/drivers/char/hw_random/omap3-rom-rng.c
@@ -0,0 +1,141 @@
+/*
+ * omap3-rom-rng.c - RNG driver for TI OMAP3 CPU family
+ *
+ * Copyright (C) 2009 Nokia Corporation
+ * Author: Juha Yrjola <[email protected]>
+ *
+ * Copyright (C) 2013 Pali Rohár <[email protected]>
+ *
+ * This file is licensed under the terms of the GNU General Public
+ * License version 2. This program is licensed "as is" without any
+ * warranty of any kind, whether express or implied.
+ */
+
+#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
+
+#include <linux/module.h>
+#include <linux/init.h>
+#include <linux/random.h>
+#include <linux/hw_random.h>
+#include <linux/timer.h>
+#include <linux/clk.h>
+#include <linux/err.h>
+#include <linux/platform_device.h>
+
+#define RNG_RESET 0x01
+#define RNG_GEN_PRNG_HW_INIT 0x02
+#define RNG_GEN_HW 0x08
+
+/* param1: ptr, param2: count, param3: flag */
+static u32 (*omap3_rom_rng_call)(u32, u32, u32);
+
+static struct timer_list idle_timer;
+static int rng_idle;
+static struct clk *rng_clk;
+
+static void omap3_rom_rng_idle(unsigned long data)
+{
+ int r;
+
+ r = omap3_rom_rng_call(0, 0, RNG_RESET);
+ if (r != 0) {
+ pr_err("reset failed: %d\n", r);
+ return;
+ }
+ clk_disable_unprepare(rng_clk);
+ rng_idle = 1;
+}
+
+static int omap3_rom_rng_get_random(void *buf, unsigned int count)
+{
+ u32 r;
+ u32 ptr;
+
+ del_timer_sync(&idle_timer);
+ if (rng_idle) {
+ clk_prepare_enable(rng_clk);
+ r = omap3_rom_rng_call(0, 0, RNG_GEN_PRNG_HW_INIT);
+ if (r != 0) {
+ clk_disable_unprepare(rng_clk);
+ pr_err("HW init failed: %d\n", r);
+ return -EIO;
+ }
+ rng_idle = 0;
+ }
+
+ ptr = virt_to_phys(buf);
+ r = omap3_rom_rng_call(ptr, count, RNG_GEN_HW);
+ mod_timer(&idle_timer, jiffies + msecs_to_jiffies(500));
+ if (r != 0)
+ return -EINVAL;
+ return 0;
+}
+
+static int omap3_rom_rng_data_present(struct hwrng *rng, int wait)
+{
+ return 1;
+}
+
+static int omap3_rom_rng_data_read(struct hwrng *rng, u32 *data)
+{
+ int r;
+
+ r = omap3_rom_rng_get_random(data, 4);
+ if (r < 0)
+ return r;
+ return 4;
+}
+
+static struct hwrng omap3_rom_rng_ops = {
+ .name = "omap3-rom",
+ .data_present = omap3_rom_rng_data_present,
+ .data_read = omap3_rom_rng_data_read,
+};
+
+static int omap3_rom_rng_probe(struct platform_device *pdev)
+{
+ pr_info("initializing\n");
+
+ omap3_rom_rng_call = pdev->dev.platform_data;
+ if (!omap3_rom_rng_call) {
+ pr_err("omap3_rom_rng_call is NULL\n");
+ return -EINVAL;
+ }
+
+ setup_timer(&idle_timer, omap3_rom_rng_idle, 0);
+ rng_clk = clk_get(&pdev->dev, "ick");
+ if (IS_ERR(rng_clk)) {
+ pr_err("unable to get RNG clock\n");
+ return PTR_ERR(rng_clk);
+ }
+
+ /* Leave the RNG in reset state. */
+ clk_prepare_enable(rng_clk);
+ omap3_rom_rng_idle(0);
+
+ return hwrng_register(&omap3_rom_rng_ops);
+}
+
+static int omap3_rom_rng_remove(struct platform_device *pdev)
+{
+ hwrng_unregister(&omap3_rom_rng_ops);
+ clk_disable_unprepare(rng_clk);
+ clk_put(rng_clk);
+ return 0;
+}
+
+static struct platform_driver omap3_rom_rng_driver = {
+ .driver = {
+ .name = "omap3-rom-rng",
+ .owner = THIS_MODULE,
+ },
+ .probe = omap3_rom_rng_probe,
+ .remove = omap3_rom_rng_remove,
+};
+
+module_platform_driver(omap3_rom_rng_driver);
+
+MODULE_ALIAS("platform:omap3-rom-rng");
+MODULE_AUTHOR("Juha Yrjola");
+MODULE_AUTHOR("Pali Rohár <[email protected]>");
+MODULE_LICENSE("GPL");
--
1.7.10.4

2013-09-20 13:27:00

by Pali Rohár

[permalink] [raw]
Subject: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

Name omap_rng is already used by omap_rng driver which is for omap2 and omap4.
For omap3 HS devices there is new driver omap3-rom-rng which needs that clk.
And because there cannot be two drivers with same name, rename omap3 clk dev id.

Signed-off-by: Pali Rohár <[email protected]>
---
arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
index 334b767..5059338 100644
--- a/arch/arm/mach-omap2/cclock3xxx_data.c
+++ b/arch/arm/mach-omap2/cclock3xxx_data.c
@@ -3274,7 +3274,7 @@ static struct omap_clk omap36xx_clks[] = {
*/
static struct omap_clk omap34xx_omap36xx_clks[] = {
CLK(NULL, "aes1_ick", &aes1_ick),
- CLK("omap_rng", "ick", &rng_ick),
+ CLK("omap3-rom-rng", "ick", &rng_ick),
CLK(NULL, "sha11_ick", &sha11_ick),
CLK(NULL, "des1_ick", &des1_ick),
CLK(NULL, "cam_mclk", &cam_mclk),
--
1.7.10.4

2013-09-20 16:23:58

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

* Pali Rohár <[email protected]> [130920 06:33]:
> Name omap_rng is already used by omap_rng driver which is for omap2 and omap4.
> For omap3 HS devices there is new driver omap3-rom-rng which needs that clk.
> And because there cannot be two drivers with same name, rename omap3 clk dev id.
>
> Signed-off-by: Pali Rohár <[email protected]>
> ---
> arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
> index 334b767..5059338 100644
> --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> @@ -3274,7 +3274,7 @@ static struct omap_clk omap36xx_clks[] = {
> */
> static struct omap_clk omap34xx_omap36xx_clks[] = {
> CLK(NULL, "aes1_ick", &aes1_ick),
> - CLK("omap_rng", "ick", &rng_ick),
> + CLK("omap3-rom-rng", "ick", &rng_ick),
> CLK(NULL, "sha11_ick", &sha11_ick),
> CLK(NULL, "des1_ick", &des1_ick),
> CLK(NULL, "cam_mclk", &cam_mclk),

Hmm are you sure the omap_rng is not available on
any of the omap3 GP versions? If so, the omap_rng
alias should be kept as well.

Regards,

Tony

2013-09-20 16:41:22

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

On Friday 20 September 2013 18:23:43 Tony Lindgren wrote:
> * Pali Rohár <[email protected]> [130920 06:33]:
> > Name omap_rng is already used by omap_rng driver which is
> > for omap2 and omap4. For omap3 HS devices there is new
> > driver omap3-rom-rng which needs that clk. And because
> > there cannot be two drivers with same name, rename omap3
> > clk dev id.
> >
> > Signed-off-by: Pali Rohár <[email protected]>
> > ---
> >
> > arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
> > 1 file changed, 1 insertion(+), 1 deletion(-)
> >
> > diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c
> > b/arch/arm/mach-omap2/cclock3xxx_data.c index
> > 334b767..5059338 100644
> > --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> > +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> > @@ -3274,7 +3274,7 @@ static struct omap_clk omap36xx_clks[]
> > = {
> >
> > */
> >
> > static struct omap_clk omap34xx_omap36xx_clks[] = {
> >
> > CLK(NULL, "aes1_ick", &aes1_ick),
> >
> > - CLK("omap_rng", "ick", &rng_ick),
> > + CLK("omap3-rom-rng", "ick", &rng_ick),
> >
> > CLK(NULL, "sha11_ick", &sha11_ick),
> > CLK(NULL, "des1_ick", &des1_ick),
> > CLK(NULL, "cam_mclk", &cam_mclk),
>
> Hmm are you sure the omap_rng is not available on
> any of the omap3 GP versions? If so, the omap_rng
> alias should be kept as well.
>
> Regards,
>
> Tony

I really do not know, but driver char/hw_random/omap-rng.c
support only omap2 and omap4 platforms. So "omap_rng" dev id for
omap3 is not used.

In email [1] you suggested to use clk_get instead clk_get_sys. If
I understand correctly clk_get calling clk_get_sys with driver
name. So dev in in CLK macro must be same as driver name. And
because in cclock3xxx_data.c is dev id "omap_rng" and there is
already driver with name "omap_rng", I need to rename dev in
cclock3xxx_data.c to get new omap3-rom-rng driver working.

Or if you know better way how to do it, let me know.

[1] - https://lkml.org/lkml/2013/4/1/278

--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-09-20 17:46:52

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

* Pali Rohár <[email protected]> [130920 09:49]:
> On Friday 20 September 2013 18:23:43 Tony Lindgren wrote:
> > * Pali Rohár <[email protected]> [130920 06:33]:
> > > Name omap_rng is already used by omap_rng driver which is
> > > for omap2 and omap4. For omap3 HS devices there is new
> > > driver omap3-rom-rng which needs that clk. And because
> > > there cannot be two drivers with same name, rename omap3
> > > clk dev id.
> > >
> > > Signed-off-by: Pali Rohár <[email protected]>
> > > ---
> > >
> > > arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
> > > 1 file changed, 1 insertion(+), 1 deletion(-)
> > >
> > > diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c
> > > b/arch/arm/mach-omap2/cclock3xxx_data.c index
> > > 334b767..5059338 100644
> > > --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> > > +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> > > @@ -3274,7 +3274,7 @@ static struct omap_clk omap36xx_clks[]
> > > = {
> > >
> > > */
> > >
> > > static struct omap_clk omap34xx_omap36xx_clks[] = {
> > >
> > > CLK(NULL, "aes1_ick", &aes1_ick),
> > >
> > > - CLK("omap_rng", "ick", &rng_ick),
> > > + CLK("omap3-rom-rng", "ick", &rng_ick),
> > >
> > > CLK(NULL, "sha11_ick", &sha11_ick),
> > > CLK(NULL, "des1_ick", &des1_ick),
> > > CLK(NULL, "cam_mclk", &cam_mclk),
> >
> > Hmm are you sure the omap_rng is not available on
> > any of the omap3 GP versions? If so, the omap_rng
> > alias should be kept as well.
> >
> > Regards,
> >
> > Tony
>
> I really do not know, but driver char/hw_random/omap-rng.c
> support only omap2 and omap4 platforms. So "omap_rng" dev id for
> omap3 is not used.
>
> In email [1] you suggested to use clk_get instead clk_get_sys. If
> I understand correctly clk_get calling clk_get_sys with driver
> name. So dev in in CLK macro must be same as driver name. And
> because in cclock3xxx_data.c is dev id "omap_rng" and there is
> already driver with name "omap_rng", I need to rename dev in
> cclock3xxx_data.c to get new omap3-rom-rng driver working.
>
> Or if you know better way how to do it, let me know.

I think it's safest to keep the existing alias also, and
add a comment saying that it may not be available on omap3
processors.

Regards,

Tony

> [1] - https://lkml.org/lkml/2013/4/1/278
>
> --
> Pali Rohár
> [email protected]

2013-09-20 18:24:57

by Pali Rohár

[permalink] [raw]
Subject: Re: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

On Friday 20 September 2013 19:46:41 Tony Lindgren wrote:
> * Pali Rohár <[email protected]> [130920 09:49]:
> > On Friday 20 September 2013 18:23:43 Tony Lindgren wrote:
> > > * Pali Rohár <[email protected]> [130920 06:33]:
> > > > Name omap_rng is already used by omap_rng driver which
> > > > is for omap2 and omap4. For omap3 HS devices there is
> > > > new driver omap3-rom-rng which needs that clk. And
> > > > because there cannot be two drivers with same name,
> > > > rename omap3 clk dev id.
> > > >
> > > > Signed-off-by: Pali Rohár <[email protected]>
> > > > ---
> > > >
> > > > arch/arm/mach-omap2/cclock3xxx_data.c | 2 +-
> > > > 1 file changed, 1 insertion(+), 1 deletion(-)
> > > >
> > > > diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c
> > > > b/arch/arm/mach-omap2/cclock3xxx_data.c index
> > > > 334b767..5059338 100644
> > > > --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> > > > +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> > > > @@ -3274,7 +3274,7 @@ static struct omap_clk
> > > > omap36xx_clks[] = {
> > > >
> > > > */
> > > >
> > > > static struct omap_clk omap34xx_omap36xx_clks[] = {
> > > >
> > > > CLK(NULL, "aes1_ick", &aes1_ick),
> > > >
> > > > - CLK("omap_rng", "ick", &rng_ick),
> > > > + CLK("omap3-rom-rng", "ick", &rng_ick),
> > > >
> > > > CLK(NULL, "sha11_ick", &sha11_ick),
> > > > CLK(NULL, "des1_ick", &des1_ick),
> > > > CLK(NULL, "cam_mclk", &cam_mclk),
> > >
> > > Hmm are you sure the omap_rng is not available on
> > > any of the omap3 GP versions? If so, the omap_rng
> > > alias should be kept as well.
> > >
> > > Regards,
> > >
> > > Tony
> >
> > I really do not know, but driver char/hw_random/omap-rng.c
> > support only omap2 and omap4 platforms. So "omap_rng" dev id
> > for omap3 is not used.
> >
> > In email [1] you suggested to use clk_get instead
> > clk_get_sys. If I understand correctly clk_get calling
> > clk_get_sys with driver name. So dev in in CLK macro must
> > be same as driver name. And because in cclock3xxx_data.c is
> > dev id "omap_rng" and there is already driver with name
> > "omap_rng", I need to rename dev in cclock3xxx_data.c to
> > get new omap3-rom-rng driver working.
> >
> > Or if you know better way how to do it, let me know.
>
> I think it's safest to keep the existing alias also, and
> add a comment saying that it may not be available on omap3
> processors.
>
> Regards,
>
> Tony
>
> > [1] - https://lkml.org/lkml/2013/4/1/278

Ok, then there is new patch which only adding omap3-rom-rng and not removing omap_rng.
It is OK to have same CLK data but with different names?

diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
index 334b767..03a2829 100644
--- a/arch/arm/mach-omap2/cclock3xxx_data.c
+++ b/arch/arm/mach-omap2/cclock3xxx_data.c
@@ -3275,6 +3275,7 @@ static struct omap_clk omap36xx_clks[] = {
static struct omap_clk omap34xx_omap36xx_clks[] = {
CLK(NULL, "aes1_ick", &aes1_ick),
CLK("omap_rng", "ick", &rng_ick),
+ CLK("omap3-rom-rng", "ick", &rng_ick),
CLK(NULL, "sha11_ick", &sha11_ick),
CLK(NULL, "des1_ick", &des1_ick),
CLK(NULL, "cam_mclk", &cam_mclk),


--
Pali Rohár
[email protected]


Attachments:
signature.asc (198.00 B)
This is a digitally signed message part.

2013-09-20 18:31:57

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH v2 1/3] omap2: Change clk dev id for rng to omap3-rom-rng

* Pali Rohár <[email protected]> [130920 11:32]:
> On Friday 20 September 2013 19:46:41 Tony Lindgren wrote:
>
> Ok, then there is new patch which only adding omap3-rom-rng and not removing omap_rng.
> It is OK to have same CLK data but with different names?

Yes in this case it's always either omap_rng or omap3-rom-rng
so the patch below looks OK to me.

Regards,

Tony

> diff --git a/arch/arm/mach-omap2/cclock3xxx_data.c b/arch/arm/mach-omap2/cclock3xxx_data.c
> index 334b767..03a2829 100644
> --- a/arch/arm/mach-omap2/cclock3xxx_data.c
> +++ b/arch/arm/mach-omap2/cclock3xxx_data.c
> @@ -3275,6 +3275,7 @@ static struct omap_clk omap36xx_clks[] = {
> static struct omap_clk omap34xx_omap36xx_clks[] = {
> CLK(NULL, "aes1_ick", &aes1_ick),
> CLK("omap_rng", "ick", &rng_ick),
> + CLK("omap3-rom-rng", "ick", &rng_ick),
> CLK(NULL, "sha11_ick", &sha11_ick),
> CLK(NULL, "des1_ick", &des1_ick),
> CLK(NULL, "cam_mclk", &cam_mclk),
>
>
> --
> Pali Rohár
> [email protected]

2013-10-08 19:04:22

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH v2 2/3] hwrng: OMAP3 ROM Random Number Generator support

* Pali Rohár <[email protected]> [130920 06:33]:
> This driver provides kernel-side support for the Random Number
> Generator hardware found on OMAP34xx processors.
>
> This driver comes from Maemo 2.6.28 kernel and was tested on Nokia RX-51.
> It is platform device because it needs board specific function for smc calls.

This one is should be merged via the hw_random patches seprately:

Acked-by: Tony Lindgren <[email protected]>

> Signed-off-by: Pali Rohár <[email protected]>
> Signed-off-by: Juha Yrjola <[email protected]>
> ---
> drivers/char/hw_random/Kconfig | 13 +++
> drivers/char/hw_random/Makefile | 1 +
> drivers/char/hw_random/omap3-rom-rng.c | 141 ++++++++++++++++++++++++++++++++
> 3 files changed, 155 insertions(+)
> create mode 100644 drivers/char/hw_random/omap3-rom-rng.c
>
> diff --git a/drivers/char/hw_random/Kconfig b/drivers/char/hw_random/Kconfig
> index 0aa9d91..0a331c3 100644
> --- a/drivers/char/hw_random/Kconfig
> +++ b/drivers/char/hw_random/Kconfig
> @@ -165,6 +165,19 @@ config HW_RANDOM_OMAP
>
> If unsure, say Y.
>
> +config HW_RANDOM_OMAP3_ROM
> + tristate "OMAP3 ROM Random Number Generator support"
> + depends on HW_RANDOM && ARCH_OMAP3
> + default HW_RANDOM
> + ---help---
> + This driver provides kernel-side support for the Random Number
> + Generator hardware found on OMAP34xx processors.
> +
> + To compile this driver as a module, choose M here: the
> + module will be called omap3-rom-rng.
> +
> + If unsure, say Y.
> +
> config HW_RANDOM_OCTEON
> tristate "Octeon Random Number Generator support"
> depends on HW_RANDOM && CAVIUM_OCTEON_SOC
> diff --git a/drivers/char/hw_random/Makefile b/drivers/char/hw_random/Makefile
> index bed467c..7c8aa80 100644
> --- a/drivers/char/hw_random/Makefile
> +++ b/drivers/char/hw_random/Makefile
> @@ -15,6 +15,7 @@ n2-rng-y := n2-drv.o n2-asm.o
> obj-$(CONFIG_HW_RANDOM_VIA) += via-rng.o
> obj-$(CONFIG_HW_RANDOM_IXP4XX) += ixp4xx-rng.o
> obj-$(CONFIG_HW_RANDOM_OMAP) += omap-rng.o
> +obj-$(CONFIG_HW_RANDOM_OMAP3_ROM) += omap3-rom-rng.o
> obj-$(CONFIG_HW_RANDOM_PASEMI) += pasemi-rng.o
> obj-$(CONFIG_HW_RANDOM_VIRTIO) += virtio-rng.o
> obj-$(CONFIG_HW_RANDOM_TX4939) += tx4939-rng.o
> diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c
> new file mode 100644
> index 0000000..c853e9e
> --- /dev/null
> +++ b/drivers/char/hw_random/omap3-rom-rng.c
> @@ -0,0 +1,141 @@
> +/*
> + * omap3-rom-rng.c - RNG driver for TI OMAP3 CPU family
> + *
> + * Copyright (C) 2009 Nokia Corporation
> + * Author: Juha Yrjola <[email protected]>
> + *
> + * Copyright (C) 2013 Pali Rohár <[email protected]>
> + *
> + * This file is licensed under the terms of the GNU General Public
> + * License version 2. This program is licensed "as is" without any
> + * warranty of any kind, whether express or implied.
> + */
> +
> +#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
> +
> +#include <linux/module.h>
> +#include <linux/init.h>
> +#include <linux/random.h>
> +#include <linux/hw_random.h>
> +#include <linux/timer.h>
> +#include <linux/clk.h>
> +#include <linux/err.h>
> +#include <linux/platform_device.h>
> +
> +#define RNG_RESET 0x01
> +#define RNG_GEN_PRNG_HW_INIT 0x02
> +#define RNG_GEN_HW 0x08
> +
> +/* param1: ptr, param2: count, param3: flag */
> +static u32 (*omap3_rom_rng_call)(u32, u32, u32);
> +
> +static struct timer_list idle_timer;
> +static int rng_idle;
> +static struct clk *rng_clk;
> +
> +static void omap3_rom_rng_idle(unsigned long data)
> +{
> + int r;
> +
> + r = omap3_rom_rng_call(0, 0, RNG_RESET);
> + if (r != 0) {
> + pr_err("reset failed: %d\n", r);
> + return;
> + }
> + clk_disable_unprepare(rng_clk);
> + rng_idle = 1;
> +}
> +
> +static int omap3_rom_rng_get_random(void *buf, unsigned int count)
> +{
> + u32 r;
> + u32 ptr;
> +
> + del_timer_sync(&idle_timer);
> + if (rng_idle) {
> + clk_prepare_enable(rng_clk);
> + r = omap3_rom_rng_call(0, 0, RNG_GEN_PRNG_HW_INIT);
> + if (r != 0) {
> + clk_disable_unprepare(rng_clk);
> + pr_err("HW init failed: %d\n", r);
> + return -EIO;
> + }
> + rng_idle = 0;
> + }
> +
> + ptr = virt_to_phys(buf);
> + r = omap3_rom_rng_call(ptr, count, RNG_GEN_HW);
> + mod_timer(&idle_timer, jiffies + msecs_to_jiffies(500));
> + if (r != 0)
> + return -EINVAL;
> + return 0;
> +}
> +
> +static int omap3_rom_rng_data_present(struct hwrng *rng, int wait)
> +{
> + return 1;
> +}
> +
> +static int omap3_rom_rng_data_read(struct hwrng *rng, u32 *data)
> +{
> + int r;
> +
> + r = omap3_rom_rng_get_random(data, 4);
> + if (r < 0)
> + return r;
> + return 4;
> +}
> +
> +static struct hwrng omap3_rom_rng_ops = {
> + .name = "omap3-rom",
> + .data_present = omap3_rom_rng_data_present,
> + .data_read = omap3_rom_rng_data_read,
> +};
> +
> +static int omap3_rom_rng_probe(struct platform_device *pdev)
> +{
> + pr_info("initializing\n");
> +
> + omap3_rom_rng_call = pdev->dev.platform_data;
> + if (!omap3_rom_rng_call) {
> + pr_err("omap3_rom_rng_call is NULL\n");
> + return -EINVAL;
> + }
> +
> + setup_timer(&idle_timer, omap3_rom_rng_idle, 0);
> + rng_clk = clk_get(&pdev->dev, "ick");
> + if (IS_ERR(rng_clk)) {
> + pr_err("unable to get RNG clock\n");
> + return PTR_ERR(rng_clk);
> + }
> +
> + /* Leave the RNG in reset state. */
> + clk_prepare_enable(rng_clk);
> + omap3_rom_rng_idle(0);
> +
> + return hwrng_register(&omap3_rom_rng_ops);
> +}
> +
> +static int omap3_rom_rng_remove(struct platform_device *pdev)
> +{
> + hwrng_unregister(&omap3_rom_rng_ops);
> + clk_disable_unprepare(rng_clk);
> + clk_put(rng_clk);
> + return 0;
> +}
> +
> +static struct platform_driver omap3_rom_rng_driver = {
> + .driver = {
> + .name = "omap3-rom-rng",
> + .owner = THIS_MODULE,
> + },
> + .probe = omap3_rom_rng_probe,
> + .remove = omap3_rom_rng_remove,
> +};
> +
> +module_platform_driver(omap3_rom_rng_driver);
> +
> +MODULE_ALIAS("platform:omap3-rom-rng");
> +MODULE_AUTHOR("Juha Yrjola");
> +MODULE_AUTHOR("Pali Rohár <[email protected]>");
> +MODULE_LICENSE("GPL");
> --
> 1.7.10.4
>

2013-10-08 19:06:57

by Tony Lindgren

[permalink] [raw]
Subject: Re: [PATCH v2 3/3] RX-51: Add support for OMAP3 ROM Random Number Generator

* Pali Rohár <[email protected]> [130920 06:33]:
> Adding this driver as platform device and only for RX-51 until somebody test if
> it working also on other OMAP3 HS devices and until there will be generic ARM
> way to deal with SMC calls.

Thanks I'll apply this with the patch #1 clock alias folded in into
omap-for-v3.13/n900 branch.

Regards,

Tony

2013-10-16 12:58:02

by Herbert Xu

[permalink] [raw]
Subject: Re: [PATCH v2 2/3] hwrng: OMAP3 ROM Random Number Generator support

On Tue, Oct 08, 2013 at 12:04:09PM -0700, Tony Lindgren wrote:
> * Pali Roh?r <[email protected]> [130920 06:33]:
> > This driver provides kernel-side support for the Random Number
> > Generator hardware found on OMAP34xx processors.
> >
> > This driver comes from Maemo 2.6.28 kernel and was tested on Nokia RX-51.
> > It is platform device because it needs board specific function for smc calls.
>
> This one is should be merged via the hw_random patches seprately:
>
> Acked-by: Tony Lindgren <[email protected]>

Patch applied. Thanks!
--
Email: Herbert Xu <[email protected]>
Home Page: http://gondor.apana.org.au/~herbert/
PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt