From: Boris Brezillon <boris.brezillon@bootlin.com>
To: Geert Uytterhoeven <geert@linux-m68k.org>
Cc: Richard Weinberger <richard@nod.at>,
David Woodhouse <dwmw2@infradead.org>,
Brian Norris <computersforpeace@gmail.com>,
Marek Vasut <marek.vasut@gmail.com>,
Miquel Raynal <miquel.raynal@bootlin.com>,
linux-mtd@lists.infradead.org, linux-m68k@vger.kernel.org,
linux-kernel@vger.kernel.org
Subject: Re: [PATCH] mtd: nand: Fix return type of __DIVIDE() when called with 32-bit
Date: Mon, 14 May 2018 13:23:24 +0200 [thread overview]
Message-ID: <20180514132324.595b63eb@bbrezillon> (raw)
In-Reply-To: <1526294977-32303-1-git-send-email-geert@linux-m68k.org>
On Mon, 14 May 2018 12:49:37 +0200
Geert Uytterhoeven <geert@linux-m68k.org> wrote:
> The __DIVIDE() macro checks whether it is called with a 32-bit or 64-bit
> dividend, to select the appropriate divide-and-round-up routine.
> As the check uses the ternary operator, the result will always be
> promoted to a type that can hold both results, i.e. unsigned long long.
>
> When using this result in a division on a 32-bit system, this may lead
> to link errors like:
>
> ERROR: "__udivdi3" [drivers/mtd/nand/raw/nand.ko] undefined!
>
> Fix this by casting the result of the 64-bit division to the type of the
> dividend.
>
> Fixes: 8878b126df769831 ("mtd: nand: add ->exec_op() implementation")
> Signed-off-by: Geert Uytterhoeven <geert@linux-m68k.org>
> ---
> This fixes the root cause of the link failure seen with
> m68k/allmodconfig since commit 3057fcef385348fe ("mtd: rawnand: Make
> sure we wait tWB before polling the STATUS reg").
>
> An alternative mitigation was posted as "[PATCH] m68k: Implement
> ndelay() as an inline function to force type checking/casting"
> (https://lkml.org/lkml/2018/5/13/102).
> ---
> include/linux/mtd/rawnand.h | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/include/linux/mtd/rawnand.h b/include/linux/mtd/rawnand.h
> index 5dad59b312440a9c..d06dc428ea0102ae 100644
> --- a/include/linux/mtd/rawnand.h
> +++ b/include/linux/mtd/rawnand.h
> @@ -871,7 +871,7 @@ struct nand_op_instr {
> #define __DIVIDE(dividend, divisor) ({ \
> sizeof(dividend) == sizeof(u32) ? \
> DIV_ROUND_UP(dividend, divisor) : \
> - DIV_ROUND_UP_ULL(dividend, divisor); \
> + (__typeof__(dividend))DIV_ROUND_UP_ULL(dividend, divisor); \
Hm, it's a bit hard to follow when you place the cast here. One could
wonder why a cast to (__typeof__(dividend)) is needed since
DIV_ROUND_UP_ULL() already returns a (__typeof__(dividend)) type.
How about:
/*
* Cast to type of dividend is needed here to guarantee that the
* result won't be an unsigned long long when the dividend is an
* unsigned long, which is what the compiler does when it sees a
* ternary operator with 2 different return types.
*/
(__typeof__(dividend))(sizeof(dividend) == sizeof(u32) ? \
DIV_ROUND_UP(dividend, divisor) : \
DIV_ROUND_UP_ULL(dividend, divisor));
Actually, I'm not even sure we care about the truncation that could
happen on an unsigned long long -> unsigned long cast because the
delays we express here will anyway be hundreds of nanosecs/millisecs,
so nothing close to the billions of nanosecs/millisecs you can express
with an unsigned long.
So, maybe we should just do:
(unsigned long)(sizeof(dividend) == sizeof(u32) ? \
DIV_ROUND_UP(dividend, divisor) : \
DIV_ROUND_UP_ULL(dividend, divisor));
to make things more readable.
> })
> #define PSEC_TO_NSEC(x) __DIVIDE(x, 1000)
> #define PSEC_TO_MSEC(x) __DIVIDE(x, 1000000000)
next prev parent reply other threads:[~2018-05-14 11:23 UTC|newest]
Thread overview: 10+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-05-14 10:49 [PATCH] mtd: nand: Fix return type of __DIVIDE() when called with 32-bit Geert Uytterhoeven
2018-05-14 11:23 ` Boris Brezillon [this message]
2018-05-14 11:32 ` Geert Uytterhoeven
2018-05-14 11:46 ` Boris Brezillon
2018-05-14 11:55 ` Boris Brezillon
2018-05-14 12:00 ` Geert Uytterhoeven
2018-05-14 12:13 ` Boris Brezillon
2018-05-14 12:13 ` Boris Brezillon
2018-05-14 12:48 ` Geert Uytterhoeven
2018-05-15 9:12 ` Boris Brezillon
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20180514132324.595b63eb@bbrezillon \
--to=boris.brezillon@bootlin.com \
--cc=computersforpeace@gmail.com \
--cc=dwmw2@infradead.org \
--cc=geert@linux-m68k.org \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-m68k@vger.kernel.org \
--cc=linux-mtd@lists.infradead.org \
--cc=marek.vasut@gmail.com \
--cc=miquel.raynal@bootlin.com \
--cc=richard@nod.at \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.