From d167b6e1fb8ad386b17485ca88804d14f1695805 Mon Sep 17 00:00:00 2001 From: Dan Carpenter Date: Thu, 30 Jan 2014 14:49:43 +0300 Subject: hwrng: cleanup in hwrng_register() My static checker complains that: drivers/char/hw_random/core.c:341 hwrng_register() warn: we tested 'old_rng' before and it was 'false' The problem is that sometimes we test "if (!old_rng)" and sometimes we test "if (must_register_misc)". The static checker knows they are equivalent but a human being reading the code could easily be confused. I have simplified the code by removing the "must_register_misc" variable and I have removed the redundant check on "if (!old_rng)". Signed-off-by: Dan Carpenter Reviewed-by: Rusty Russell Signed-off-by: Herbert Xu --- drivers/char/hw_random/core.c | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/core.c b/drivers/char/hw_random/core.c index a0f7724852e..cf49f1c88f0 100644 --- a/drivers/char/hw_random/core.c +++ b/drivers/char/hw_random/core.c @@ -302,7 +302,6 @@ err_misc_dereg: int hwrng_register(struct hwrng *rng) { - int must_register_misc; int err = -EINVAL; struct hwrng *old_rng, *tmp; @@ -327,7 +326,6 @@ int hwrng_register(struct hwrng *rng) goto out_unlock; } - must_register_misc = (current_rng == NULL); old_rng = current_rng; if (!old_rng) { err = hwrng_init(rng); @@ -336,13 +334,11 @@ int hwrng_register(struct hwrng *rng) current_rng = rng; } err = 0; - if (must_register_misc) { + if (!old_rng) { err = register_miscdev(); if (err) { - if (!old_rng) { - hwrng_cleanup(rng); - current_rng = NULL; - } + hwrng_cleanup(rng); + current_rng = NULL; goto out_unlock; } } -- cgit v1.2.3-70-g09d2 From 2257ffbca73c72f3de1ba20c500f4c9fd333014b Mon Sep 17 00:00:00 2001 From: Kumar Gala Date: Thu, 30 Jan 2014 14:43:49 -0600 Subject: hwrng: msm: switch Kconfig to ARCH_QCOM depends We've split Qualcomm MSM support into legacy and multiplatform. The RNG driver is only relevant on the multiplatform supported SoCs so switch the Kconfig depends to ARCH_QCOM. Acked-by: Herbert Xu CC: Stanimir Varbanov Signed-off-by: Kumar Gala --- drivers/char/hw_random/Kconfig | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/Kconfig b/drivers/char/hw_random/Kconfig index 2f2b08457c6..244759bbd7b 100644 --- a/drivers/char/hw_random/Kconfig +++ b/drivers/char/hw_random/Kconfig @@ -342,11 +342,11 @@ config HW_RANDOM_TPM If unsure, say Y. config HW_RANDOM_MSM - tristate "Qualcomm MSM Random Number Generator support" - depends on HW_RANDOM && ARCH_MSM + tristate "Qualcomm SoCs Random Number Generator support" + depends on HW_RANDOM && ARCH_QCOM ---help--- This driver provides kernel-side support for the Random Number - Generator hardware found on Qualcomm MSM SoCs. + Generator hardware found on Qualcomm SoCs. To compile this driver as a module, choose M here. the module will be called msm-rng. -- cgit v1.2.3-70-g09d2 From bfaff75b09c42d8fc57b020034e836fe9048f8b1 Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Wed, 12 Feb 2014 14:17:08 +0900 Subject: hwrng: atmel - Use devm_ioremap_resource() Use devm_ioremap_resource() in order to make the code simpler, and remove redundant return value check of platform_get_resource() because the value is checked by devm_ioremap_resource(). Signed-off-by: Jingoo Han Acked-by: Peter Korsgaard Acked-by: Nicolas Ferre Signed-off-by: Herbert Xu --- drivers/char/hw_random/atmel-rng.c | 15 ++++----------- 1 file changed, 4 insertions(+), 11 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/atmel-rng.c b/drivers/char/hw_random/atmel-rng.c index bf9fc6b7932..dfeddf2c00b 100644 --- a/drivers/char/hw_random/atmel-rng.c +++ b/drivers/char/hw_random/atmel-rng.c @@ -54,21 +54,14 @@ static int atmel_trng_probe(struct platform_device *pdev) struct resource *res; int ret; - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!res) - return -EINVAL; - trng = devm_kzalloc(&pdev->dev, sizeof(*trng), GFP_KERNEL); if (!trng) return -ENOMEM; - if (!devm_request_mem_region(&pdev->dev, res->start, - resource_size(res), pdev->name)) - return -EBUSY; - - trng->base = devm_ioremap(&pdev->dev, res->start, resource_size(res)); - if (!trng->base) - return -EBUSY; + res = platform_get_resource(pdev, IORESOURCE_MEM, 0); + trng->base = devm_ioremap_resource(&pdev->dev, res); + if (IS_ERR(trng->base)) + return PTR_ERR(trng->base); trng->clk = clk_get(&pdev->dev, NULL); if (IS_ERR(trng->clk)) -- cgit v1.2.3-70-g09d2 From fb5d23e3e09d6c9719b783ac1955c085aca3d4ae Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Wed, 12 Feb 2014 14:19:48 +0900 Subject: hwrng: pixocell - Use devm_ioremap_resource() Use devm_ioremap_resource() in order to make the code simpler, and remove redundant return value check of platform_get_resource() because the value is checked by devm_ioremap_resource(). Signed-off-by: Jingoo Han Signed-off-by: Herbert Xu --- drivers/char/hw_random/picoxcell-rng.c | 19 +++---------------- 1 file changed, 3 insertions(+), 16 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/picoxcell-rng.c b/drivers/char/hw_random/picoxcell-rng.c index 3d4c2293c6f..c03beeeb1ae 100644 --- a/drivers/char/hw_random/picoxcell-rng.c +++ b/drivers/char/hw_random/picoxcell-rng.c @@ -104,22 +104,9 @@ static int picoxcell_trng_probe(struct platform_device *pdev) int ret; struct resource *mem = platform_get_resource(pdev, IORESOURCE_MEM, 0); - if (!mem) { - dev_warn(&pdev->dev, "no memory resource\n"); - return -ENOMEM; - } - - if (!devm_request_mem_region(&pdev->dev, mem->start, resource_size(mem), - "picoxcell_trng")) { - dev_warn(&pdev->dev, "unable to request io mem\n"); - return -EBUSY; - } - - rng_base = devm_ioremap(&pdev->dev, mem->start, resource_size(mem)); - if (!rng_base) { - dev_warn(&pdev->dev, "unable to remap io mem\n"); - return -ENOMEM; - } + rng_base = devm_ioremap_resource(&pdev->dev, mem); + if (IS_ERR(rng_base)) + return PTR_ERR(rng_base); rng_clk = clk_get(&pdev->dev, NULL); if (IS_ERR(rng_clk)) { -- cgit v1.2.3-70-g09d2 From 0c0becd0269240cd832b7aac16fb9b48d067520e Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Thu, 27 Feb 2014 14:00:09 +0900 Subject: hwrng: atmel - Use devm_clk_get() Use devm_clk_get() to make cleanup paths simpler. Signed-off-by: Jingoo Han Acked-by: Peter Korsgaard Acked-by: Nicolas Ferre Signed-off-by: Herbert Xu --- drivers/char/hw_random/atmel-rng.c | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/atmel-rng.c b/drivers/char/hw_random/atmel-rng.c index dfeddf2c00b..851bc7e20ad 100644 --- a/drivers/char/hw_random/atmel-rng.c +++ b/drivers/char/hw_random/atmel-rng.c @@ -63,13 +63,13 @@ static int atmel_trng_probe(struct platform_device *pdev) if (IS_ERR(trng->base)) return PTR_ERR(trng->base); - trng->clk = clk_get(&pdev->dev, NULL); + trng->clk = devm_clk_get(&pdev->dev, NULL); if (IS_ERR(trng->clk)) return PTR_ERR(trng->clk); ret = clk_enable(trng->clk); if (ret) - goto err_enable; + return ret; writel(TRNG_KEY | 1, trng->base + TRNG_CR); trng->rng.name = pdev->name; @@ -85,9 +85,6 @@ static int atmel_trng_probe(struct platform_device *pdev) err_register: clk_disable(trng->clk); -err_enable: - clk_put(trng->clk); - return ret; } @@ -99,7 +96,6 @@ static int atmel_trng_remove(struct platform_device *pdev) writel(TRNG_KEY, trng->base + TRNG_CR); clk_disable(trng->clk); - clk_put(trng->clk); return 0; } -- cgit v1.2.3-70-g09d2 From 0574bce9691f238f3351b28c27de337d4519d595 Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Thu, 27 Feb 2014 14:02:24 +0900 Subject: hwrng: omap3-rom - Use devm_clk_get() Use devm_clk_get() to make cleanup paths simpler. Signed-off-by: Jingoo Han Signed-off-by: Herbert Xu --- drivers/char/hw_random/omap3-rom-rng.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/omap3-rom-rng.c b/drivers/char/hw_random/omap3-rom-rng.c index c853e9e6857..6f2eaffed62 100644 --- a/drivers/char/hw_random/omap3-rom-rng.c +++ b/drivers/char/hw_random/omap3-rom-rng.c @@ -103,7 +103,7 @@ static int omap3_rom_rng_probe(struct platform_device *pdev) } setup_timer(&idle_timer, omap3_rom_rng_idle, 0); - rng_clk = clk_get(&pdev->dev, "ick"); + rng_clk = devm_clk_get(&pdev->dev, "ick"); if (IS_ERR(rng_clk)) { pr_err("unable to get RNG clock\n"); return PTR_ERR(rng_clk); @@ -120,7 +120,6 @@ 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; } -- cgit v1.2.3-70-g09d2 From 0c0aa8446433849f19761ebb7cd2f58fde387a04 Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Thu, 27 Feb 2014 14:04:28 +0900 Subject: hwrng: pixocell - Use devm_clk_get() Use devm_clk_get() to make cleanup paths simpler. Signed-off-by: Jingoo Han Signed-off-by: Herbert Xu --- drivers/char/hw_random/picoxcell-rng.c | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/picoxcell-rng.c b/drivers/char/hw_random/picoxcell-rng.c index c03beeeb1ae..eab5448ad56 100644 --- a/drivers/char/hw_random/picoxcell-rng.c +++ b/drivers/char/hw_random/picoxcell-rng.c @@ -108,7 +108,7 @@ static int picoxcell_trng_probe(struct platform_device *pdev) if (IS_ERR(rng_base)) return PTR_ERR(rng_base); - rng_clk = clk_get(&pdev->dev, NULL); + rng_clk = devm_clk_get(&pdev->dev, NULL); if (IS_ERR(rng_clk)) { dev_warn(&pdev->dev, "no clk\n"); return PTR_ERR(rng_clk); @@ -117,7 +117,7 @@ static int picoxcell_trng_probe(struct platform_device *pdev) ret = clk_enable(rng_clk); if (ret) { dev_warn(&pdev->dev, "unable to enable clk\n"); - goto err_enable; + return ret; } picoxcell_trng_start(); @@ -132,9 +132,6 @@ static int picoxcell_trng_probe(struct platform_device *pdev) err_register: clk_disable(rng_clk); -err_enable: - clk_put(rng_clk); - return ret; } @@ -142,7 +139,6 @@ static int picoxcell_trng_remove(struct platform_device *pdev) { hwrng_unregister(&picoxcell_trng); clk_disable(rng_clk); - clk_put(rng_clk); return 0; } -- cgit v1.2.3-70-g09d2 From 1655c24095da0b13bbd7a80b25948b19f6efdb37 Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Thu, 27 Feb 2014 14:06:31 +0900 Subject: hwrng: nomadik - Use devm_*() functions Use devm_*() functions to make cleanup paths simpler. Signed-off-by: Jingoo Han Reviewed-by: Linus Walleij Signed-off-by: Herbert Xu --- drivers/char/hw_random/nomadik-rng.c | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/nomadik-rng.c b/drivers/char/hw_random/nomadik-rng.c index 232b87fb5fc..bc904bb3f8a 100644 --- a/drivers/char/hw_random/nomadik-rng.c +++ b/drivers/char/hw_random/nomadik-rng.c @@ -44,7 +44,7 @@ static int nmk_rng_probe(struct amba_device *dev, const struct amba_id *id) void __iomem *base; int ret; - rng_clk = clk_get(&dev->dev, NULL); + rng_clk = devm_clk_get(&dev->dev, NULL); if (IS_ERR(rng_clk)) { dev_err(&dev->dev, "could not get rng clock\n"); ret = PTR_ERR(rng_clk); @@ -57,33 +57,28 @@ static int nmk_rng_probe(struct amba_device *dev, const struct amba_id *id) if (ret) goto out_clk; ret = -ENOMEM; - base = ioremap(dev->res.start, resource_size(&dev->res)); + base = devm_ioremap(&dev->dev, dev->res.start, + resource_size(&dev->res)); if (!base) goto out_release; nmk_rng.priv = (unsigned long)base; ret = hwrng_register(&nmk_rng); if (ret) - goto out_unmap; + goto out_release; return 0; -out_unmap: - iounmap(base); out_release: amba_release_regions(dev); out_clk: clk_disable(rng_clk); - clk_put(rng_clk); return ret; } static int nmk_rng_remove(struct amba_device *dev) { - void __iomem *base = (void __iomem *)nmk_rng.priv; hwrng_unregister(&nmk_rng); - iounmap(base); amba_release_regions(dev); clk_disable(rng_clk); - clk_put(rng_clk); return 0; } -- cgit v1.2.3-70-g09d2 From 93b7f9c92840102da43aafc41dd943926826269e Mon Sep 17 00:00:00 2001 From: Jingoo Han Date: Thu, 27 Feb 2014 14:07:52 +0900 Subject: hwrng: timeriomem - Use devm_*() functions Use devm_*() functions to make cleanup paths simpler. Signed-off-by: Jingoo Han Signed-off-by: Herbert Xu --- drivers/char/hw_random/timeriomem-rng.c | 40 +++++++++------------------------ 1 file changed, 10 insertions(+), 30 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/timeriomem-rng.c b/drivers/char/hw_random/timeriomem-rng.c index 73ce739f8e1..439ff8b28c4 100644 --- a/drivers/char/hw_random/timeriomem-rng.c +++ b/drivers/char/hw_random/timeriomem-rng.c @@ -118,7 +118,8 @@ static int timeriomem_rng_probe(struct platform_device *pdev) } /* Allocate memory for the device structure (and zero it) */ - priv = kzalloc(sizeof(struct timeriomem_rng_private_data), GFP_KERNEL); + priv = devm_kzalloc(&pdev->dev, + sizeof(struct timeriomem_rng_private_data), GFP_KERNEL); if (!priv) { dev_err(&pdev->dev, "failed to allocate device structure.\n"); return -ENOMEM; @@ -134,17 +135,16 @@ static int timeriomem_rng_probe(struct platform_device *pdev) period = i; else { dev_err(&pdev->dev, "missing period\n"); - err = -EINVAL; - goto out_free; + return -EINVAL; } - } else + } else { period = pdata->period; + } priv->period = usecs_to_jiffies(period); if (priv->period < 1) { dev_err(&pdev->dev, "period is less than one jiffy\n"); - err = -EINVAL; - goto out_free; + return -EINVAL; } priv->expires = jiffies; @@ -160,24 +160,16 @@ static int timeriomem_rng_probe(struct platform_device *pdev) priv->timeriomem_rng_ops.data_read = timeriomem_rng_data_read; priv->timeriomem_rng_ops.priv = (unsigned long)priv; - if (!request_mem_region(res->start, resource_size(res), - dev_name(&pdev->dev))) { - dev_err(&pdev->dev, "request_mem_region failed\n"); - err = -EBUSY; + priv->io_base = devm_ioremap_resource(&pdev->dev, res); + if (IS_ERR(priv->io_base)) { + err = PTR_ERR(priv->io_base); goto out_timer; } - priv->io_base = ioremap(res->start, resource_size(res)); - if (priv->io_base == NULL) { - dev_err(&pdev->dev, "ioremap failed\n"); - err = -EIO; - goto out_release_io; - } - err = hwrng_register(&priv->timeriomem_rng_ops); if (err) { dev_err(&pdev->dev, "problem registering\n"); - goto out; + goto out_timer; } dev_info(&pdev->dev, "32bits from 0x%p @ %dus\n", @@ -185,30 +177,18 @@ static int timeriomem_rng_probe(struct platform_device *pdev) return 0; -out: - iounmap(priv->io_base); -out_release_io: - release_mem_region(res->start, resource_size(res)); out_timer: del_timer_sync(&priv->timer); -out_free: - kfree(priv); return err; } static int timeriomem_rng_remove(struct platform_device *pdev) { struct timeriomem_rng_private_data *priv = platform_get_drvdata(pdev); - struct resource *res; - - res = platform_get_resource(pdev, IORESOURCE_MEM, 0); hwrng_unregister(&priv->timeriomem_rng_ops); del_timer_sync(&priv->timer); - iounmap(priv->io_base); - release_mem_region(res->start, resource_size(res)); - kfree(priv); return 0; } -- cgit v1.2.3-70-g09d2 From d9e79726193346569af7953369a638ee2275ade5 Mon Sep 17 00:00:00 2001 From: Kees Cook Date: Mon, 3 Mar 2014 15:51:48 -0800 Subject: hwrng: add randomness to system from rng sources When bringing a new RNG source online, it seems like it would make sense to use some of its bytes to make the system entropy pool more random, as done with all sorts of other devices that contain per-device or per-boot differences. Signed-off-by: Kees Cook Reviewed-by: Jason Cooper Signed-off-by: Herbert Xu --- drivers/char/hw_random/core.c | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/core.c b/drivers/char/hw_random/core.c index cf49f1c88f0..7ac96fbc06e 100644 --- a/drivers/char/hw_random/core.c +++ b/drivers/char/hw_random/core.c @@ -41,6 +41,7 @@ #include #include #include +#include #include @@ -304,6 +305,8 @@ int hwrng_register(struct hwrng *rng) { int err = -EINVAL; struct hwrng *old_rng, *tmp; + unsigned char bytes[16]; + int bytes_read; if (rng->name == NULL || (rng->data_read == NULL && rng->read == NULL)) @@ -344,6 +347,10 @@ int hwrng_register(struct hwrng *rng) } INIT_LIST_HEAD(&rng->list); list_add_tail(&rng->list, &rng_list); + + bytes_read = rng_get_data(rng, bytes, sizeof(bytes), 1); + if (bytes_read > 0) + add_device_randomness(bytes, bytes_read); out_unlock: mutex_unlock(&rng_mutex); out: -- cgit v1.2.3-70-g09d2 From 9914a766174d50eb2343f204fef3ee23dbe07c4c Mon Sep 17 00:00:00 2001 From: Rusty Russell Date: Thu, 13 Mar 2014 11:23:40 +1030 Subject: virtio-rng: don't crash if virtqueue is broken. A bad implementation of virtio might cause us to mark the virtqueue broken: we'll dev_err() in that case, and the device is useless, but let's not BUG(). Signed-off-by: Rusty Russell --- drivers/char/hw_random/virtio-rng.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/virtio-rng.c b/drivers/char/hw_random/virtio-rng.c index c12398d1517..2ce0e225e58 100644 --- a/drivers/char/hw_random/virtio-rng.c +++ b/drivers/char/hw_random/virtio-rng.c @@ -47,8 +47,7 @@ static void register_buffer(u8 *buf, size_t size) sg_init_one(&sg, buf, size); /* There should always be room for one buffer. */ - if (virtqueue_add_inbuf(vq, &sg, 1, buf, GFP_KERNEL) < 0) - BUG(); + virtqueue_add_inbuf(vq, &sg, 1, buf, GFP_KERNEL); virtqueue_kick(vq); } -- cgit v1.2.3-70-g09d2 From dfd38750db3cc17a1da3405389a81b430720c2c6 Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 14:58:06 -0500 Subject: random: fix typos / spelling errors in comments Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 429b75bb60e..b8e44e25bc3 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -305,7 +305,7 @@ static int random_read_wakeup_thresh = 64; static int random_write_wakeup_thresh = 28 * OUTPUT_POOL_WORDS; /* - * The minimum number of seconds between urandom pool resending. We + * The minimum number of seconds between urandom pool reseeding. We * do this to limit the amount of entropy that can be drained from the * input pool even if there are heavy demands on /dev/urandom. */ @@ -322,7 +322,7 @@ static int random_min_urandom_seed = 60; * Register. (See M. Matsumoto & Y. Kurita, 1992. Twisted GFSR * generators. ACM Transactions on Modeling and Computer Simulation * 2(3):179-194. Also see M. Matsumoto & Y. Kurita, 1994. Twisted - * GFSR generators II. ACM Transactions on Mdeling and Computer + * GFSR generators II. ACM Transactions on Modeling and Computer * Simulation 4:254-266) * * Thanks to Colin Plumb for suggesting this. @@ -1036,7 +1036,7 @@ static void extract_buf(struct entropy_store *r, __u8 *out) sha_transform(hash.w, (__u8 *)(r->pool + i), workspace); /* - * If we have a architectural hardware random number + * If we have an architectural hardware random number * generator, mix that in, too. */ for (i = 0; i < LONGS(20); i++) { -- cgit v1.2.3-70-g09d2 From f22052b2025b78475a60dbe01b66b3120f4faefa Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 14:58:16 -0500 Subject: random: fix comment on proc_do_uuid There's only one function here now, as uuid_strategy is long gone. Also make the bit about "If accesses via ..." clearer. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index b8e44e25bc3..f0eea5fdc1b 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1512,13 +1512,13 @@ static int max_write_thresh = INPUT_POOL_WORDS * 32; static char sysctl_bootid[16]; /* - * These functions is used to return both the bootid UUID, and random + * This function is used to return both the bootid UUID, and random * UUID. The difference is in whether table->data is NULL; if it is, * then a new UUID is generated and returned to the user. * - * If the user accesses this via the proc interface, it will be returned - * as an ASCII string in the standard UUID format. If accesses via the - * sysctl system call, it is returned as 16 bytes of binary data. + * If the user accesses this via the proc interface, the UUID will be + * returned as an ASCII string in the standard UUID format; if via the + * sysctl system call, as 16 bytes of binary data. */ static int proc_do_uuid(struct ctl_table *table, int write, void __user *buffer, size_t *lenp, loff_t *ppos) -- cgit v1.2.3-70-g09d2 From 18e9cea74951b64282964f9625db94c5d5a007bd Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 14:59:45 -0500 Subject: random: fix description of get_random_bytes After this remark was written, commit d2e7c96af added a use of arch_get_random_long() inside the get_random_bytes codepath. The main point stands, but it needs to be reworded. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index f0eea5fdc1b..fcda7d3937e 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1170,8 +1170,9 @@ static ssize_t extract_entropy_user(struct entropy_store *r, void __user *buf, /* * This function is the exported kernel interface. It returns some * number of good random numbers, suitable for key generation, seeding - * TCP sequence numbers, etc. It does not use the hw random number - * generator, if available; use get_random_bytes_arch() for that. + * TCP sequence numbers, etc. It does not rely on the hardware random + * number generator. For random bytes direct from the hardware RNG + * (when available), use get_random_bytes_arch(). */ void get_random_bytes(void *buf, int nbytes) { -- cgit v1.2.3-70-g09d2 From 12ff3a517ab92b5496c731a3c354caa1f16c569f Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 15:02:33 -0500 Subject: random: simplify loop in random_read The loop condition never changes until just before a break, so we might as well write it as a constant. Also since a996996dd75a ("random: drop weird m_time/a_time manipulation") we don't do anything after the loop finishes, so the 'break's might as well return directly. Some other simplifications. There should be no change in behavior introduced by this commit. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 57 ++++++++++++++++----------------------------------- 1 file changed, 18 insertions(+), 39 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index fcda7d3937e..fcc2bff8f88 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1285,53 +1285,32 @@ void rand_initialize_disk(struct gendisk *disk) static ssize_t random_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) { - ssize_t n, retval = 0, count = 0; + ssize_t n; if (nbytes == 0) return 0; - while (nbytes > 0) { - n = nbytes; - if (n > SEC_XFER_SIZE) - n = SEC_XFER_SIZE; - - n = extract_entropy_user(&blocking_pool, buf, n); - - if (n < 0) { - retval = n; - break; - } - + nbytes = min_t(size_t, nbytes, SEC_XFER_SIZE); + while (1) { + n = extract_entropy_user(&blocking_pool, buf, nbytes); + if (n < 0) + return n; trace_random_read(n*8, (nbytes-n)*8, ENTROPY_BITS(&blocking_pool), ENTROPY_BITS(&input_pool)); - - if (n == 0) { - if (file->f_flags & O_NONBLOCK) { - retval = -EAGAIN; - break; - } - - wait_event_interruptible(random_read_wait, - ENTROPY_BITS(&input_pool) >= - random_read_wakeup_thresh); - - if (signal_pending(current)) { - retval = -ERESTARTSYS; - break; - } - - continue; - } - - count += n; - buf += n; - nbytes -= n; - break; /* This break makes the device work */ - /* like a named pipe */ + if (n > 0) + return n; + /* Pool is (near) empty. Maybe wait and retry. */ + + if (file->f_flags & O_NONBLOCK) + return -EAGAIN; + + wait_event_interruptible(random_read_wait, + ENTROPY_BITS(&input_pool) >= + random_read_wakeup_thresh); + if (signal_pending(current)) + return -ERESTARTSYS; } - - return (count ? count : retval); } static ssize_t -- cgit v1.2.3-70-g09d2 From 19fa5be1d92be3112521145bf99f77007abf6b16 Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 15:50:06 -0500 Subject: random: fix comment on "account" This comment didn't quite keep up as extract_entropy() was split into four functions. Put each bit by the function it describes. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 31 +++++++++++++++++++++---------- 1 file changed, 21 insertions(+), 10 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index fcc2bff8f88..2c532a6b0a2 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -958,17 +958,9 @@ static void push_to_pool(struct work_struct *work) } /* - * These functions extracts randomness from the "entropy pool", and - * returns it in a buffer. - * - * The min parameter specifies the minimum amount we can pull before - * failing to avoid races that defeat catastrophic reseeding while the - * reserved parameter indicates how much entropy we must leave in the - * pool after each pull to avoid starving other readers. - * - * Note: extract_entropy() assumes that .poolwords is a multiple of 16 words. + * This function decides how many bytes to actually take from the + * given pool, and also debits the entropy count accordingly. */ - static size_t account(struct entropy_store *r, size_t nbytes, int min, int reserved) { @@ -1018,6 +1010,12 @@ retry: return ibytes; } +/* + * This function does the actual extraction for extract_entropy and + * extract_entropy_user. + * + * Note: we assume that .poolwords is a multiple of 16 words. + */ static void extract_buf(struct entropy_store *r, __u8 *out) { int i; @@ -1079,6 +1077,15 @@ static void extract_buf(struct entropy_store *r, __u8 *out) memset(&hash, 0, sizeof(hash)); } +/* + * This function extracts randomness from the "entropy pool", and + * returns it in a buffer. + * + * The min parameter specifies the minimum amount we can pull before + * failing to avoid races that defeat catastrophic reseeding while the + * reserved parameter indicates how much entropy we must leave in the + * pool after each pull to avoid starving other readers. + */ static ssize_t extract_entropy(struct entropy_store *r, void *buf, size_t nbytes, int min, int reserved) { @@ -1129,6 +1136,10 @@ static ssize_t extract_entropy(struct entropy_store *r, void *buf, return ret; } +/* + * This function extracts randomness from the "entropy pool", and + * returns it in a userspace buffer. + */ static ssize_t extract_entropy_user(struct entropy_store *r, void __user *buf, size_t nbytes) { -- cgit v1.2.3-70-g09d2 From ee1de406ba6eb1e01f143fe3351e70cc772cc63e Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 15:56:16 -0500 Subject: random: simplify accounting logic This logic is exactly equivalent to the old logic, but it should be easier to see what it's doing. The equivalence depends on one fact from outside this function: when 'r->limit' is false, 'reserved' is zero. (Well, two facts; the other is that 'reserved' is never negative.) Cc: Jiri Kosina Cc: "H. Peter Anvin" Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 2c532a6b0a2..9675821b4b5 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -984,14 +984,10 @@ retry: ibytes = 0; } else { /* If limited, never pull more than available */ - if (r->limit && ibytes + reserved >= have_bytes) - ibytes = have_bytes - reserved; - - if (have_bytes >= ibytes + reserved) - entropy_count -= ibytes << (ENTROPY_SHIFT + 3); - else - entropy_count = reserved << (ENTROPY_SHIFT + 3); - + if (r->limit) + ibytes = min_t(size_t, ibytes, have_bytes - reserved); + entropy_count = max_t(int, 0, + entropy_count - (ibytes << (ENTROPY_SHIFT + 3))); if (cmpxchg(&r->entropy_count, orig, entropy_count) != orig) goto retry; -- cgit v1.2.3-70-g09d2 From a58aa4edc6d2e779894b1fa95a2f4de157ff3b3b Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 29 Nov 2013 20:09:37 -0500 Subject: random: forget lock in lockless accounting The only mutable data accessed here is ->entropy_count, but since 10b3a32d2 ("random: fix accounting race condition") we use cmpxchg to protect our accesses to ->entropy_count here. Drop the use of the lock. Cc: Jiri Kosina Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 4 ---- 1 file changed, 4 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 9675821b4b5..694510af4fc 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -970,9 +970,6 @@ static size_t account(struct entropy_store *r, size_t nbytes, int min, int entropy_count, orig; size_t ibytes; - /* Hold lock while accounting */ - spin_lock_irqsave(&r->lock, flags); - BUG_ON(r->entropy_count > r->poolinfo->poolfracbits); /* Can we pull enough? */ @@ -995,7 +992,6 @@ retry: < random_write_wakeup_thresh) wakeup_write = 1; } - spin_unlock_irqrestore(&r->lock, flags); trace_debit_entropy(r->name, 8 * ibytes); if (wakeup_write) { -- cgit v1.2.3-70-g09d2 From 8c2aa3390ebb59cba4495a56557b70ad0575eef5 Mon Sep 17 00:00:00 2001 From: Greg Price Date: Thu, 5 Dec 2013 19:19:29 -0500 Subject: random: tighten bound on random_read_wakeup_thresh We use this value in a few places other than its literal meaning, in particular in _xfer_secondary_pool() as a minimum number of bits to pull from the input pool at a time into either output pool. It doesn't make sense to pull more bits than the whole size of an output pool. We could and possibly should separate the quantities "how much should the input pool have to have to wake up /dev/random readers" and "how much should we transfer from the input to an output pool at a time", but nobody is likely to be sad they can't set the first quantity to more than 1024 bits, so for now just limit them both. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 694510af4fc..70b8ebf08ed 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1490,7 +1490,7 @@ EXPORT_SYMBOL(generate_random_uuid); #include static int min_read_thresh = 8, min_write_thresh; -static int max_read_thresh = INPUT_POOL_WORDS * 32; +static int max_read_thresh = OUTPUT_POOL_WORDS * 32; static int max_write_thresh = INPUT_POOL_WORDS * 32; static char sysctl_bootid[16]; -- cgit v1.2.3-70-g09d2 From 0fb7a01af5b0cbe5bf365891fc4d186f2caa23f7 Mon Sep 17 00:00:00 2001 From: Greg Price Date: Thu, 5 Dec 2013 19:32:19 -0500 Subject: random: simplify accounting code With this we handle "reserved" in just one place. As a bonus the code becomes less nested, and the "wakeup_write" flag variable becomes unnecessary. The variable "flags" was already unused. This code behaves identically to the previous version except in two pathological cases that don't occur. If the argument "nbytes" is already less than "min", then we didn't previously enforce "min". If r->limit is false while "reserved" is nonzero, then we previously applied "reserved" in checking whether we had enough bits, even though we don't apply it to actually limit how many we take. The callers of account() never exercise either of these cases. Before the previous commit, it was possible for "nbytes" to be less than "min" if userspace chose a pathological configuration, but no longer. Cc: Jiri Kosina Cc: "H. Peter Anvin" Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 27 ++++++++++----------------- 1 file changed, 10 insertions(+), 17 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 70b8ebf08ed..ded4339be8f 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -964,8 +964,6 @@ static void push_to_pool(struct work_struct *work) static size_t account(struct entropy_store *r, size_t nbytes, int min, int reserved) { - unsigned long flags; - int wakeup_write = 0; int have_bytes; int entropy_count, orig; size_t ibytes; @@ -977,24 +975,19 @@ retry: entropy_count = orig = ACCESS_ONCE(r->entropy_count); have_bytes = entropy_count >> (ENTROPY_SHIFT + 3); ibytes = nbytes; - if (have_bytes < min + reserved) { + /* If limited, never pull more than available */ + if (r->limit) + ibytes = min_t(size_t, ibytes, have_bytes - reserved); + if (ibytes < min) ibytes = 0; - } else { - /* If limited, never pull more than available */ - if (r->limit) - ibytes = min_t(size_t, ibytes, have_bytes - reserved); - entropy_count = max_t(int, 0, - entropy_count - (ibytes << (ENTROPY_SHIFT + 3))); - if (cmpxchg(&r->entropy_count, orig, entropy_count) != orig) - goto retry; - - if ((r->entropy_count >> ENTROPY_SHIFT) - < random_write_wakeup_thresh) - wakeup_write = 1; - } + entropy_count = max_t(int, 0, + entropy_count - (ibytes << (ENTROPY_SHIFT + 3))); + if (cmpxchg(&r->entropy_count, orig, entropy_count) != orig) + goto retry; trace_debit_entropy(r->name, 8 * ibytes); - if (wakeup_write) { + if (ibytes && + (r->entropy_count >> ENTROPY_SHIFT) < random_write_wakeup_thresh) { wake_up_interruptible(&random_write_wait); kill_fasync(&fasync, SIGIO, POLL_OUT); } -- cgit v1.2.3-70-g09d2 From 7d1b08c40c4f02c119476b29eca9bbc8d98d2a83 Mon Sep 17 00:00:00 2001 From: Greg Price Date: Sat, 7 Dec 2013 09:49:55 -0500 Subject: random: entropy_bytes is actually bits The variable 'entropy_bytes' is set from an expression that actually counts bits. Fortunately it's also only compared to values that also count bits. Rename it accordingly. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index ded4339be8f..581d806823e 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -666,10 +666,10 @@ retry: r->entropy_total, _RET_IP_); if (r == &input_pool) { - int entropy_bytes = entropy_count >> ENTROPY_SHIFT; + int entropy_bits = entropy_count >> ENTROPY_SHIFT; /* should we wake readers? */ - if (entropy_bytes >= random_read_wakeup_thresh) { + if (entropy_bits >= random_read_wakeup_thresh) { wake_up_interruptible(&random_read_wait); kill_fasync(&fasync, SIGIO, POLL_IN); } @@ -678,7 +678,7 @@ retry: * forth between them, until the output pools are 75% * full. */ - if (entropy_bytes > random_write_wakeup_thresh && + if (entropy_bits > random_write_wakeup_thresh && r->initialized && r->entropy_total >= 2*random_read_wakeup_thresh) { static struct entropy_store *last = &blocking_pool; -- cgit v1.2.3-70-g09d2 From 2132a96f66b6b4d865113e7d4cb56d5f7c6e3cdf Mon Sep 17 00:00:00 2001 From: Greg Price Date: Fri, 6 Dec 2013 21:28:03 -0500 Subject: random: clarify bits/bytes in wakeup thresholds These are a recurring cause of confusion, so rename them to hopefully be clearer. Signed-off-by: Greg Price Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 34 +++++++++++++++++----------------- 1 file changed, 17 insertions(+), 17 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 581d806823e..8cc7d651567 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -295,14 +295,14 @@ * The minimum number of bits of entropy before we wake up a read on * /dev/random. Should be enough to do a significant reseed. */ -static int random_read_wakeup_thresh = 64; +static int random_read_wakeup_bits = 64; /* * If the entropy count falls under this number of bits, then we * should wake up processes which are selecting or polling on write * access to /dev/random. */ -static int random_write_wakeup_thresh = 28 * OUTPUT_POOL_WORDS; +static int random_write_wakeup_bits = 28 * OUTPUT_POOL_WORDS; /* * The minimum number of seconds between urandom pool reseeding. We @@ -669,7 +669,7 @@ retry: int entropy_bits = entropy_count >> ENTROPY_SHIFT; /* should we wake readers? */ - if (entropy_bits >= random_read_wakeup_thresh) { + if (entropy_bits >= random_read_wakeup_bits) { wake_up_interruptible(&random_read_wait); kill_fasync(&fasync, SIGIO, POLL_IN); } @@ -678,9 +678,9 @@ retry: * forth between them, until the output pools are 75% * full. */ - if (entropy_bits > random_write_wakeup_thresh && + if (entropy_bits > random_write_wakeup_bits && r->initialized && - r->entropy_total >= 2*random_read_wakeup_thresh) { + r->entropy_total >= 2*random_read_wakeup_bits) { static struct entropy_store *last = &blocking_pool; struct entropy_store *other = &blocking_pool; @@ -924,19 +924,19 @@ static void _xfer_secondary_pool(struct entropy_store *r, size_t nbytes) { __u32 tmp[OUTPUT_POOL_WORDS]; - /* For /dev/random's pool, always leave two wakeup worth's BITS */ - int rsvd = r->limit ? 0 : random_read_wakeup_thresh/4; + /* For /dev/random's pool, always leave two wakeups' worth */ + int rsvd_bytes = r->limit ? 0 : random_read_wakeup_bits / 4; int bytes = nbytes; - /* pull at least as many as BYTES as wakeup BITS */ - bytes = max_t(int, bytes, random_read_wakeup_thresh / 8); + /* pull at least as much as a wakeup */ + bytes = max_t(int, bytes, random_read_wakeup_bits / 8); /* but never more than the buffer size */ bytes = min_t(int, bytes, sizeof(tmp)); trace_xfer_secondary_pool(r->name, bytes * 8, nbytes * 8, ENTROPY_BITS(r), ENTROPY_BITS(r->pull)); bytes = extract_entropy(r->pull, tmp, bytes, - random_read_wakeup_thresh / 8, rsvd); + random_read_wakeup_bits / 8, rsvd_bytes); mix_pool_bytes(r, tmp, bytes, NULL); credit_entropy_bits(r, bytes*8); } @@ -952,7 +952,7 @@ static void push_to_pool(struct work_struct *work) struct entropy_store *r = container_of(work, struct entropy_store, push_work); BUG_ON(!r); - _xfer_secondary_pool(r, random_read_wakeup_thresh/8); + _xfer_secondary_pool(r, random_read_wakeup_bits/8); trace_push_to_pool(r->name, r->entropy_count >> ENTROPY_SHIFT, r->pull->entropy_count >> ENTROPY_SHIFT); } @@ -987,7 +987,7 @@ retry: trace_debit_entropy(r->name, 8 * ibytes); if (ibytes && - (r->entropy_count >> ENTROPY_SHIFT) < random_write_wakeup_thresh) { + (r->entropy_count >> ENTROPY_SHIFT) < random_write_wakeup_bits) { wake_up_interruptible(&random_write_wait); kill_fasync(&fasync, SIGIO, POLL_OUT); } @@ -1303,7 +1303,7 @@ random_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) wait_event_interruptible(random_read_wait, ENTROPY_BITS(&input_pool) >= - random_read_wakeup_thresh); + random_read_wakeup_bits); if (signal_pending(current)) return -ERESTARTSYS; } @@ -1334,9 +1334,9 @@ random_poll(struct file *file, poll_table * wait) poll_wait(file, &random_read_wait, wait); poll_wait(file, &random_write_wait, wait); mask = 0; - if (ENTROPY_BITS(&input_pool) >= random_read_wakeup_thresh) + if (ENTROPY_BITS(&input_pool) >= random_read_wakeup_bits) mask |= POLLIN | POLLRDNORM; - if (ENTROPY_BITS(&input_pool) < random_write_wakeup_thresh) + if (ENTROPY_BITS(&input_pool) < random_write_wakeup_bits) mask |= POLLOUT | POLLWRNORM; return mask; } @@ -1559,7 +1559,7 @@ struct ctl_table random_table[] = { }, { .procname = "read_wakeup_threshold", - .data = &random_read_wakeup_thresh, + .data = &random_read_wakeup_bits, .maxlen = sizeof(int), .mode = 0644, .proc_handler = proc_dointvec_minmax, @@ -1568,7 +1568,7 @@ struct ctl_table random_table[] = { }, { .procname = "write_wakeup_threshold", - .data = &random_write_wakeup_thresh, + .data = &random_write_wakeup_bits, .maxlen = sizeof(int), .mode = 0644, .proc_handler = proc_dointvec_minmax, -- cgit v1.2.3-70-g09d2 From 46884442fc5bb81a896f7245bd850fde9b435509 Mon Sep 17 00:00:00 2001 From: Theodore Ts'o Date: Tue, 17 Dec 2013 21:16:39 -0500 Subject: random: use the architectural HWRNG for the SHA's IV in extract_buf() To help assuage the fears of those who think the NSA can introduce a massive hack into the instruction decode and out of order execution engine in the CPU without hundreds of Intel engineers knowing about it (only one of which woud need to have the conscience and courage of Edward Snowden to spill the beans to the public), use the HWRNG to initialize the SHA starting value, instead of xor'ing it in afterwards. Signed-off-by: "Theodore Ts'o" --- drivers/char/random.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index 8cc7d651567..d07575c99a5 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1012,23 +1012,23 @@ static void extract_buf(struct entropy_store *r, __u8 *out) __u8 extract[64]; unsigned long flags; - /* Generate a hash across the pool, 16 words (512 bits) at a time */ - sha_init(hash.w); - spin_lock_irqsave(&r->lock, flags); - for (i = 0; i < r->poolinfo->poolwords; i += 16) - sha_transform(hash.w, (__u8 *)(r->pool + i), workspace); - /* * If we have an architectural hardware random number - * generator, mix that in, too. + * generator, use it for SHA's initial vector */ + sha_init(hash.w); for (i = 0; i < LONGS(20); i++) { unsigned long v; if (!arch_get_random_long(&v)) break; - hash.l[i] ^= v; + hash.l[i] = v; } + /* Generate a hash across the pool, 16 words (512 bits) at a time */ + spin_lock_irqsave(&r->lock, flags); + for (i = 0; i < r->poolinfo->poolwords; i += 16) + sha_transform(hash.w, (__u8 *)(r->pool + i), workspace); + /* * We mix the hash back into the pool to prevent backtracking * attacks (where the attacker knows the state of the pool -- cgit v1.2.3-70-g09d2 From 83664a6928a420b5ccfc0cf23ddbfe3634fea271 Mon Sep 17 00:00:00 2001 From: "H. Peter Anvin" Date: Mon, 17 Mar 2014 16:36:28 -0700 Subject: random: Use arch_get_random_seed*() at init time and once a second Use arch_get_random_seed*() in two places in the Linux random driver (drivers/char/random.c): 1. During entropy pool initialization, use RDSEED in favor of RDRAND, with a fallback to the latter. Entropy exhaustion is unlikely to happen there on physical hardware as the machine is single-threaded at that point, but could happen in a virtual machine. In that case, the fallback to RDRAND will still provide more than adequate entropy pool initialization. 2. Once a second, issue RDSEED and, if successful, feed it to the entropy pool. To ensure an extra layer of security, only credit half the entropy just in case. Suggested-by: Linus Torvalds Reviewed-by: Ingo Molnar Signed-off-by: H. Peter Anvin Signed-off-by: Theodore Ts'o --- drivers/char/random.c | 24 ++++++++++++++++++++---- 1 file changed, 20 insertions(+), 4 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index d07575c99a5..a4bea7775e0 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -844,6 +844,8 @@ void add_interrupt_randomness(int irq, int irq_flags) cycles_t cycles = random_get_entropy(); __u32 input[4], c_high, j_high; __u64 ip; + unsigned long seed; + int credit; c_high = (sizeof(cycles) > 4) ? cycles >> 32 : 0; j_high = (sizeof(now) > 4) ? now >> 32 : 0; @@ -862,20 +864,33 @@ void add_interrupt_randomness(int irq, int irq_flags) r = nonblocking_pool.initialized ? &input_pool : &nonblocking_pool; __mix_pool_bytes(r, &fast_pool->pool, sizeof(fast_pool->pool), NULL); + /* * If we don't have a valid cycle counter, and we see * back-to-back timer interrupts, then skip giving credit for - * any entropy. + * any entropy, otherwise credit 1 bit. */ + credit = 1; if (cycles == 0) { if (irq_flags & __IRQF_TIMER) { if (fast_pool->last_timer_intr) - return; + credit = 0; fast_pool->last_timer_intr = 1; } else fast_pool->last_timer_intr = 0; } - credit_entropy_bits(r, 1); + + /* + * If we have architectural seed generator, produce a seed and + * add it to the pool. For the sake of paranoia count it as + * 50% entropic. + */ + if (arch_get_random_seed_long(&seed)) { + __mix_pool_bytes(r, &seed, sizeof(seed), NULL); + credit += sizeof(seed) * 4; + } + + credit_entropy_bits(r, credit); } #ifdef CONFIG_BLOCK @@ -1235,7 +1250,8 @@ static void init_std_data(struct entropy_store *r) r->last_pulled = jiffies; mix_pool_bytes(r, &now, sizeof(now), NULL); for (i = r->poolinfo->poolbytes; i > 0; i -= sizeof(rv)) { - if (!arch_get_random_long(&rv)) + if (!arch_get_random_seed_long(&rv) && + !arch_get_random_long(&rv)) rv = random_get_entropy(); mix_pool_bytes(r, &rv, sizeof(rv), NULL); } -- cgit v1.2.3-70-g09d2 From 331c6490c7f10dcf263712e313b7c0bc7fb6d77a Mon Sep 17 00:00:00 2001 From: "H. Peter Anvin" Date: Mon, 17 Mar 2014 16:36:29 -0700 Subject: random: If we have arch_get_random_seed*(), try it before blocking If we have arch_get_random_seed*(), try to use it for emergency refill of the entropy pool before giving up and blocking on /dev/random. It may or may not work in the moment, but if it does work, it will give the user better service than blocking will. Reviewed-by: Ingo Molnar Signed-off-by: H. Peter Anvin Signed-off-by: Theodore Ts'o --- drivers/char/random.c | 33 +++++++++++++++++++++++++++++++++ 1 file changed, 33 insertions(+) (limited to 'drivers/char') diff --git a/drivers/char/random.c b/drivers/char/random.c index a4bea7775e0..c35cee268e1 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1294,6 +1294,34 @@ void rand_initialize_disk(struct gendisk *disk) } #endif +/* + * Attempt an emergency refill using arch_get_random_seed_long(). + * + * As with add_interrupt_randomness() be paranoid and only + * credit the output as 50% entropic. + */ +static int arch_random_refill(void) +{ + const unsigned int nlongs = 64; /* Arbitrary number */ + unsigned int n = 0; + unsigned int i; + unsigned long buf[nlongs]; + + for (i = 0; i < nlongs; i++) { + if (arch_get_random_seed_long(&buf[n])) + n++; + } + + if (n) { + unsigned int rand_bytes = n * sizeof(unsigned long); + + mix_pool_bytes(&input_pool, buf, rand_bytes, NULL); + credit_entropy_bits(&input_pool, rand_bytes*4); + } + + return n; +} + static ssize_t random_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) { @@ -1312,8 +1340,13 @@ random_read(struct file *file, char __user *buf, size_t nbytes, loff_t *ppos) ENTROPY_BITS(&input_pool)); if (n > 0) return n; + /* Pool is (near) empty. Maybe wait and retry. */ + /* First try an emergency refill */ + if (arch_random_refill()) + continue; + if (file->f_flags & O_NONBLOCK) return -EAGAIN; -- cgit v1.2.3-70-g09d2 From 7b878d4b48c4e04b936918bb83836a107ba453b3 Mon Sep 17 00:00:00 2001 From: "H. Peter Anvin" Date: Mon, 17 Mar 2014 16:36:30 -0700 Subject: random: Add arch_has_random[_seed]() Add predicate functions for having arch_get_random[_seed]*(). The only current use is to avoid the loop in arch_random_refill() when arch_get_random_seed_long() is unavailable. Signed-off-by: H. Peter Anvin Cc: Benjamin Herrenschmidt Cc: Paul Mackerras Cc: Michael Ellerman Signed-off-by: Theodore Ts'o --- arch/powerpc/include/asm/archrandom.h | 9 +++++++++ arch/x86/include/asm/archrandom.h | 3 +++ drivers/char/random.c | 3 +++ include/linux/random.h | 8 ++++++++ 4 files changed, 23 insertions(+) (limited to 'drivers/char') diff --git a/arch/powerpc/include/asm/archrandom.h b/arch/powerpc/include/asm/archrandom.h index 801beba4e64..bde53110363 100644 --- a/arch/powerpc/include/asm/archrandom.h +++ b/arch/powerpc/include/asm/archrandom.h @@ -25,6 +25,11 @@ static inline int arch_get_random_int(unsigned int *v) return rc; } +static inline int arch_has_random(void) +{ + return !!ppc_md.get_random_long; +} + int powernv_get_random_long(unsigned long *v); static inline int arch_get_random_seed_long(unsigned long *v) @@ -35,6 +40,10 @@ static inline int arch_get_random_seed_int(unsigned int *v) { return 0; } +static inline int arch_has_random_seed(void) +{ + return 0; +} #endif /* CONFIG_ARCH_RANDOM */ diff --git a/arch/x86/include/asm/archrandom.h b/arch/x86/include/asm/archrandom.h index 6ad7f6d3f97..69f1366f1aa 100644 --- a/arch/x86/include/asm/archrandom.h +++ b/arch/x86/include/asm/archrandom.h @@ -114,6 +114,9 @@ GET_SEED(arch_get_random_seed_int, unsigned int, RDSEED_INT, ASM_NOP4); #endif /* CONFIG_X86_64 */ +#define arch_has_random() static_cpu_has(X86_FEATURE_RDRAND) +#define arch_has_random_seed() static_cpu_has(X86_FEATURE_RDSEED) + #else static inline int rdrand_long(unsigned long *v) diff --git a/drivers/char/random.c b/drivers/char/random.c index c35cee268e1..6b75713d953 100644 --- a/drivers/char/random.c +++ b/drivers/char/random.c @@ -1307,6 +1307,9 @@ static int arch_random_refill(void) unsigned int i; unsigned long buf[nlongs]; + if (!arch_has_random_seed()) + return 0; + for (i = 0; i < nlongs; i++) { if (arch_get_random_seed_long(&buf[n])) n++; diff --git a/include/linux/random.h b/include/linux/random.h index c2f08131050..57fbbffd77a 100644 --- a/include/linux/random.h +++ b/include/linux/random.h @@ -88,6 +88,10 @@ static inline int arch_get_random_int(unsigned int *v) { return 0; } +static inline int arch_has_random(void) +{ + return 0; +} static inline int arch_get_random_seed_long(unsigned long *v) { return 0; @@ -96,6 +100,10 @@ static inline int arch_get_random_seed_int(unsigned int *v) { return 0; } +static inline int arch_has_random_seed(void) +{ + return 0; +} #endif /* Pseudo random number generator from numerical recipes. */ -- cgit v1.2.3-70-g09d2 From fbb32750a62df75d1ffea547f3908b21c5496d9f Mon Sep 17 00:00:00 2001 From: Al Viro Date: Sun, 2 Feb 2014 21:09:54 -0500 Subject: pipe: kill ->map() and ->unmap() all pipe_buffer_operations have the same instances of those... Signed-off-by: Al Viro --- drivers/char/virtio_console.c | 4 +-- fs/fuse/dev.c | 6 ++-- fs/pipe.c | 70 ++++++++++--------------------------------- fs/splice.c | 24 +++++---------- include/linux/pipe_fs_i.h | 19 ------------ kernel/relay.c | 2 -- kernel/trace/trace.c | 4 --- 7 files changed, 29 insertions(+), 100 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/virtio_console.c b/drivers/char/virtio_console.c index 6928d094451..60aafb8a1f2 100644 --- a/drivers/char/virtio_console.c +++ b/drivers/char/virtio_console.c @@ -901,9 +901,9 @@ static int pipe_to_sg(struct pipe_inode_info *pipe, struct pipe_buffer *buf, if (len + offset > PAGE_SIZE) len = PAGE_SIZE - offset; - src = buf->ops->map(pipe, buf, 1); + src = kmap_atomic(buf->page); memcpy(page_address(page) + offset, src + buf->offset, len); - buf->ops->unmap(pipe, buf, src); + kunmap_atomic(src); sg_set_page(&(sgl->sg[sgl->n]), page, len, offset); } diff --git a/fs/fuse/dev.c b/fs/fuse/dev.c index f90af6fe688..aac71ce373e 100644 --- a/fs/fuse/dev.c +++ b/fs/fuse/dev.c @@ -667,7 +667,7 @@ static void fuse_copy_finish(struct fuse_copy_state *cs) struct pipe_buffer *buf = cs->currbuf; if (!cs->write) { - buf->ops->unmap(cs->pipe, buf, cs->mapaddr); + kunmap_atomic(cs->mapaddr); } else { kunmap_atomic(cs->mapaddr); buf->len = PAGE_SIZE - cs->len; @@ -706,7 +706,7 @@ static int fuse_copy_fill(struct fuse_copy_state *cs) BUG_ON(!cs->nr_segs); cs->currbuf = buf; - cs->mapaddr = buf->ops->map(cs->pipe, buf, 1); + cs->mapaddr = kmap_atomic(buf->page); cs->len = buf->len; cs->buf = cs->mapaddr + buf->offset; cs->pipebufs++; @@ -874,7 +874,7 @@ static int fuse_try_move_page(struct fuse_copy_state *cs, struct page **pagep) out_fallback_unlock: unlock_page(newpage); out_fallback: - cs->mapaddr = buf->ops->map(cs->pipe, buf, 1); + cs->mapaddr = kmap_atomic(buf->page); cs->buf = cs->mapaddr + buf->offset; err = lock_request(cs->fc, cs->req); diff --git a/fs/pipe.c b/fs/pipe.c index 78fd0d0788d..6679c95eb4c 100644 --- a/fs/pipe.c +++ b/fs/pipe.c @@ -225,52 +225,6 @@ static void anon_pipe_buf_release(struct pipe_inode_info *pipe, page_cache_release(page); } -/** - * generic_pipe_buf_map - virtually map a pipe buffer - * @pipe: the pipe that the buffer belongs to - * @buf: the buffer that should be mapped - * @atomic: whether to use an atomic map - * - * Description: - * This function returns a kernel virtual address mapping for the - * pipe_buffer passed in @buf. If @atomic is set, an atomic map is provided - * and the caller has to be careful not to fault before calling - * the unmap function. - * - * Note that this function calls kmap_atomic() if @atomic != 0. - */ -void *generic_pipe_buf_map(struct pipe_inode_info *pipe, - struct pipe_buffer *buf, int atomic) -{ - if (atomic) { - buf->flags |= PIPE_BUF_FLAG_ATOMIC; - return kmap_atomic(buf->page); - } - - return kmap(buf->page); -} -EXPORT_SYMBOL(generic_pipe_buf_map); - -/** - * generic_pipe_buf_unmap - unmap a previously mapped pipe buffer - * @pipe: the pipe that the buffer belongs to - * @buf: the buffer that should be unmapped - * @map_data: the data that the mapping function returned - * - * Description: - * This function undoes the mapping that ->map() provided. - */ -void generic_pipe_buf_unmap(struct pipe_inode_info *pipe, - struct pipe_buffer *buf, void *map_data) -{ - if (buf->flags & PIPE_BUF_FLAG_ATOMIC) { - buf->flags &= ~PIPE_BUF_FLAG_ATOMIC; - kunmap_atomic(map_data); - } else - kunmap(buf->page); -} -EXPORT_SYMBOL(generic_pipe_buf_unmap); - /** * generic_pipe_buf_steal - attempt to take ownership of a &pipe_buffer * @pipe: the pipe that the buffer belongs to @@ -351,8 +305,6 @@ EXPORT_SYMBOL(generic_pipe_buf_release); static const struct pipe_buf_operations anon_pipe_buf_ops = { .can_merge = 1, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = anon_pipe_buf_release, .steal = generic_pipe_buf_steal, @@ -361,8 +313,6 @@ static const struct pipe_buf_operations anon_pipe_buf_ops = { static const struct pipe_buf_operations packet_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = anon_pipe_buf_release, .steal = generic_pipe_buf_steal, @@ -410,9 +360,15 @@ pipe_read(struct kiocb *iocb, const struct iovec *_iov, atomic = !iov_fault_in_pages_write(iov, chars); redo: - addr = ops->map(pipe, buf, atomic); + if (atomic) + addr = kmap_atomic(buf->page); + else + addr = kmap(buf->page); error = pipe_iov_copy_to_user(iov, addr + buf->offset, chars, atomic); - ops->unmap(pipe, buf, addr); + if (atomic) + kunmap_atomic(addr); + else + kunmap(buf->page); if (unlikely(error)) { /* * Just retry with the slow path if we failed. @@ -538,10 +494,16 @@ pipe_write(struct kiocb *iocb, const struct iovec *_iov, iov_fault_in_pages_read(iov, chars); redo1: - addr = ops->map(pipe, buf, atomic); + if (atomic) + addr = kmap_atomic(buf->page); + else + addr = kmap(buf->page); error = pipe_iov_copy_from_user(offset + addr, iov, chars, atomic); - ops->unmap(pipe, buf, addr); + if (atomic) + kunmap_atomic(addr); + else + kunmap(buf->page); ret = error; do_wakeup = 1; if (error) { diff --git a/fs/splice.c b/fs/splice.c index 12028fa41de..ca3bfbd970f 100644 --- a/fs/splice.c +++ b/fs/splice.c @@ -136,8 +136,6 @@ error: const struct pipe_buf_operations page_cache_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = page_cache_pipe_buf_confirm, .release = page_cache_pipe_buf_release, .steal = page_cache_pipe_buf_steal, @@ -156,8 +154,6 @@ static int user_page_pipe_buf_steal(struct pipe_inode_info *pipe, static const struct pipe_buf_operations user_page_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = page_cache_pipe_buf_release, .steal = user_page_pipe_buf_steal, @@ -547,8 +543,6 @@ EXPORT_SYMBOL(generic_file_splice_read); static const struct pipe_buf_operations default_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = generic_pipe_buf_release, .steal = generic_pipe_buf_steal, @@ -564,8 +558,6 @@ static int generic_pipe_buf_nosteal(struct pipe_inode_info *pipe, /* Pipe buffer operations for a socket and similar. */ const struct pipe_buf_operations nosteal_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = generic_pipe_buf_release, .steal = generic_pipe_buf_nosteal, @@ -767,13 +759,13 @@ int pipe_to_file(struct pipe_inode_info *pipe, struct pipe_buffer *buf, goto out; if (buf->page != page) { - char *src = buf->ops->map(pipe, buf, 1); + char *src = kmap_atomic(buf->page); char *dst = kmap_atomic(page); memcpy(dst + offset, src + buf->offset, this_len); flush_dcache_page(page); kunmap_atomic(dst); - buf->ops->unmap(pipe, buf, src); + kunmap_atomic(src); } ret = pagecache_write_end(file, mapping, sd->pos, this_len, this_len, page, fsdata); @@ -1067,9 +1059,9 @@ static int write_pipe_buf(struct pipe_inode_info *pipe, struct pipe_buffer *buf, void *data; loff_t tmp = sd->pos; - data = buf->ops->map(pipe, buf, 0); + data = kmap(buf->page); ret = __kernel_write(sd->u.file, data + buf->offset, sd->len, &tmp); - buf->ops->unmap(pipe, buf, data); + kunmap(buf->page); return ret; } @@ -1536,10 +1528,10 @@ static int pipe_to_user(struct pipe_inode_info *pipe, struct pipe_buffer *buf, * pages and doing an atomic copy */ if (!fault_in_pages_writeable(sd->u.userptr, sd->len)) { - src = buf->ops->map(pipe, buf, 1); + src = kmap_atomic(buf->page); ret = __copy_to_user_inatomic(sd->u.userptr, src + buf->offset, sd->len); - buf->ops->unmap(pipe, buf, src); + kunmap_atomic(src); if (!ret) { ret = sd->len; goto out; @@ -1549,13 +1541,13 @@ static int pipe_to_user(struct pipe_inode_info *pipe, struct pipe_buffer *buf, /* * No dice, use slow non-atomic map and copy */ - src = buf->ops->map(pipe, buf, 0); + src = kmap(buf->page); ret = sd->len; if (copy_to_user(sd->u.userptr, src + buf->offset, sd->len)) ret = -EFAULT; - buf->ops->unmap(pipe, buf, src); + kunmap(buf->page); out: if (ret > 0) sd->u.userptr += ret; diff --git a/include/linux/pipe_fs_i.h b/include/linux/pipe_fs_i.h index ab575269211..6dffcebe610 100644 --- a/include/linux/pipe_fs_i.h +++ b/include/linux/pipe_fs_i.h @@ -82,23 +82,6 @@ struct pipe_buf_operations { */ int can_merge; - /* - * ->map() returns a virtual address mapping of the pipe buffer. - * The last integer flag reflects whether this should be an atomic - * mapping or not. The atomic map is faster, however you can't take - * page faults before calling ->unmap() again. So if you need to eg - * access user data through copy_to/from_user(), then you must get - * a non-atomic map. ->map() uses the kmap_atomic slot for - * atomic maps, you have to be careful if mapping another page as - * source or destination for a copy. - */ - void * (*map)(struct pipe_inode_info *, struct pipe_buffer *, int); - - /* - * Undoes ->map(), finishes the virtual mapping of the pipe buffer. - */ - void (*unmap)(struct pipe_inode_info *, struct pipe_buffer *, void *); - /* * ->confirm() verifies that the data in the pipe buffer is there * and that the contents are good. If the pages in the pipe belong @@ -150,8 +133,6 @@ struct pipe_inode_info *alloc_pipe_info(void); void free_pipe_info(struct pipe_inode_info *); /* Generic pipe buffer ops functions */ -void *generic_pipe_buf_map(struct pipe_inode_info *, struct pipe_buffer *, int); -void generic_pipe_buf_unmap(struct pipe_inode_info *, struct pipe_buffer *, void *); void generic_pipe_buf_get(struct pipe_inode_info *, struct pipe_buffer *); int generic_pipe_buf_confirm(struct pipe_inode_info *, struct pipe_buffer *); int generic_pipe_buf_steal(struct pipe_inode_info *, struct pipe_buffer *); diff --git a/kernel/relay.c b/kernel/relay.c index 5001c9887db..98833f664fb 100644 --- a/kernel/relay.c +++ b/kernel/relay.c @@ -1195,8 +1195,6 @@ static void relay_pipe_buf_release(struct pipe_inode_info *pipe, static const struct pipe_buf_operations relay_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = relay_pipe_buf_release, .steal = generic_pipe_buf_steal, diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c index 24c1f238255..7511de35257 100644 --- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c @@ -4316,8 +4316,6 @@ static void tracing_spd_release_pipe(struct splice_pipe_desc *spd, static const struct pipe_buf_operations tracing_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = generic_pipe_buf_release, .steal = generic_pipe_buf_steal, @@ -5194,8 +5192,6 @@ static void buffer_pipe_buf_get(struct pipe_inode_info *pipe, /* Pipe buffer operations for a buffer. */ static const struct pipe_buf_operations buffer_pipe_buf_ops = { .can_merge = 0, - .map = generic_pipe_buf_map, - .unmap = generic_pipe_buf_unmap, .confirm = generic_pipe_buf_confirm, .release = buffer_pipe_buf_release, .steal = generic_pipe_buf_steal, -- cgit v1.2.3-70-g09d2 From 57dcf020f406e430050ed4153c03ce904ede07bc Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Mon, 31 Mar 2014 15:15:36 +0200 Subject: sonypi: Simplify dependencies X86 && !64BIT is better expressed as X86_32. Signed-off-by: Jean Delvare Cc: Arnd Bergmann Cc: Greg Kroah-Hartman Cc: Mattia Dongili Signed-off-by: Matthew Garrett --- drivers/char/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/char') diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig index 1386749b48f..fbae63e3d30 100644 --- a/drivers/char/Kconfig +++ b/drivers/char/Kconfig @@ -408,7 +408,7 @@ config APPLICOM config SONYPI tristate "Sony Vaio Programmable I/O Control Device support" - depends on X86 && PCI && INPUT && !64BIT + depends on X86_32 && PCI && INPUT ---help--- This driver enables access to the Sony Programmable I/O Control Device which can be found in many (all ?) Sony Vaio laptops. -- cgit v1.2.3-70-g09d2 From ce816fa88cca083c47ab9000b2138a83043a78be Mon Sep 17 00:00:00 2001 From: Uwe Kleine-König Date: Mon, 7 Apr 2014 15:39:19 -0700 Subject: Kconfig: rename HAS_IOPORT to HAS_IOPORT_MAP MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If the renamed symbol is defined lib/iomap.c implements ioport_map and ioport_unmap and currently (nearly) all platforms define the port accessor functions outb/inb and friend unconditionally. So HAS_IOPORT_MAP is the better name for this. Consequently NO_IOPORT is renamed to NO_IOPORT_MAP. The motivation for this change is to reintroduce a symbol HAS_IOPORT that signals if outb/int et al are available. I will address that at least one merge window later though to keep surprises to a minimum and catch new introductions of (HAS|NO)_IOPORT. The changes in this commit were done using: $ git grep -l -E '(NO|HAS)_IOPORT' | xargs perl -p -i -e 's/\b((?:CONFIG_)?(?:NO|HAS)_IOPORT)\b/$1_MAP/' Signed-off-by: Uwe Kleine-König Acked-by: Arnd Bergmann Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- arch/arc/Kconfig | 2 +- arch/arm/Kconfig | 12 ++++++------ arch/arm/mach-picoxcell/Kconfig | 2 +- arch/arm/mach-prima2/Kconfig | 2 +- arch/arm/mach-s3c24xx/Kconfig | 2 +- arch/arm/mach-shmobile/Kconfig | 2 +- arch/arm/mach-vexpress/Kconfig | 2 +- arch/arm/plat-samsung/Kconfig | 4 ++-- arch/arm64/Kconfig | 2 +- arch/cris/Kconfig | 2 +- arch/hexagon/Kconfig | 2 +- arch/m32r/Kconfig | 2 +- arch/m68k/Kconfig | 2 +- arch/metag/Kconfig | 2 +- arch/mips/Kconfig | 4 ++-- arch/openrisc/Kconfig | 2 +- arch/s390/Kconfig | 2 +- arch/sh/Kconfig | 4 ++-- arch/sh/boards/Kconfig | 8 ++++---- arch/sh/include/asm/io.h | 4 ++-- arch/sh/include/asm/io_trapped.h | 2 +- arch/sh/include/asm/machvec.h | 2 +- arch/sh/kernel/Makefile | 2 +- arch/sh/kernel/io_trapped.c | 4 ++-- arch/tile/Kconfig | 2 +- arch/unicore32/Kconfig | 2 +- arch/xtensa/Kconfig | 4 ++-- arch/xtensa/configs/iss_defconfig | 2 +- arch/xtensa/configs/s6105_defconfig | 2 +- drivers/char/tpm/Kconfig | 2 +- drivers/i2c/busses/Kconfig | 2 +- drivers/net/can/sja1000/Kconfig | 2 +- drivers/net/ethernet/3com/Kconfig | 2 +- include/asm-generic/io.h | 4 ++-- include/asm-generic/iomap.h | 2 +- include/linux/io.h | 2 +- lib/Kconfig | 4 ++-- lib/devres.c | 4 ++-- lib/iomap.c | 4 ++-- sound/isa/Kconfig | 2 +- sound/pci/Kconfig | 2 +- 41 files changed, 59 insertions(+), 59 deletions(-) (limited to 'drivers/char') diff --git a/arch/arc/Kconfig b/arch/arc/Kconfig index 75de197a2fe..9596b0ab108 100644 --- a/arch/arc/Kconfig +++ b/arch/arc/Kconfig @@ -57,7 +57,7 @@ config ARCH_FLATMEM_ENABLE config MMU def_bool y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config GENERIC_CALIBRATE_DELAY diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig index d7a71e3ef55..5db05f6a041 100644 --- a/arch/arm/Kconfig +++ b/arch/arm/Kconfig @@ -126,7 +126,7 @@ config HAVE_TCM config HAVE_PROC_CPU bool -config NO_IOPORT +config NO_IOPORT_MAP bool config EISA @@ -410,7 +410,7 @@ config ARCH_EBSA110 select ISA select NEED_MACH_IO_H select NEED_MACH_MEMORY_H - select NO_IOPORT + select NO_IOPORT_MAP help This is an evaluation board for the StrongARM processor available from Digital. It has limited hardware on-board, including an @@ -428,7 +428,7 @@ config ARCH_EFM32 select CPU_V7M select GENERIC_CLOCKEVENTS select NO_DMA - select NO_IOPORT + select NO_IOPORT_MAP select SPARSE_IRQ select USE_OF help @@ -677,7 +677,7 @@ config ARCH_SHMOBILE_LEGACY select HAVE_SMP select MIGHT_HAVE_CACHE_L2X0 select MULTI_IRQ_HANDLER - select NO_IOPORT + select NO_IOPORT_MAP select PINCTRL select PM_GENERIC_DOMAINS if PM select SPARSE_IRQ @@ -699,7 +699,7 @@ config ARCH_RPC select ISA_DMA_API select NEED_MACH_IO_H select NEED_MACH_MEMORY_H - select NO_IOPORT + select NO_IOPORT_MAP select VIRT_TO_BUS help On the Acorn Risc-PC, Linux can support the internal IDE disk and @@ -760,7 +760,7 @@ config ARCH_S3C64XX select HAVE_S3C2410_I2C if I2C select HAVE_S3C2410_WATCHDOG if WATCHDOG select HAVE_TCM - select NO_IOPORT + select NO_IOPORT_MAP select PLAT_SAMSUNG select PM_GENERIC_DOMAINS if PM select S3C_DEV_NAND diff --git a/arch/arm/mach-picoxcell/Kconfig b/arch/arm/mach-picoxcell/Kconfig index eca9eb1c593..62240f69b4e 100644 --- a/arch/arm/mach-picoxcell/Kconfig +++ b/arch/arm/mach-picoxcell/Kconfig @@ -4,4 +4,4 @@ config ARCH_PICOXCELL select ARM_VIC select DW_APB_TIMER_OF select HAVE_TCM - select NO_IOPORT + select NO_IOPORT_MAP diff --git a/arch/arm/mach-prima2/Kconfig b/arch/arm/mach-prima2/Kconfig index 3e8189186a5..e4e505f52ba 100644 --- a/arch/arm/mach-prima2/Kconfig +++ b/arch/arm/mach-prima2/Kconfig @@ -3,7 +3,7 @@ config ARCH_SIRF select ARCH_HAS_RESET_CONTROLLER select ARCH_REQUIRE_GPIOLIB select GENERIC_IRQ_CHIP - select NO_IOPORT + select NO_IOPORT_MAP select PINCTRL select PINCTRL_SIRF help diff --git a/arch/arm/mach-s3c24xx/Kconfig b/arch/arm/mach-s3c24xx/Kconfig index ba1cc624677..40cf50b9940 100644 --- a/arch/arm/mach-s3c24xx/Kconfig +++ b/arch/arm/mach-s3c24xx/Kconfig @@ -12,7 +12,7 @@ if ARCH_S3C24XX config PLAT_S3C24XX def_bool y select ARCH_REQUIRE_GPIOLIB - select NO_IOPORT + select NO_IOPORT_MAP select S3C_DEV_NAND select IRQ_DOMAIN help diff --git a/arch/arm/mach-shmobile/Kconfig b/arch/arm/mach-shmobile/Kconfig index a182008e3ae..0f92ba8e788 100644 --- a/arch/arm/mach-shmobile/Kconfig +++ b/arch/arm/mach-shmobile/Kconfig @@ -10,7 +10,7 @@ config ARCH_SHMOBILE_MULTI select ARM_GIC select MIGHT_HAVE_PCI select ARCH_DMA_ADDR_T_64BIT if ARM_LPAE - select NO_IOPORT + select NO_IOPORT_MAP select PINCTRL select ARCH_REQUIRE_GPIOLIB diff --git a/arch/arm/mach-vexpress/Kconfig b/arch/arm/mach-vexpress/Kconfig index 80b4be36f10..657d52d0391 100644 --- a/arch/arm/mach-vexpress/Kconfig +++ b/arch/arm/mach-vexpress/Kconfig @@ -10,7 +10,7 @@ config ARCH_VEXPRESS select HAVE_ARM_TWD if SMP select HAVE_PATA_PLATFORM select ICST - select NO_IOPORT + select NO_IOPORT_MAP select PLAT_VERSATILE select PLAT_VERSATILE_CLCD select POWER_RESET diff --git a/arch/arm/plat-samsung/Kconfig b/arch/arm/plat-samsung/Kconfig index b57e922f161..243dfcb2ca0 100644 --- a/arch/arm/plat-samsung/Kconfig +++ b/arch/arm/plat-samsung/Kconfig @@ -9,7 +9,7 @@ config PLAT_SAMSUNG depends on PLAT_S3C24XX || ARCH_S3C64XX || PLAT_S5P || ARCH_EXYNOS default y select GENERIC_IRQ_CHIP - select NO_IOPORT + select NO_IOPORT_MAP help Base platform code for all Samsung SoC based systems @@ -19,7 +19,7 @@ config PLAT_S5P default y select ARCH_REQUIRE_GPIOLIB select ARM_VIC - select NO_IOPORT + select NO_IOPORT_MAP select PLAT_SAMSUNG select S3C_GPIO_TRACK select S5P_GPIO_DRVSTR diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig index 9711a5fd948..8079a23e270 100644 --- a/arch/arm64/Kconfig +++ b/arch/arm64/Kconfig @@ -66,7 +66,7 @@ config ARCH_PHYS_ADDR_T_64BIT config MMU def_bool y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config STACKTRACE_SUPPORT diff --git a/arch/cris/Kconfig b/arch/cris/Kconfig index 7cb90a54b59..52731e22185 100644 --- a/arch/cris/Kconfig +++ b/arch/cris/Kconfig @@ -29,7 +29,7 @@ config GENERIC_CALIBRATE_DELAY bool default y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config FORCE_MAX_ZONEORDER diff --git a/arch/hexagon/Kconfig b/arch/hexagon/Kconfig index fbc5c78c9ac..0fd6138f620 100644 --- a/arch/hexagon/Kconfig +++ b/arch/hexagon/Kconfig @@ -19,7 +19,7 @@ config HEXAGON select GENERIC_IRQ_SHOW select HAVE_ARCH_KGDB select HAVE_ARCH_TRACEHOOK - select NO_IOPORT + select NO_IOPORT_MAP select GENERIC_IOMAP select GENERIC_SMP_IDLE_THREAD select STACKTRACE_SUPPORT diff --git a/arch/m32r/Kconfig b/arch/m32r/Kconfig index ca4504424da..9e44bbd8051 100644 --- a/arch/m32r/Kconfig +++ b/arch/m32r/Kconfig @@ -28,7 +28,7 @@ config ZONE_DMA bool default y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config NO_DMA diff --git a/arch/m68k/Kconfig b/arch/m68k/Kconfig index b2e32293925..87b7c7581b1 100644 --- a/arch/m68k/Kconfig +++ b/arch/m68k/Kconfig @@ -52,7 +52,7 @@ config TIME_LOW_RES bool default y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config NO_DMA diff --git a/arch/metag/Kconfig b/arch/metag/Kconfig index b1d3c9c0eff..499b7610eaa 100644 --- a/arch/metag/Kconfig +++ b/arch/metag/Kconfig @@ -52,7 +52,7 @@ config GENERIC_HWEIGHT config GENERIC_CALIBRATE_DELAY def_bool y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y source "init/Kconfig" diff --git a/arch/mips/Kconfig b/arch/mips/Kconfig index 16d5ab1615b..5cd695f905a 100644 --- a/arch/mips/Kconfig +++ b/arch/mips/Kconfig @@ -175,7 +175,7 @@ config MACH_DECSTATION select CPU_R4000_WORKAROUNDS if 64BIT select CPU_R4400_WORKAROUNDS if 64BIT select DMA_NONCOHERENT - select NO_IOPORT + select NO_IOPORT_MAP select IRQ_CPU select SYS_HAS_CPU_R3000 select SYS_HAS_CPU_R4X00 @@ -947,7 +947,7 @@ config SYNC_R4K config MIPS_MACHINE def_bool n -config NO_IOPORT +config NO_IOPORT_MAP def_bool n config GENERIC_ISA_DMA diff --git a/arch/openrisc/Kconfig b/arch/openrisc/Kconfig index 9488209a525..e71d712afb7 100644 --- a/arch/openrisc/Kconfig +++ b/arch/openrisc/Kconfig @@ -41,7 +41,7 @@ config RWSEM_XCHGADD_ALGORITHM config GENERIC_HWEIGHT def_bool y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config TRACE_IRQFLAGS_SUPPORT diff --git a/arch/s390/Kconfig b/arch/s390/Kconfig index 953f17c8d17..346d21678ff 100644 --- a/arch/s390/Kconfig +++ b/arch/s390/Kconfig @@ -52,7 +52,7 @@ config KEXEC config AUDIT_ARCH def_bool y -config NO_IOPORT +config NO_IOPORT_MAP def_bool y config PCI_QUIRKS diff --git a/arch/sh/Kconfig b/arch/sh/Kconfig index 1399383315a..ba55e939a82 100644 --- a/arch/sh/Kconfig +++ b/arch/sh/Kconfig @@ -3,7 +3,7 @@ config SUPERH select ARCH_MIGHT_HAVE_PC_PARPORT select EXPERT select CLKDEV_LOOKUP - select HAVE_IDE if HAS_IOPORT + select HAVE_IDE if HAS_IOPORT_MAP select HAVE_MEMBLOCK select HAVE_MEMBLOCK_NODE_MAP select ARCH_DISCARD_MEMBLOCK @@ -138,7 +138,7 @@ config ARCH_HAS_ILOG2_U32 config ARCH_HAS_ILOG2_U64 def_bool n -config NO_IOPORT +config NO_IOPORT_MAP def_bool !PCI depends on !SH_CAYMAN && !SH_SH4202_MICRODEV && !SH_SHMIN && \ !SH_HP6XX && !SH_SOLUTION_ENGINE diff --git a/arch/sh/boards/Kconfig b/arch/sh/boards/Kconfig index eb1cf84231a..e331e5373b8 100644 --- a/arch/sh/boards/Kconfig +++ b/arch/sh/boards/Kconfig @@ -158,7 +158,7 @@ config SH_SDK7786 bool "SDK7786" depends on CPU_SUBTYPE_SH7786 select SYS_SUPPORTS_PCI - select NO_IOPORT if !PCI + select NO_IOPORT_MAP if !PCI select ARCH_WANT_OPTIONAL_GPIOLIB select HAVE_SRAM_POOL select REGULATOR_FIXED_VOLTAGE if REGULATOR @@ -204,7 +204,7 @@ config SH_URQUELL depends on CPU_SUBTYPE_SH7786 select ARCH_REQUIRE_GPIOLIB select SYS_SUPPORTS_PCI - select NO_IOPORT if !PCI + select NO_IOPORT_MAP if !PCI config SH_MIGOR bool "Migo-R" @@ -306,7 +306,7 @@ config SH_LBOX_RE2 config SH_X3PROTO bool "SH-X3 Prototype board" depends on CPU_SUBTYPE_SHX3 - select NO_IOPORT if !PCI + select NO_IOPORT_MAP if !PCI select IRQ_DOMAIN config SH_MAGIC_PANEL_R2 @@ -333,7 +333,7 @@ config SH_POLARIS config SH_SH2007 bool "SH-2007 board" - select NO_IOPORT + select NO_IOPORT_MAP select REGULATOR_FIXED_VOLTAGE if REGULATOR depends on CPU_SUBTYPE_SH7780 help diff --git a/arch/sh/include/asm/io.h b/arch/sh/include/asm/io.h index 629db2ad791..728c4c571f4 100644 --- a/arch/sh/include/asm/io.h +++ b/arch/sh/include/asm/io.h @@ -122,7 +122,7 @@ __BUILD_MEMORY_STRING(__raw_, l, u32) __BUILD_MEMORY_STRING(__raw_, q, u64) -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP /* * Slowdown I/O port space accesses for antique hardware. @@ -218,7 +218,7 @@ __BUILD_IOPORT_STRING(w, u16) __BUILD_IOPORT_STRING(l, u32) __BUILD_IOPORT_STRING(q, u64) -#else /* !CONFIG_HAS_IOPORT */ +#else /* !CONFIG_HAS_IOPORT_MAP */ #include diff --git a/arch/sh/include/asm/io_trapped.h b/arch/sh/include/asm/io_trapped.h index f1251d4f0ba..4ab94ef5107 100644 --- a/arch/sh/include/asm/io_trapped.h +++ b/arch/sh/include/asm/io_trapped.h @@ -36,7 +36,7 @@ __ioremap_trapped(unsigned long offset, unsigned long size) #define __ioremap_trapped(offset, size) NULL #endif -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP extern struct list_head trapped_io; static inline void __iomem * diff --git a/arch/sh/include/asm/machvec.h b/arch/sh/include/asm/machvec.h index eb9c20d971d..d3324e4f372 100644 --- a/arch/sh/include/asm/machvec.h +++ b/arch/sh/include/asm/machvec.h @@ -21,7 +21,7 @@ struct sh_machine_vector { int (*mv_irq_demux)(int irq); void (*mv_init_irq)(void); -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP void __iomem *(*mv_ioport_map)(unsigned long port, unsigned int size); void (*mv_ioport_unmap)(void __iomem *); #endif diff --git a/arch/sh/kernel/Makefile b/arch/sh/kernel/Makefile index 261c8bfd75c..2ccf36c824c 100644 --- a/arch/sh/kernel/Makefile +++ b/arch/sh/kernel/Makefile @@ -22,7 +22,7 @@ obj-y := debugtraps.o dma-nommu.o dumpstack.o \ ifndef CONFIG_GENERIC_IOMAP obj-y += iomap.o -obj-$(CONFIG_HAS_IOPORT) += ioport.o +obj-$(CONFIG_HAS_IOPORT_MAP) += ioport.o endif obj-$(CONFIG_SUPERH32) += sys_sh32.o diff --git a/arch/sh/kernel/io_trapped.c b/arch/sh/kernel/io_trapped.c index c0a9761f2f8..f8ce36286ce 100644 --- a/arch/sh/kernel/io_trapped.c +++ b/arch/sh/kernel/io_trapped.c @@ -22,7 +22,7 @@ #define TRAPPED_PAGES_MAX 16 -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP LIST_HEAD(trapped_io); EXPORT_SYMBOL_GPL(trapped_io); #endif @@ -90,7 +90,7 @@ int register_trapped_io(struct trapped_io *tiop) tiop->magic = IO_TRAPPED_MAGIC; INIT_LIST_HEAD(&tiop->list); spin_lock_irq(&trapped_lock); -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP if (flags & IORESOURCE_IO) list_add(&tiop->list, &trapped_io); #endif diff --git a/arch/tile/Kconfig b/arch/tile/Kconfig index 31c8c622399..85258ca43ff 100644 --- a/arch/tile/Kconfig +++ b/arch/tile/Kconfig @@ -411,7 +411,7 @@ config PCI_DOMAINS config NO_IOMEM def_bool !PCI -config NO_IOPORT +config NO_IOPORT_MAP def_bool !PCI config TILE_PCI_IO diff --git a/arch/unicore32/Kconfig b/arch/unicore32/Kconfig index 25c0dba508c..aafad6fa166 100644 --- a/arch/unicore32/Kconfig +++ b/arch/unicore32/Kconfig @@ -27,7 +27,7 @@ config UNICORE32 config GENERIC_CSUM def_bool y -config NO_IOPORT +config NO_IOPORT_MAP bool config STACKTRACE_SUPPORT diff --git a/arch/xtensa/Kconfig b/arch/xtensa/Kconfig index c87ae7c6e5f..02d6d29a63c 100644 --- a/arch/xtensa/Kconfig +++ b/arch/xtensa/Kconfig @@ -41,7 +41,7 @@ config ARCH_HAS_ILOG2_U32 config ARCH_HAS_ILOG2_U64 def_bool n -config NO_IOPORT +config NO_IOPORT_MAP def_bool n config HZ @@ -239,7 +239,7 @@ config XTENSA_PLATFORM_XT2000 config XTENSA_PLATFORM_S6105 bool "S6105" select SERIAL_CONSOLE - select NO_IOPORT + select NO_IOPORT_MAP config XTENSA_PLATFORM_XTFPGA bool "XTFPGA" diff --git a/arch/xtensa/configs/iss_defconfig b/arch/xtensa/configs/iss_defconfig index 4f233204faf..d57d917ff24 100644 --- a/arch/xtensa/configs/iss_defconfig +++ b/arch/xtensa/configs/iss_defconfig @@ -11,7 +11,7 @@ CONFIG_GENERIC_FIND_NEXT_BIT=y CONFIG_GENERIC_HWEIGHT=y # CONFIG_ARCH_HAS_ILOG2_U32 is not set # CONFIG_ARCH_HAS_ILOG2_U64 is not set -CONFIG_NO_IOPORT=y +CONFIG_NO_IOPORT_MAP=y CONFIG_HZ=100 CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" CONFIG_CONSTRUCTORS=y diff --git a/arch/xtensa/configs/s6105_defconfig b/arch/xtensa/configs/s6105_defconfig index d929f77a036..583c2b0974c 100644 --- a/arch/xtensa/configs/s6105_defconfig +++ b/arch/xtensa/configs/s6105_defconfig @@ -11,7 +11,7 @@ CONFIG_GENERIC_FIND_NEXT_BIT=y CONFIG_GENERIC_HWEIGHT=y # CONFIG_ARCH_HAS_ILOG2_U32 is not set # CONFIG_ARCH_HAS_ILOG2_U64 is not set -CONFIG_NO_IOPORT=y +CONFIG_NO_IOPORT_MAP=y CONFIG_HZ=100 CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config" diff --git a/drivers/char/tpm/Kconfig b/drivers/char/tpm/Kconfig index 1a65838888c..c54cac3f8bc 100644 --- a/drivers/char/tpm/Kconfig +++ b/drivers/char/tpm/Kconfig @@ -74,7 +74,7 @@ config TCG_NSC config TCG_ATMEL tristate "Atmel TPM Interface" - depends on PPC64 || HAS_IOPORT + depends on PPC64 || HAS_IOPORT_MAP ---help--- If you have a TPM security chip from Atmel say Yes and it will be accessible from within Linux. To compile this driver diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index de17c5593d9..014afab1d55 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig @@ -936,7 +936,7 @@ config I2C_ACORN config I2C_ELEKTOR tristate "Elektor ISA card" - depends on ISA && HAS_IOPORT && BROKEN_ON_SMP + depends on ISA && HAS_IOPORT_MAP && BROKEN_ON_SMP select I2C_ALGOPCF help This supports the PCF8584 ISA bus I2C adapter. Say Y if you own diff --git a/drivers/net/can/sja1000/Kconfig b/drivers/net/can/sja1000/Kconfig index 4b18b876552..1e65cb6c259 100644 --- a/drivers/net/can/sja1000/Kconfig +++ b/drivers/net/can/sja1000/Kconfig @@ -39,7 +39,7 @@ config CAN_EMS_PCI config CAN_PEAK_PCMCIA tristate "PEAK PCAN-PC Card" depends on PCMCIA - depends on HAS_IOPORT + depends on HAS_IOPORT_MAP ---help--- This driver is for the PCAN-PC Card PCMCIA adapter (1 or 2 channels) from PEAK-System (http://www.peak-system.com). To compile this diff --git a/drivers/net/ethernet/3com/Kconfig b/drivers/net/ethernet/3com/Kconfig index 65b735d4a6a..afaab4b2333 100644 --- a/drivers/net/ethernet/3com/Kconfig +++ b/drivers/net/ethernet/3com/Kconfig @@ -66,7 +66,7 @@ config PCMCIA_3C589 config VORTEX tristate "3c590/3c900 series (592/595/597) \"Vortex/Boomerang\" support" - depends on (PCI || EISA) && HAS_IOPORT + depends on (PCI || EISA) && HAS_IOPORT_MAP select MII ---help--- This option enables driver support for a large number of 10Mbps and diff --git a/include/asm-generic/io.h b/include/asm-generic/io.h index d5afe96adba..975e1cc75ed 100644 --- a/include/asm-generic/io.h +++ b/include/asm-generic/io.h @@ -327,7 +327,7 @@ static inline void iounmap(void __iomem *addr) } #endif /* CONFIG_MMU */ -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP #ifndef CONFIG_GENERIC_IOMAP static inline void __iomem *ioport_map(unsigned long port, unsigned int nr) { @@ -341,7 +341,7 @@ static inline void ioport_unmap(void __iomem *p) extern void __iomem *ioport_map(unsigned long port, unsigned int nr); extern void ioport_unmap(void __iomem *p); #endif /* CONFIG_GENERIC_IOMAP */ -#endif /* CONFIG_HAS_IOPORT */ +#endif /* CONFIG_HAS_IOPORT_MAP */ #ifndef xlate_dev_kmem_ptr #define xlate_dev_kmem_ptr(p) p diff --git a/include/asm-generic/iomap.h b/include/asm-generic/iomap.h index 6afd7d6a989..1b41011643a 100644 --- a/include/asm-generic/iomap.h +++ b/include/asm-generic/iomap.h @@ -56,7 +56,7 @@ extern void iowrite8_rep(void __iomem *port, const void *buf, unsigned long coun extern void iowrite16_rep(void __iomem *port, const void *buf, unsigned long count); extern void iowrite32_rep(void __iomem *port, const void *buf, unsigned long count); -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP /* Create a virtual mapping cookie for an IO port range */ extern void __iomem *ioport_map(unsigned long port, unsigned int nr); extern void ioport_unmap(void __iomem *); diff --git a/include/linux/io.h b/include/linux/io.h index 8a18e75600c..b76e6e54580 100644 --- a/include/linux/io.h +++ b/include/linux/io.h @@ -41,7 +41,7 @@ static inline int ioremap_page_range(unsigned long addr, unsigned long end, /* * Managed iomap interface */ -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP void __iomem * devm_ioport_map(struct device *dev, unsigned long port, unsigned int nr); void devm_ioport_unmap(struct device *dev, void __iomem *addr); diff --git a/lib/Kconfig b/lib/Kconfig index 991c98bc4a3..5d4984c505f 100644 --- a/lib/Kconfig +++ b/lib/Kconfig @@ -342,9 +342,9 @@ config HAS_IOMEM select GENERIC_IO default y -config HAS_IOPORT +config HAS_IOPORT_MAP boolean - depends on HAS_IOMEM && !NO_IOPORT + depends on HAS_IOMEM && !NO_IOPORT_MAP default y config HAS_DMA diff --git a/lib/devres.c b/lib/devres.c index 48cb3c7bd7d..2f16c133fd3 100644 --- a/lib/devres.c +++ b/lib/devres.c @@ -170,7 +170,7 @@ void __iomem *devm_request_and_ioremap(struct device *device, } EXPORT_SYMBOL(devm_request_and_ioremap); -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP /* * Generic iomap devres */ @@ -229,7 +229,7 @@ void devm_ioport_unmap(struct device *dev, void __iomem *addr) devm_ioport_map_match, (__force void *)addr)); } EXPORT_SYMBOL(devm_ioport_unmap); -#endif /* CONFIG_HAS_IOPORT */ +#endif /* CONFIG_HAS_IOPORT_MAP */ #ifdef CONFIG_PCI /* diff --git a/lib/iomap.c b/lib/iomap.c index 2c08f36862e..fc3dcb4b238 100644 --- a/lib/iomap.c +++ b/lib/iomap.c @@ -224,7 +224,7 @@ EXPORT_SYMBOL(iowrite8_rep); EXPORT_SYMBOL(iowrite16_rep); EXPORT_SYMBOL(iowrite32_rep); -#ifdef CONFIG_HAS_IOPORT +#ifdef CONFIG_HAS_IOPORT_MAP /* Create a virtual mapping cookie for an IO port range */ void __iomem *ioport_map(unsigned long port, unsigned int nr) { @@ -239,7 +239,7 @@ void ioport_unmap(void __iomem *addr) } EXPORT_SYMBOL(ioport_map); EXPORT_SYMBOL(ioport_unmap); -#endif /* CONFIG_HAS_IOPORT */ +#endif /* CONFIG_HAS_IOPORT_MAP */ #ifdef CONFIG_PCI /* Hide the details if this is a MMIO or PIO address space and just do what diff --git a/sound/isa/Kconfig b/sound/isa/Kconfig index affa1348065..0216475fc75 100644 --- a/sound/isa/Kconfig +++ b/sound/isa/Kconfig @@ -191,7 +191,7 @@ config SND_ES18XX config SND_SC6000 tristate "Gallant SC-6000/6600/7000 and Audio Excel DSP 16" - depends on HAS_IOPORT + depends on HAS_IOPORT_MAP select SND_WSS_LIB select SND_OPL3_LIB select SND_MPU401_UART diff --git a/sound/pci/Kconfig b/sound/pci/Kconfig index 0b0c0cf13f7..3a3a3a71088 100644 --- a/sound/pci/Kconfig +++ b/sound/pci/Kconfig @@ -688,7 +688,7 @@ config SND_LOLA config SND_LX6464ES tristate "Digigram LX6464ES" - depends on HAS_IOPORT + depends on HAS_IOPORT_MAP select SND_PCM help Say Y here to include support for Digigram LX6464ES boards. -- cgit v1.2.3-70-g09d2 From eb4a5346e777784f1b5ae9fd0c29b96344bdc3ae Mon Sep 17 00:00:00 2001 From: Matt Porter Date: Thu, 10 Apr 2014 15:22:10 -0400 Subject: hwrng: bcm2835 - fix oops when rng h/w is accessed during registration Commit "d9e7972 hwrng: add randomness to system from rng sources" exposed a bug in the bcm2835-rng driver resulting in boot failure on Raspberry Pi due to the following oops: [ 28.261523] BUG: soft lockup - CPU#0 stuck for 23s! [swapper:1] [ 28.271058] [ 28.275958] CPU: 0 PID: 1 Comm: swapper Not tainted 3.14.0+ #11 [ 28.285374] task: db480000 ti: db484000 task.ti: db484000 [ 28.294279] PC is at bcm2835_rng_read+0x28/0x48 [ 28.302276] LR is at hwrng_register+0x1a8/0x238 . . . The RNG h/w is not completely initialized and enabled before hwrng_register() is called and so the bcm2835_rng_read() fails. Fix this by making the warmup/enable writes before registering the RNG source with the hwrng core. Signed-off-by: Matt Porter Signed-off-by: Herbert Xu --- drivers/char/hw_random/bcm2835-rng.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/hw_random/bcm2835-rng.c b/drivers/char/hw_random/bcm2835-rng.c index 8c3b255e629..e900961cdd2 100644 --- a/drivers/char/hw_random/bcm2835-rng.c +++ b/drivers/char/hw_random/bcm2835-rng.c @@ -61,18 +61,18 @@ static int bcm2835_rng_probe(struct platform_device *pdev) } bcm2835_rng_ops.priv = (unsigned long)rng_base; + /* set warm-up count & enable */ + __raw_writel(RNG_WARMUP_COUNT, rng_base + RNG_STATUS); + __raw_writel(RNG_RBGEN, rng_base + RNG_CTRL); + /* register driver */ err = hwrng_register(&bcm2835_rng_ops); if (err) { dev_err(dev, "hwrng registration failed\n"); iounmap(rng_base); - } else { + } else dev_info(dev, "hwrng registered\n"); - /* set warm-up count & enable */ - __raw_writel(RNG_WARMUP_COUNT, rng_base + RNG_STATUS); - __raw_writel(RNG_RBGEN, rng_base + RNG_CTRL); - } return err; } -- cgit v1.2.3-70-g09d2 From 7d1c2858c49095ab748f55354b89dbd6b18d28b9 Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 2 Apr 2014 14:45:21 +0200 Subject: ttyprintk: Fix wrong tty_unregister_driver() call in the error path ttyprintk driver calls tty_unregister_driver() wrongly in the error path of tty_register_driver(). Also, setting ttyprintk_driver to NULL is utterly superfluous, so let's get rid of it, too. Reported-by: Jean Delvare Reviewed-by: Jean Delvare Signed-off-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/char/ttyprintk.c | 2 -- 1 file changed, 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/ttyprintk.c b/drivers/char/ttyprintk.c index daea84c4174..2a39c579036 100644 --- a/drivers/char/ttyprintk.c +++ b/drivers/char/ttyprintk.c @@ -210,10 +210,8 @@ static int __init ttyprintk_init(void) return 0; error: - tty_unregister_driver(ttyprintk_driver); put_tty_driver(ttyprintk_driver); tty_port_destroy(&tpk_port.port); - ttyprintk_driver = NULL; return ret; } device_initcall(ttyprintk_init); -- cgit v1.2.3-70-g09d2 From b24313a82cf24e90170671ea74360b3e6ef3a91f Mon Sep 17 00:00:00 2001 From: Takashi Iwai Date: Wed, 2 Apr 2014 14:45:22 +0200 Subject: ttyprintk: Allow built as a module The driver is well written to be used as a module, just the exit call is missing. Reviewed-by: Jean Delvare Signed-off-by: Takashi Iwai Signed-off-by: Greg Kroah-Hartman --- drivers/char/Kconfig | 2 +- drivers/char/ttyprintk.c | 13 ++++++++++++- 2 files changed, 13 insertions(+), 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/Kconfig b/drivers/char/Kconfig index fbae63e3d30..6e9f74a5c09 100644 --- a/drivers/char/Kconfig +++ b/drivers/char/Kconfig @@ -40,7 +40,7 @@ config SGI_MBCS source "drivers/tty/serial/Kconfig" config TTY_PRINTK - bool "TTY driver to output user messages via printk" + tristate "TTY driver to output user messages via printk" depends on EXPERT && TTY default n ---help--- diff --git a/drivers/char/ttyprintk.c b/drivers/char/ttyprintk.c index 2a39c579036..a15ce4ef39c 100644 --- a/drivers/char/ttyprintk.c +++ b/drivers/char/ttyprintk.c @@ -17,7 +17,7 @@ #include #include #include -#include +#include struct ttyprintk_port { struct tty_port port; @@ -214,4 +214,15 @@ error: tty_port_destroy(&tpk_port.port); return ret; } + +static void __exit ttyprintk_exit(void) +{ + tty_unregister_driver(ttyprintk_driver); + put_tty_driver(ttyprintk_driver); + tty_port_destroy(&tpk_port.port); +} + device_initcall(ttyprintk_init); +module_exit(ttyprintk_exit); + +MODULE_LICENSE("GPL"); -- cgit v1.2.3-70-g09d2 From 9ca83fd2d5805a5e4608a901ffa802697adc638b Mon Sep 17 00:00:00 2001 From: Jean Delvare Date: Mon, 14 Apr 2014 18:32:13 +0200 Subject: tty: Fix help text of SYNCLINK_CS Enabling SYNCLINK_CS as a module builds synclink_cs, not synclinkmp. Signed-off-by: Jean Delvare Signed-off-by: Greg Kroah-Hartman --- drivers/char/pcmcia/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/char') diff --git a/drivers/char/pcmcia/Kconfig b/drivers/char/pcmcia/Kconfig index b27f5342fe7..8d3dfb0c8a2 100644 --- a/drivers/char/pcmcia/Kconfig +++ b/drivers/char/pcmcia/Kconfig @@ -15,7 +15,7 @@ config SYNCLINK_CS This driver may be built as a module ( = code which can be inserted in and removed from the running kernel whenever you want). - The module will be called synclinkmp. If you want to do that, say M + The module will be called synclink_cs. If you want to do that, say M here. config CARDMAN_4000 -- cgit v1.2.3-70-g09d2 From a94cdd1f4d30f12904ab528152731fb13a812a16 Mon Sep 17 00:00:00 2001 From: Jiri Slaby Date: Mon, 14 Apr 2014 09:46:50 -0500 Subject: Char: ipmi_bt_sm, fix infinite loop In read_all_bytes, we do unsigned char i; ... bt->read_data[0] = BMC2HOST; bt->read_count = bt->read_data[0]; ... for (i = 1; i <= bt->read_count; i++) bt->read_data[i] = BMC2HOST; If bt->read_data[0] == bt->read_count == 255, we loop infinitely in the 'for' loop. Make 'i' an 'int' instead of 'char' to get rid of the overflow and finish the loop after 255 iterations every time. Signed-off-by: Jiri Slaby Reported-and-debugged-by: Rui Hui Dian Cc: Tomas Cech Cc: Corey Minyard Cc: Signed-off-by: Corey Minyard Signed-off-by: Linus Torvalds --- drivers/char/ipmi/ipmi_bt_sm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/ipmi_bt_sm.c b/drivers/char/ipmi/ipmi_bt_sm.c index f5e4cd7617f..61e71616689 100644 --- a/drivers/char/ipmi/ipmi_bt_sm.c +++ b/drivers/char/ipmi/ipmi_bt_sm.c @@ -352,7 +352,7 @@ static inline void write_all_bytes(struct si_sm_data *bt) static inline int read_all_bytes(struct si_sm_data *bt) { - unsigned char i; + unsigned int i; /* * length is "framing info", minimum = 4: NetFn, Seq, Cmd, cCode. -- cgit v1.2.3-70-g09d2 From 48e8ac2979920ffa39117e2d725afa3a749bfe8d Mon Sep 17 00:00:00 2001 From: Bodo Stroesser Date: Mon, 14 Apr 2014 09:46:51 -0500 Subject: ipmi: Fix a race restarting the timer With recent changes it is possible for the timer handler to detect an idle interface and not start the timer, but the thread to start an operation at the same time. The thread will not start the timer in that instance, resulting in the timer not running. Instead, move all timer operations under the lock and start the timer in the thread if it detect non-idle and the timer is not already running. Moving under locks allows the last timeout to be set in both the thread and the timer. 'Timer is not running' means that the timer is not pending and smi_timeout() is not running. So we need a flag to detect this correctly. Also fix a few other timeout bugs: setting the last timeout when the interrupt has to be disabled and the timer started, and setting the last timeout in check_start_timer_thread possibly racing with the timer Signed-off-by: Corey Minyard Signed-off-by: Bodo Stroesser Signed-off-by: Linus Torvalds --- drivers/char/ipmi/ipmi_si_intf.c | 46 ++++++++++++++++++++++++---------------- 1 file changed, 28 insertions(+), 18 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c index b7efd3c1a88..9c406915195 100644 --- a/drivers/char/ipmi/ipmi_si_intf.c +++ b/drivers/char/ipmi/ipmi_si_intf.c @@ -248,6 +248,9 @@ struct smi_info { /* The timer for this si. */ struct timer_list si_timer; + /* This flag is set, if the timer is running (timer_pending() isn't enough) */ + bool timer_running; + /* The time (in jiffies) the last timeout occurred at. */ unsigned long last_timeout_jiffies; @@ -434,6 +437,13 @@ static void start_clear_flags(struct smi_info *smi_info) smi_info->si_state = SI_CLEARING_FLAGS; } +static void smi_mod_timer(struct smi_info *smi_info, unsigned long new_val) +{ + smi_info->last_timeout_jiffies = jiffies; + mod_timer(&smi_info->si_timer, new_val); + smi_info->timer_running = true; +} + /* * When we have a situtaion where we run out of memory and cannot * allocate messages, we just leave them in the BMC and run the system @@ -446,8 +456,7 @@ static inline void disable_si_irq(struct smi_info *smi_info) start_disable_irq(smi_info); smi_info->interrupt_disabled = 1; if (!atomic_read(&smi_info->stop_operation)) - mod_timer(&smi_info->si_timer, - jiffies + SI_TIMEOUT_JIFFIES); + smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); } } @@ -907,15 +916,7 @@ static void sender(void *send_info, list_add_tail(&msg->link, &smi_info->xmit_msgs); if (smi_info->si_state == SI_NORMAL && smi_info->curr_msg == NULL) { - /* - * last_timeout_jiffies is updated here to avoid - * smi_timeout() handler passing very large time_diff - * value to smi_event_handler() that causes - * the send command to abort. - */ - smi_info->last_timeout_jiffies = jiffies; - - mod_timer(&smi_info->si_timer, jiffies + SI_TIMEOUT_JIFFIES); + smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); if (smi_info->thread) wake_up_process(smi_info->thread); @@ -1004,6 +1005,17 @@ static int ipmi_thread(void *data) spin_lock_irqsave(&(smi_info->si_lock), flags); smi_result = smi_event_handler(smi_info, 0); + + /* + * If the driver is doing something, there is a possible + * race with the timer. If the timer handler see idle, + * and the thread here sees something else, the timer + * handler won't restart the timer even though it is + * required. So start it here if necessary. + */ + if (smi_result != SI_SM_IDLE && !smi_info->timer_running) + smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); + spin_unlock_irqrestore(&(smi_info->si_lock), flags); busy_wait = ipmi_thread_busy_wait(smi_result, smi_info, &busy_until); @@ -1073,10 +1085,6 @@ static void smi_timeout(unsigned long data) * SI_USEC_PER_JIFFY); smi_result = smi_event_handler(smi_info, time_diff); - spin_unlock_irqrestore(&(smi_info->si_lock), flags); - - smi_info->last_timeout_jiffies = jiffies_now; - if ((smi_info->irq) && (!smi_info->interrupt_disabled)) { /* Running with interrupts, only do long timeouts. */ timeout = jiffies + SI_TIMEOUT_JIFFIES; @@ -1098,7 +1106,10 @@ static void smi_timeout(unsigned long data) do_mod_timer: if (smi_result != SI_SM_IDLE) - mod_timer(&(smi_info->si_timer), timeout); + smi_mod_timer(smi_info, timeout); + else + smi_info->timer_running = false; + spin_unlock_irqrestore(&(smi_info->si_lock), flags); } static irqreturn_t si_irq_handler(int irq, void *data) @@ -1146,8 +1157,7 @@ static int smi_start_processing(void *send_info, /* Set up the timer that drives the interface. */ setup_timer(&new_smi->si_timer, smi_timeout, (long)new_smi); - new_smi->last_timeout_jiffies = jiffies; - mod_timer(&new_smi->si_timer, jiffies + SI_TIMEOUT_JIFFIES); + smi_mod_timer(new_smi, jiffies + SI_TIMEOUT_JIFFIES); /* * Check if the user forcefully enabled the daemon. -- cgit v1.2.3-70-g09d2 From eb6d78ec213e6938559b801421d64714dafcf4b2 Mon Sep 17 00:00:00 2001 From: Corey Minyard Date: Mon, 14 Apr 2014 09:46:52 -0500 Subject: ipmi: Reset the KCS timeout when starting error recovery The OBF timer in KCS was not reset in one situation when error recovery was started, resulting in an immediate timeout. Reported-by: Bodo Stroesser Signed-off-by: Corey Minyard Signed-off-by: Linus Torvalds --- drivers/char/ipmi/ipmi_kcs_sm.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/ipmi_kcs_sm.c b/drivers/char/ipmi/ipmi_kcs_sm.c index 6a4bdc18955..8c25f596808 100644 --- a/drivers/char/ipmi/ipmi_kcs_sm.c +++ b/drivers/char/ipmi/ipmi_kcs_sm.c @@ -251,8 +251,9 @@ static inline int check_obf(struct si_sm_data *kcs, unsigned char status, if (!GET_STATUS_OBF(status)) { kcs->obf_timeout -= time; if (kcs->obf_timeout < 0) { - start_error_recovery(kcs, "OBF not ready in time"); - return 1; + kcs->obf_timeout = OBF_RETRY_TIMEOUT; + start_error_recovery(kcs, "OBF not ready in time"); + return 1; } return 0; } -- cgit v1.2.3-70-g09d2 From 0dfe6e7ed47feeb22f3cf8c7d8ac7e65bd4e87f5 Mon Sep 17 00:00:00 2001 From: Corey Minyard Date: Mon, 14 Apr 2014 09:46:53 -0500 Subject: ipmi: Turn off default probing of interfaces The default probing can cause problems with some system, slow booting, extra CPU usages, etc. Turn it off by default and give a config option to enable it. From: Matthew Garrett Signed-off-by: Corey Minyard Signed-off-by: Linus Torvalds --- drivers/char/ipmi/Kconfig | 12 ++++++++++++ drivers/char/ipmi/ipmi_si_intf.c | 2 +- 2 files changed, 13 insertions(+), 1 deletion(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/Kconfig b/drivers/char/ipmi/Kconfig index 0baa8fab4ea..db1c9b7adaa 100644 --- a/drivers/char/ipmi/Kconfig +++ b/drivers/char/ipmi/Kconfig @@ -50,6 +50,18 @@ config IPMI_SI Currently, only KCS and SMIC are supported. If you are using IPMI, you should probably say "y" here. +config IPMI_SI_PROBE_DEFAULTS + bool 'Probe for all possible IPMI system interfaces by default' + default n + depends on IPMI_SI + help + Modern systems will usually expose IPMI interfaces via a discoverable + firmware mechanism such as ACPI or DMI. Older systems do not, and so + the driver is forced to probe hardware manually. This may cause boot + delays. Say "n" here to disable this manual probing. IPMI will then + only be available on older systems if the "ipmi_si_intf.trydefaults=1" + boot argument is passed. + config IPMI_WATCHDOG tristate 'IPMI Watchdog Timer' help diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c index 9c406915195..25a1436a429 100644 --- a/drivers/char/ipmi/ipmi_si_intf.c +++ b/drivers/char/ipmi/ipmi_si_intf.c @@ -1239,7 +1239,7 @@ static bool si_tryplatform = 1; #ifdef CONFIG_PCI static bool si_trypci = 1; #endif -static bool si_trydefaults = 1; +static bool si_trydefaults = IS_ENABLED(CONFIG_IPMI_SI_PROBE_DEFAULTS); static char *si_type[SI_MAX_PARMS]; #define MAX_SI_TYPE_STR 30 static char si_type_str[MAX_SI_TYPE_STR]; -- cgit v1.2.3-70-g09d2 From 89986496de141213206d49450ffdd36098d41209 Mon Sep 17 00:00:00 2001 From: Corey Minyard Date: Mon, 14 Apr 2014 09:46:54 -0500 Subject: ipmi: Turn off all activity on an idle ipmi interface The IPMI driver would wake up periodically looking for events and watchdog pretimeouts. If there is nothing waiting for these events, it's really kind of pointless to be checking for them. So modify the driver so the message handler can pass down if it needs the lower layer to be waiting for these. Modify the system interface lower layer to turn off all timer and thread activity if the upper layer doesn't need anything and it is not currently handling messages. And modify the message handler to not restart the timer if its timer is not needed. The timers and kthread will still be enabled if: - the SI interface is handling a message. - a user has enabled watching for events. - the IPMI watchdog timer is in use (since it uses pretimeouts). - the message handler is waiting on a remote response. - a user has registered to receive commands. This mostly affects interfaces without interrupts. Interfaces with interrupts already don't use CPU in the system interface when the interface is idle. Signed-off-by: Corey Minyard Signed-off-by: Linus Torvalds --- drivers/char/ipmi/ipmi_msghandler.c | 219 ++++++++++++++++++++++-------------- drivers/char/ipmi/ipmi_si_intf.c | 51 +++++++-- include/linux/ipmi.h | 2 +- include/linux/ipmi_smi.h | 7 ++ 4 files changed, 182 insertions(+), 97 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/ipmi_msghandler.c b/drivers/char/ipmi/ipmi_msghandler.c index ec4e10fcf1a..872c4ec79bf 100644 --- a/drivers/char/ipmi/ipmi_msghandler.c +++ b/drivers/char/ipmi/ipmi_msghandler.c @@ -55,6 +55,7 @@ static struct ipmi_recv_msg *ipmi_alloc_recv_msg(void); static int ipmi_init_msghandler(void); static void smi_recv_tasklet(unsigned long); static void handle_new_recv_msgs(ipmi_smi_t intf); +static void need_waiter(ipmi_smi_t intf); static int initialized; @@ -73,6 +74,20 @@ static struct proc_dir_entry *proc_ipmi_root; */ #define MAX_MSG_TIMEOUT 60000 +/* Call every ~1000 ms. */ +#define IPMI_TIMEOUT_TIME 1000 + +/* How many jiffies does it take to get to the timeout time. */ +#define IPMI_TIMEOUT_JIFFIES ((IPMI_TIMEOUT_TIME * HZ) / 1000) + +/* + * Request events from the queue every second (this is the number of + * IPMI_TIMEOUT_TIMES between event requests). Hopefully, in the + * future, IPMI will add a way to know immediately if an event is in + * the queue and this silliness can go away. + */ +#define IPMI_REQUEST_EV_TIME (1000 / (IPMI_TIMEOUT_TIME)) + /* * The main "user" data structure. */ @@ -92,7 +107,7 @@ struct ipmi_user { ipmi_smi_t intf; /* Does this interface receive IPMI events? */ - int gets_events; + bool gets_events; }; struct cmd_rcvr { @@ -383,6 +398,9 @@ struct ipmi_smi { unsigned int waiting_events_count; /* How many events in queue? */ char delivering_events; char event_msg_printed; + atomic_t event_waiters; + unsigned int ticks_to_req_ev; + int last_needs_timer; /* * The event receiver for my BMC, only really used at panic @@ -451,7 +469,6 @@ static DEFINE_MUTEX(ipmi_interfaces_mutex); static LIST_HEAD(smi_watchers); static DEFINE_MUTEX(smi_watchers_mutex); - #define ipmi_inc_stat(intf, stat) \ atomic_inc(&(intf)->stats[IPMI_STAT_ ## stat]) #define ipmi_get_stat(intf, stat) \ @@ -772,6 +789,7 @@ static int intf_next_seq(ipmi_smi_t intf, *seq = i; *seqid = intf->seq_table[i].seqid; intf->curr_seq = (i+1)%IPMI_IPMB_NUM_SEQ; + need_waiter(intf); } else { rv = -EAGAIN; } @@ -941,7 +959,7 @@ int ipmi_create_user(unsigned int if_num, new_user->handler = handler; new_user->handler_data = handler_data; new_user->intf = intf; - new_user->gets_events = 0; + new_user->gets_events = false; if (!try_module_get(intf->handlers->owner)) { rv = -ENODEV; @@ -966,6 +984,11 @@ int ipmi_create_user(unsigned int if_num, spin_lock_irqsave(&intf->seq_lock, flags); list_add_rcu(&new_user->link, &intf->users); spin_unlock_irqrestore(&intf->seq_lock, flags); + if (handler->ipmi_watchdog_pretimeout) { + /* User wants pretimeouts, so make sure to watch for them. */ + if (atomic_inc_return(&intf->event_waiters) == 1) + need_waiter(intf); + } *user = new_user; return 0; @@ -1021,6 +1044,12 @@ int ipmi_destroy_user(ipmi_user_t user) user->valid = 0; + if (user->handler->ipmi_watchdog_pretimeout) + atomic_dec(&intf->event_waiters); + + if (user->gets_events) + atomic_dec(&intf->event_waiters); + /* Remove the user from the interface's sequence table. */ spin_lock_irqsave(&intf->seq_lock, flags); list_del_rcu(&user->link); @@ -1184,7 +1213,7 @@ int ipmi_set_maintenance_mode(ipmi_user_t user, int mode) } EXPORT_SYMBOL(ipmi_set_maintenance_mode); -int ipmi_set_gets_events(ipmi_user_t user, int val) +int ipmi_set_gets_events(ipmi_user_t user, bool val) { unsigned long flags; ipmi_smi_t intf = user->intf; @@ -1194,8 +1223,18 @@ int ipmi_set_gets_events(ipmi_user_t user, int val) INIT_LIST_HEAD(&msgs); spin_lock_irqsave(&intf->events_lock, flags); + if (user->gets_events == val) + goto out; + user->gets_events = val; + if (val) { + if (atomic_inc_return(&intf->event_waiters) == 1) + need_waiter(intf); + } else { + atomic_dec(&intf->event_waiters); + } + if (intf->delivering_events) /* * Another thread is delivering events for this, so @@ -1289,6 +1328,9 @@ int ipmi_register_for_cmd(ipmi_user_t user, goto out_unlock; } + if (atomic_inc_return(&intf->event_waiters) == 1) + need_waiter(intf); + list_add_rcu(&rcvr->link, &intf->cmd_rcvrs); out_unlock: @@ -1330,6 +1372,7 @@ int ipmi_unregister_for_cmd(ipmi_user_t user, mutex_unlock(&intf->cmd_rcvrs_mutex); synchronize_rcu(); while (rcvrs) { + atomic_dec(&intf->event_waiters); rcvr = rcvrs; rcvrs = rcvr->next; kfree(rcvr); @@ -2876,6 +2919,8 @@ int ipmi_register_smi(struct ipmi_smi_handlers *handlers, (unsigned long) intf); atomic_set(&intf->watchdog_pretimeouts_to_deliver, 0); spin_lock_init(&intf->events_lock); + atomic_set(&intf->event_waiters, 0); + intf->ticks_to_req_ev = IPMI_REQUEST_EV_TIME; INIT_LIST_HEAD(&intf->waiting_events); intf->waiting_events_count = 0; mutex_init(&intf->cmd_rcvrs_mutex); @@ -3965,7 +4010,8 @@ smi_from_recv_msg(ipmi_smi_t intf, struct ipmi_recv_msg *recv_msg, static void check_msg_timeout(ipmi_smi_t intf, struct seq_table *ent, struct list_head *timeouts, long timeout_period, - int slot, unsigned long *flags) + int slot, unsigned long *flags, + unsigned int *waiting_msgs) { struct ipmi_recv_msg *msg; struct ipmi_smi_handlers *handlers; @@ -3977,8 +4023,10 @@ static void check_msg_timeout(ipmi_smi_t intf, struct seq_table *ent, return; ent->timeout -= timeout_period; - if (ent->timeout > 0) + if (ent->timeout > 0) { + (*waiting_msgs)++; return; + } if (ent->retries_left == 0) { /* The message has used all its retries. */ @@ -3995,6 +4043,8 @@ static void check_msg_timeout(ipmi_smi_t intf, struct seq_table *ent, struct ipmi_smi_msg *smi_msg; /* More retries, send again. */ + (*waiting_msgs)++; + /* * Start with the max timer, set to normal timer after * the message is sent. @@ -4040,117 +4090,118 @@ static void check_msg_timeout(ipmi_smi_t intf, struct seq_table *ent, } } -static void ipmi_timeout_handler(long timeout_period) +static unsigned int ipmi_timeout_handler(ipmi_smi_t intf, long timeout_period) { - ipmi_smi_t intf; struct list_head timeouts; struct ipmi_recv_msg *msg, *msg2; unsigned long flags; int i; + unsigned int waiting_msgs = 0; - rcu_read_lock(); - list_for_each_entry_rcu(intf, &ipmi_interfaces, link) { - tasklet_schedule(&intf->recv_tasklet); - - /* - * Go through the seq table and find any messages that - * have timed out, putting them in the timeouts - * list. - */ - INIT_LIST_HEAD(&timeouts); - spin_lock_irqsave(&intf->seq_lock, flags); - for (i = 0; i < IPMI_IPMB_NUM_SEQ; i++) - check_msg_timeout(intf, &(intf->seq_table[i]), - &timeouts, timeout_period, i, - &flags); - spin_unlock_irqrestore(&intf->seq_lock, flags); + /* + * Go through the seq table and find any messages that + * have timed out, putting them in the timeouts + * list. + */ + INIT_LIST_HEAD(&timeouts); + spin_lock_irqsave(&intf->seq_lock, flags); + for (i = 0; i < IPMI_IPMB_NUM_SEQ; i++) + check_msg_timeout(intf, &(intf->seq_table[i]), + &timeouts, timeout_period, i, + &flags, &waiting_msgs); + spin_unlock_irqrestore(&intf->seq_lock, flags); - list_for_each_entry_safe(msg, msg2, &timeouts, link) - deliver_err_response(msg, IPMI_TIMEOUT_COMPLETION_CODE); + list_for_each_entry_safe(msg, msg2, &timeouts, link) + deliver_err_response(msg, IPMI_TIMEOUT_COMPLETION_CODE); - /* - * Maintenance mode handling. Check the timeout - * optimistically before we claim the lock. It may - * mean a timeout gets missed occasionally, but that - * only means the timeout gets extended by one period - * in that case. No big deal, and it avoids the lock - * most of the time. - */ + /* + * Maintenance mode handling. Check the timeout + * optimistically before we claim the lock. It may + * mean a timeout gets missed occasionally, but that + * only means the timeout gets extended by one period + * in that case. No big deal, and it avoids the lock + * most of the time. + */ + if (intf->auto_maintenance_timeout > 0) { + spin_lock_irqsave(&intf->maintenance_mode_lock, flags); if (intf->auto_maintenance_timeout > 0) { - spin_lock_irqsave(&intf->maintenance_mode_lock, flags); - if (intf->auto_maintenance_timeout > 0) { - intf->auto_maintenance_timeout - -= timeout_period; - if (!intf->maintenance_mode - && (intf->auto_maintenance_timeout <= 0)) { - intf->maintenance_mode_enable = 0; - maintenance_mode_update(intf); - } + intf->auto_maintenance_timeout + -= timeout_period; + if (!intf->maintenance_mode + && (intf->auto_maintenance_timeout <= 0)) { + intf->maintenance_mode_enable = 0; + maintenance_mode_update(intf); } - spin_unlock_irqrestore(&intf->maintenance_mode_lock, - flags); } + spin_unlock_irqrestore(&intf->maintenance_mode_lock, + flags); } - rcu_read_unlock(); + + tasklet_schedule(&intf->recv_tasklet); + + return waiting_msgs; } -static void ipmi_request_event(void) +static void ipmi_request_event(ipmi_smi_t intf) { - ipmi_smi_t intf; struct ipmi_smi_handlers *handlers; - rcu_read_lock(); - /* - * Called from the timer, no need to check if handlers is - * valid. - */ - list_for_each_entry_rcu(intf, &ipmi_interfaces, link) { - /* No event requests when in maintenance mode. */ - if (intf->maintenance_mode_enable) - continue; + /* No event requests when in maintenance mode. */ + if (intf->maintenance_mode_enable) + return; - handlers = intf->handlers; - if (handlers) - handlers->request_events(intf->send_info); - } - rcu_read_unlock(); + handlers = intf->handlers; + if (handlers) + handlers->request_events(intf->send_info); } static struct timer_list ipmi_timer; -/* Call every ~1000 ms. */ -#define IPMI_TIMEOUT_TIME 1000 - -/* How many jiffies does it take to get to the timeout time. */ -#define IPMI_TIMEOUT_JIFFIES ((IPMI_TIMEOUT_TIME * HZ) / 1000) - -/* - * Request events from the queue every second (this is the number of - * IPMI_TIMEOUT_TIMES between event requests). Hopefully, in the - * future, IPMI will add a way to know immediately if an event is in - * the queue and this silliness can go away. - */ -#define IPMI_REQUEST_EV_TIME (1000 / (IPMI_TIMEOUT_TIME)) - static atomic_t stop_operation; -static unsigned int ticks_to_req_ev = IPMI_REQUEST_EV_TIME; static void ipmi_timeout(unsigned long data) { + ipmi_smi_t intf; + int nt = 0; + if (atomic_read(&stop_operation)) return; - ticks_to_req_ev--; - if (ticks_to_req_ev == 0) { - ipmi_request_event(); - ticks_to_req_ev = IPMI_REQUEST_EV_TIME; - } + rcu_read_lock(); + list_for_each_entry_rcu(intf, &ipmi_interfaces, link) { + int lnt = 0; + + if (atomic_read(&intf->event_waiters)) { + intf->ticks_to_req_ev--; + if (intf->ticks_to_req_ev == 0) { + ipmi_request_event(intf); + intf->ticks_to_req_ev = IPMI_REQUEST_EV_TIME; + } + lnt++; + } - ipmi_timeout_handler(IPMI_TIMEOUT_TIME); + lnt += ipmi_timeout_handler(intf, IPMI_TIMEOUT_TIME); - mod_timer(&ipmi_timer, jiffies + IPMI_TIMEOUT_JIFFIES); + lnt = !!lnt; + if (lnt != intf->last_needs_timer && + intf->handlers->set_need_watch) + intf->handlers->set_need_watch(intf->send_info, lnt); + intf->last_needs_timer = lnt; + + nt += lnt; + } + rcu_read_unlock(); + + if (nt) + mod_timer(&ipmi_timer, jiffies + IPMI_TIMEOUT_JIFFIES); } +static void need_waiter(ipmi_smi_t intf) +{ + /* Racy, but worst case we start the timer twice. */ + if (!timer_pending(&ipmi_timer)) + mod_timer(&ipmi_timer, jiffies + IPMI_TIMEOUT_JIFFIES); +} static atomic_t smi_msg_inuse_count = ATOMIC_INIT(0); static atomic_t recv_msg_inuse_count = ATOMIC_INIT(0); diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c index 25a1436a429..444ea548dfe 100644 --- a/drivers/char/ipmi/ipmi_si_intf.c +++ b/drivers/char/ipmi/ipmi_si_intf.c @@ -257,6 +257,9 @@ struct smi_info { /* Used to gracefully stop the timer without race conditions. */ atomic_t stop_operation; + /* Are we waiting for the events, pretimeouts, received msgs? */ + atomic_t need_watch; + /* * The driver will disable interrupts when it gets into a * situation where it cannot handle messages due to lack of @@ -862,6 +865,19 @@ static enum si_sm_result smi_event_handler(struct smi_info *smi_info, return si_sm_result; } +static void check_start_timer_thread(struct smi_info *smi_info) +{ + if (smi_info->si_state == SI_NORMAL && smi_info->curr_msg == NULL) { + smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); + + if (smi_info->thread) + wake_up_process(smi_info->thread); + + start_next_msg(smi_info); + smi_event_handler(smi_info, 0); + } +} + static void sender(void *send_info, struct ipmi_smi_msg *msg, int priority) @@ -915,15 +931,7 @@ static void sender(void *send_info, else list_add_tail(&msg->link, &smi_info->xmit_msgs); - if (smi_info->si_state == SI_NORMAL && smi_info->curr_msg == NULL) { - smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); - - if (smi_info->thread) - wake_up_process(smi_info->thread); - - start_next_msg(smi_info); - smi_event_handler(smi_info, 0); - } + check_start_timer_thread(smi_info); spin_unlock_irqrestore(&smi_info->si_lock, flags); } @@ -1023,9 +1031,15 @@ static int ipmi_thread(void *data) ; /* do nothing */ else if (smi_result == SI_SM_CALL_WITH_DELAY && busy_wait) schedule(); - else if (smi_result == SI_SM_IDLE) - schedule_timeout_interruptible(100); - else + else if (smi_result == SI_SM_IDLE) { + if (atomic_read(&smi_info->need_watch)) { + schedule_timeout_interruptible(100); + } else { + /* Wait to be woken up when we are needed. */ + __set_current_state(TASK_INTERRUPTIBLE); + schedule(); + } + } else schedule_timeout_interruptible(1); } return 0; @@ -1061,6 +1075,17 @@ static void request_events(void *send_info) atomic_set(&smi_info->req_events, 1); } +static void set_need_watch(void *send_info, int enable) +{ + struct smi_info *smi_info = send_info; + unsigned long flags; + + atomic_set(&smi_info->need_watch, enable); + spin_lock_irqsave(&smi_info->si_lock, flags); + check_start_timer_thread(smi_info); + spin_unlock_irqrestore(&smi_info->si_lock, flags); +} + static int initialized; static void smi_timeout(unsigned long data) @@ -1212,6 +1237,7 @@ static struct ipmi_smi_handlers handlers = { .get_smi_info = get_smi_info, .sender = sender, .request_events = request_events, + .set_need_watch = set_need_watch, .set_maintenance_mode = set_maintenance_mode, .set_run_to_completion = set_run_to_completion, .poll = poll, @@ -3352,6 +3378,7 @@ static int try_smi_init(struct smi_info *new_smi) new_smi->interrupt_disabled = 1; atomic_set(&new_smi->stop_operation, 0); + atomic_set(&new_smi->need_watch, 0); new_smi->intf_num = smi_num; smi_num++; diff --git a/include/linux/ipmi.h b/include/linux/ipmi.h index 1f9f56e2885..76d2acbfa7c 100644 --- a/include/linux/ipmi.h +++ b/include/linux/ipmi.h @@ -237,7 +237,7 @@ int ipmi_set_maintenance_mode(ipmi_user_t user, int mode); * The first user that sets this to TRUE will receive all events that * have been queued while no one was waiting for events. */ -int ipmi_set_gets_events(ipmi_user_t user, int val); +int ipmi_set_gets_events(ipmi_user_t user, bool val); /* * Called when a new SMI is registered. This will also be called on diff --git a/include/linux/ipmi_smi.h b/include/linux/ipmi_smi.h index 8ea3fe0b975..2a7ff302d99 100644 --- a/include/linux/ipmi_smi.h +++ b/include/linux/ipmi_smi.h @@ -109,6 +109,13 @@ struct ipmi_smi_handlers { events from the BMC we are attached to. */ void (*request_events)(void *send_info); + /* Called by the upper layer when some user requires that the + interface watch for events, received messages, watchdog + pretimeouts, or not. Used by the SMI to know if it should + watch for these. This may be NULL if the SMI does not + implement it. */ + void (*set_need_watch)(void *send_info, int enable); + /* Called when the interface should go into "run to completion" mode. If this call sets the value to true, the interface should make sure that all messages are flushed -- cgit v1.2.3-70-g09d2 From 7aefac26fc67158cb8826a5f5bfc2a5086a7d962 Mon Sep 17 00:00:00 2001 From: Corey Minyard Date: Mon, 14 Apr 2014 09:46:56 -0500 Subject: ipmi: boolify some things Convert some ints to bools. Signed-off-by: Corey Minyard Signed-off-by: Linus Torvalds --- drivers/char/ipmi/ipmi_msghandler.c | 22 ++++++++-------- drivers/char/ipmi/ipmi_si_intf.c | 50 ++++++++++++++++++------------------- include/linux/ipmi_smi.h | 6 ++--- 3 files changed, 38 insertions(+), 40 deletions(-) (limited to 'drivers/char') diff --git a/drivers/char/ipmi/ipmi_msghandler.c b/drivers/char/ipmi/ipmi_msghandler.c index 872c4ec79bf..e6db9381b2c 100644 --- a/drivers/char/ipmi/ipmi_msghandler.c +++ b/drivers/char/ipmi/ipmi_msghandler.c @@ -94,8 +94,8 @@ static struct proc_dir_entry *proc_ipmi_root; struct ipmi_user { struct list_head link; - /* Set to "0" when the user is destroyed. */ - int valid; + /* Set to false when the user is destroyed. */ + bool valid; struct kref refcount; @@ -413,7 +413,7 @@ struct ipmi_smi { /* For handling of maintenance mode. */ int maintenance_mode; - int maintenance_mode_enable; + bool maintenance_mode_enable; int auto_maintenance_timeout; spinlock_t maintenance_mode_lock; /* Used in a timer... */ @@ -980,7 +980,7 @@ int ipmi_create_user(unsigned int if_num, */ mutex_unlock(&ipmi_interfaces_mutex); - new_user->valid = 1; + new_user->valid = true; spin_lock_irqsave(&intf->seq_lock, flags); list_add_rcu(&new_user->link, &intf->users); spin_unlock_irqrestore(&intf->seq_lock, flags); @@ -1042,7 +1042,7 @@ int ipmi_destroy_user(ipmi_user_t user) struct cmd_rcvr *rcvr; struct cmd_rcvr *rcvrs = NULL; - user->valid = 0; + user->valid = false; if (user->handler->ipmi_watchdog_pretimeout) atomic_dec(&intf->event_waiters); @@ -1184,25 +1184,23 @@ int ipmi_set_maintenance_mode(ipmi_user_t user, int mode) if (intf->maintenance_mode != mode) { switch (mode) { case IPMI_MAINTENANCE_MODE_AUTO: - intf->maintenance_mode = mode; intf->maintenance_mode_enable = (intf->auto_maintenance_timeout > 0); break; case IPMI_MAINTENANCE_MODE_OFF: - intf->maintenance_mode = mode; - intf->maintenance_mode_enable = 0; + intf->maintenance_mode_enable = false; break; case IPMI_MAINTENANCE_MODE_ON: - intf->maintenance_mode = mode; - intf->maintenance_mode_enable = 1; + intf->maintenance_mode_enable = true; break; default: rv = -EINVAL; goto out_unlock; } + intf->maintenance_mode = mode; maintenance_mode_update(intf); } @@ -1578,7 +1576,7 @@ static int i_ipmi_request(ipmi_user_t user, = IPMI_MAINTENANCE_MODE_TIMEOUT; if (!intf->maintenance_mode && !intf->maintenance_mode_enable) { - intf->maintenance_mode_enable = 1; + intf->maintenance_mode_enable = true; maintenance_mode_update(intf); } spin_unlock_irqrestore(&intf->maintenance_mode_lock, @@ -4129,7 +4127,7 @@ static unsigned int ipmi_timeout_handler(ipmi_smi_t intf, long timeout_period) -= timeout_period; if (!intf->maintenance_mode && (intf->auto_maintenance_timeout <= 0)) { - intf->maintenance_mode_enable = 0; + intf->maintenance_mode_enable = false; maintenance_mode_update(intf); } } diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c index 444ea548dfe..1c4bb4f6ce9 100644 --- a/drivers/char/ipmi/ipmi_si_intf.c +++ b/drivers/char/ipmi/ipmi_si_intf.c @@ -217,7 +217,7 @@ struct smi_info { unsigned char msg_flags; /* Does the BMC have an event buffer? */ - char has_event_buffer; + bool has_event_buffer; /* * If set to true, this will request events the next time the @@ -230,7 +230,7 @@ struct smi_info { * call. Generally used after a panic to make sure stuff goes * out. */ - int run_to_completion; + bool run_to_completion; /* The I/O port of an SI interface. */ int port; @@ -266,7 +266,7 @@ struct smi_info { * memory. Once that situation clears up, it will re-enable * interrupts. */ - int interrupt_disabled; + bool interrupt_disabled; /* From the get device id response... */ struct ipmi_device_id device_id; @@ -279,7 +279,7 @@ struct smi_info { * True if we allocated the device, false if it came from * someplace else (like PCI). */ - int dev_registered; + bool dev_registered; /* Slave address, could be reported from DMI. */ unsigned char slave_addr; @@ -303,19 +303,19 @@ struct smi_info { static int force_kipmid[SI_MAX_PARMS]; static int num_force_kipmid; #ifdef CONFIG_PCI -static int pci_registered; +static bool pci_registered; #endif #ifdef CONFIG_ACPI -static int pnp_registered; +static bool pnp_registered; #endif #ifdef CONFIG_PARISC -static int parisc_registered; +static bool parisc_registered; #endif static unsigned int kipmid_max_busy_us[SI_MAX_PARMS]; static int num_max_busy_us; -static int unload_when_empty = 1; +static bool unload_when_empty = true; static int add_smi(struct smi_info *smi); static int try_smi_init(struct smi_info *smi); @@ -457,7 +457,7 @@ static inline void disable_si_irq(struct smi_info *smi_info) { if ((smi_info->irq) && (!smi_info->interrupt_disabled)) { start_disable_irq(smi_info); - smi_info->interrupt_disabled = 1; + smi_info->interrupt_disabled = true; if (!atomic_read(&smi_info->stop_operation)) smi_mod_timer(smi_info, jiffies + SI_TIMEOUT_JIFFIES); } @@ -467,7 +467,7 @@ static inline void enable_si_irq(struct smi_info *smi_info) { if ((smi_info->irq) && (smi_info->interrupt_disabled)) { start_enable_irq(smi_info); - smi_info->interrupt_disabled = 0; + smi_info->interrupt_disabled = false; } } @@ -712,7 +712,7 @@ static void handle_transaction_done(struct smi_info *smi_info) dev_warn(smi_info->dev, "Maybe ok, but ipmi might run very slowly.\n"); } else - smi_info->interrupt_disabled = 0; + smi_info->interrupt_disabled = false; smi_info->si_state = SI_NORMAL; break; } @@ -935,7 +935,7 @@ static void sender(void *send_info, spin_unlock_irqrestore(&smi_info->si_lock, flags); } -static void set_run_to_completion(void *send_info, int i_run_to_completion) +static void set_run_to_completion(void *send_info, bool i_run_to_completion) { struct smi_info *smi_info = send_info; enum si_sm_result result; @@ -1050,7 +1050,7 @@ static void poll(void *send_info) { struct smi_info *smi_info = send_info; unsigned long flags = 0; - int run_to_completion = smi_info->run_to_completion; + bool run_to_completion = smi_info->run_to_completion; /* * Make sure there is some delay in the poll loop so we can @@ -1075,7 +1075,7 @@ static void request_events(void *send_info) atomic_set(&smi_info->req_events, 1); } -static void set_need_watch(void *send_info, int enable) +static void set_need_watch(void *send_info, bool enable) { struct smi_info *smi_info = send_info; unsigned long flags; @@ -1223,7 +1223,7 @@ static int get_smi_info(void *send_info, struct ipmi_smi_info *data) return 0; } -static void set_maintenance_mode(void *send_info, int enable) +static void set_maintenance_mode(void *send_info, bool enable) { struct smi_info *smi_info = send_info; @@ -1364,7 +1364,7 @@ module_param_array(force_kipmid, int, &num_force_kipmid, 0); MODULE_PARM_DESC(force_kipmid, "Force the kipmi daemon to be enabled (1) or" " disabled(0). Normally the IPMI driver auto-detects" " this, but the value may be overridden by this parm."); -module_param(unload_when_empty, int, 0); +module_param(unload_when_empty, bool, 0); MODULE_PARM_DESC(unload_when_empty, "Unload the module if no interfaces are" " specified or found, default is 1. Setting to 0" " is useful for hot add of devices using hotmod."); @@ -3372,11 +3372,11 @@ static int try_smi_init(struct smi_info *new_smi) INIT_LIST_HEAD(&(new_smi->hp_xmit_msgs)); new_smi->curr_msg = NULL; atomic_set(&new_smi->req_events, 0); - new_smi->run_to_completion = 0; + new_smi->run_to_completion = false; for (i = 0; i < SI_NUM_STATS; i++) atomic_set(&new_smi->stats[i], 0); - new_smi->interrupt_disabled = 1; + new_smi->interrupt_disabled = true; atomic_set(&new_smi->stop_operation, 0); atomic_set(&new_smi->need_watch, 0); new_smi->intf_num = smi_num; @@ -3384,7 +3384,7 @@ static int try_smi_init(struct smi_info *new_smi) rv = try_enable_event_buffer(new_smi); if (rv == 0) - new_smi->has_event_buffer = 1; + new_smi->has_event_buffer = true; /* * Start clearing the flags before we enable interrupts or the @@ -3418,7 +3418,7 @@ static int try_smi_init(struct smi_info *new_smi) rv); goto out_err; } - new_smi->dev_registered = 1; + new_smi->dev_registered = true; } rv = ipmi_register_smi(&handlers, @@ -3467,7 +3467,7 @@ static int try_smi_init(struct smi_info *new_smi) wait_for_timer_and_thread(new_smi); out_err: - new_smi->interrupt_disabled = 1; + new_smi->interrupt_disabled = true; if (new_smi->intf) { ipmi_unregister_smi(new_smi->intf); @@ -3503,7 +3503,7 @@ static int try_smi_init(struct smi_info *new_smi) if (new_smi->dev_registered) { platform_device_unregister(new_smi->pdev); - new_smi->dev_registered = 0; + new_smi->dev_registered = false; } return rv; @@ -3558,14 +3558,14 @@ static int init_ipmi_si(void) printk(KERN_ERR PFX "Unable to register " "PCI driver: %d\n", rv); else - pci_registered = 1; + pci_registered = true; } #endif #ifdef CONFIG_ACPI if (si_tryacpi) { pnp_register_driver(&ipmi_pnp_driver); - pnp_registered = 1; + pnp_registered = true; } #endif @@ -3581,7 +3581,7 @@ static int init_ipmi_si(void) #ifdef CONFIG_PARISC register_parisc_driver(&ipmi_parisc_driver); - parisc_registered = 1; + parisc_registered = true; /* poking PC IO addresses will crash machine, don't do it */ si_trydefaults = 0; #endif diff --git a/include/linux/ipmi_smi.h b/include/linux/ipmi_smi.h index 2a7ff302d99..bd349240d50 100644 --- a/include/linux/ipmi_smi.h +++ b/include/linux/ipmi_smi.h @@ -114,14 +114,14 @@ struct ipmi_smi_handlers { pretimeouts, or not. Used by the SMI to know if it should watch for these. This may be NULL if the SMI does not implement it. */ - void (*set_need_watch)(void *send_info, int enable); + void (*set_need_watch)(void *send_info, bool enable); /* Called when the interface should go into "run to completion" mode. If this call sets the value to true, the interface should make sure that all messages are flushed out and that none are pending, and any new requests are run to completion immediately. */ - void (*set_run_to_completion)(void *send_info, int run_to_completion); + void (*set_run_to_completion)(void *send_info, bool run_to_completion); /* Called to poll for work to do. This is so upper layers can poll for operations during things like crash dumps. */ @@ -132,7 +132,7 @@ struct ipmi_smi_handlers { setting. The message handler does the mode handling. Note that this is called from interrupt context, so it cannot block. */ - void (*set_maintenance_mode)(void *send_info, int enable); + void (*set_maintenance_mode)(void *send_info, bool enable); /* Tell the handler that we are using it/not using it. The message handler get the modules that this handler belongs -- cgit v1.2.3-70-g09d2