Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-11-05 Thread Rusty Russell
On Thu, 5 Nov 2009 05:08:42 pm Stephen Rothwell wrote:
> Hi Rusty,
> 
> On Thu, 5 Nov 2009 16:58:36 +1030 Rusty Russell  wrote:
> >
> > Huh?  virtio_has_feature does:
> > 
> > if (__builtin_constant_p(fbit))
> > BUILD_BUG_ON(fbit >= 32);
> > else
> > BUG_ON(fbit >= 32);
> 
> In Linus' tree (and linux-next) it looks like this:

Ah.  My patch series fixes that as part of removing MAYBE_BUILD_BUG_ON.

I've put both in for linux-next.

Cheers,
Rusty.
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev


Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-11-04 Thread Stephen Rothwell
Hi Rusty,

On Tue, 20 Oct 2009 14:15:33 +1030 Rusty Russell  wrote:
>
> +#ifndef __OPTIMIZE__
> +#define BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)]))
> +#else
> +extern int __build_bug_on_failed;
> +#define BUILD_BUG_ON(condition)  \
> + do {\
> + ((void)sizeof(char[1 - 2*!!(condition)]));  \
> + if (condition) __build_bug_on_failed = 1;   \
> + } while(0)
> +#endif
> +#define MAYBE_BUILD_BUG_ON(condition) BUILD_BUG_ON(condition)
> +

I decided to try this in linux-next, but an x86_64 allmodconfig build
gave this (gcc 4.4.0):

ERROR: "__build_bug_on_failed" [drivers/net/virtio_net.ko] undefined!
ERROR: "__build_bug_on_failed" [drivers/block/virtio_blk.ko] undefined!

I assume that this is caused by the "MAYBE_BUILD_BUG_ON(fbit >= 32)" in
virtio_has_feature() (in include/linux/virtio_config.h) which is called
all over the place.  Unfortunately, virtio_has_feature() gets uninlined
in those two files ...

I have taken the patch back out again for today.
-- 
Cheers,
Stephen Rothwells...@canb.auug.org.au
http://www.canb.auug.org.au/~sfr/


pgpepvBMY373a.pgp
Description: PGP signature
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev

Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-10-29 Thread Hollis Blanchard
On Tue, 2009-10-20 at 14:15 +1030, Rusty Russell wrote:
> BUILD_BUG_ON used to use the optimizer to do code elimination or fail
> at link time; it was changed to first the size of a negative array (a
> nicer compile time error), then (in
> 8c87df457cb58fe75b9b893007917cf8095660a0) to a bitfield.
> 
> bitfields: needs a literal constant at parse time, and can't be put under
>   "if (__builtin_constant_p(x))" for example.
> negative array: can handle anything, but if the compiler can't tell it's
>   a constant, silently has no effect.
> link time: breaks link if the compiler can't determine the value, but the
>   linker output is not usually as informative as a compiler error.
> 
> If we use the negative-array-size method *and* the link time trick,
> we get the ability to use BUILD_BUG_ON() under __builtin_constant_p()
> branches, and maximal ability for the compiler to detect errors at
> build time.
> 
> Signed-off-by: Rusty Russell 
> 
> diff --git a/include/linux/kernel.h b/include/linux/kernel.h
> --- a/include/linux/kernel.h
> +++ b/include/linux/kernel.h
> @@ -683,12 +683,6 @@ struct sysinfo {
>   char _f[20-2*sizeof(long)-sizeof(int)]; /* Padding: libc5 uses this.. */
>  };
> 
> -/* Force a compilation error if condition is true */
> -#define BUILD_BUG_ON(condition) ((void)BUILD_BUG_ON_ZERO(condition))
> -
> -/* Force a compilation error if condition is constant and true */
> -#define MAYBE_BUILD_BUG_ON(cond) ((void)sizeof(char[1 - 2 * !!(cond)]))
> -
>  /* Force a compilation error if condition is true, but also produce a
> result (of value 0 and type size_t), so the expression can be used
> e.g. in a structure initializer (or where-ever else comma expressions
> @@ -696,6 +690,33 @@ struct sysinfo {
>  #define BUILD_BUG_ON_ZERO(e) (sizeof(struct { int:-!!(e); }))
>  #define BUILD_BUG_ON_NULL(e) ((void *)sizeof(struct { int:-!!(e); }))
> 
> +/**
> + * BUILD_BUG_ON - break compile if a condition is true.
> + * @cond: the condition which the compiler should know is false.
> + *
> + * If you have some code which relies on certain constants being equal, or
> + * other compile-time-evaluated condition, you should use BUILD_BUG_ON to
> + * detect if someone changes it.
> + *
> + * The implementation uses gcc's reluctance to create a negative array, but
> + * gcc (as of 4.4) only emits that error for obvious cases (eg. not arguments
> + * to inline functions).  So as a fallback we use the optimizer; if it can't
> + * prove the condition is false, it will cause a link error on the undefined
> + * "__build_bug_on_failed".  This error message can be harder to track down
> + * though, hence the two different methods.
> + */
> +#ifndef __OPTIMIZE__
> +#define BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)]))
> +#else
> +extern int __build_bug_on_failed;
> +#define BUILD_BUG_ON(condition)  \
> + do {\
> + ((void)sizeof(char[1 - 2*!!(condition)]));  \
> + if (condition) __build_bug_on_failed = 1;   \
> + } while(0)
> +#endif
> +#define MAYBE_BUILD_BUG_ON(condition) BUILD_BUG_ON(condition)
> +
>  /* Trap pasters of __FUNCTION__ at compile-time */
>  #define __FUNCTION__ (__func__)

What's the state of this patch?

-- 
Hollis Blanchard
IBM Linux Technology Center

___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev


Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-10-22 Thread Américo Wang
On Tue, Oct 20, 2009 at 10:43 PM, Alan Jenkins
 wrote:
> On 10/20/09, Américo Wang  wrote:
>> On Tue, Oct 20, 2009 at 02:15:33PM +1030, Rusty Russell wrote:
>>>BUILD_BUG_ON used to use the optimizer to do code elimination or fail
>>>at link time; it was changed to first the size of a negative array (a
>>>nicer compile time error), then (in
>>>8c87df457cb58fe75b9b893007917cf8095660a0) to a bitfield.
>>>
>>>bitfields: needs a literal constant at parse time, and can't be put under
>>>      "if (__builtin_constant_p(x))" for example.
>>>negative array: can handle anything, but if the compiler can't tell it's
>>>      a constant, silently has no effect.
>>>link time: breaks link if the compiler can't determine the value, but the
>>>      linker output is not usually as informative as a compiler error.
>>>
>>>If we use the negative-array-size method *and* the link time trick,
>>>we get the ability to use BUILD_BUG_ON() under __builtin_constant_p()
>>>branches, and maximal ability for the compiler to detect errors at
>>>build time.
>>>
>>>Signed-off-by: Rusty Russell 
>>>
>>>diff --git a/include/linux/kernel.h b/include/linux/kernel.h
>>>--- a/include/linux/kernel.h
>>>+++ b/include/linux/kernel.h
>>>@@ -683,12 +683,6 @@ struct sysinfo {
>>>      char _f[20-2*sizeof(long)-sizeof(int)]; /* Padding: libc5 uses this.. 
>>> */
>>> };
>>>
>>>-/* Force a compilation error if condition is true */
>>>-#define BUILD_BUG_ON(condition) ((void)BUILD_BUG_ON_ZERO(condition))
>>>-
>>>-/* Force a compilation error if condition is constant and true */
>>>-#define MAYBE_BUILD_BUG_ON(cond) ((void)sizeof(char[1 - 2 * !!(cond)]))
>>>-
>>> /* Force a compilation error if condition is true, but also produce a
>>>    result (of value 0 and type size_t), so the expression can be used
>>>    e.g. in a structure initializer (or where-ever else comma expressions
>>>@@ -696,6 +690,33 @@ struct sysinfo {
>>> #define BUILD_BUG_ON_ZERO(e) (sizeof(struct { int:-!!(e); }))
>>> #define BUILD_BUG_ON_NULL(e) ((void *)sizeof(struct { int:-!!(e); }))
>>>
>>>+/**
>>>+ * BUILD_BUG_ON - break compile if a condition is true.
>>>+ * @cond: the condition which the compiler should know is false.
>>>+ *
>>>+ * If you have some code which relies on certain constants being equal, or
>>>+ * other compile-time-evaluated condition, you should use BUILD_BUG_ON to
>>>+ * detect if someone changes it.
>>>+ *
>>>+ * The implementation uses gcc's reluctance to create a negative array,
>>> but
>>>+ * gcc (as of 4.4) only emits that error for obvious cases (eg. not
>>> arguments
>>>+ * to inline functions).  So as a fallback we use the optimizer; if it
>>> can't
>>>+ * prove the condition is false, it will cause a link error on the
>>> undefined
>>>+ * "__build_bug_on_failed".  This error message can be harder to track
>>> down
>>>+ * though, hence the two different methods.
>>>+ */
>>>+#ifndef __OPTIMIZE__
>>>+#define BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)]))
>>>+#else
>>>+extern int __build_bug_on_failed;
>>
>> Hmm, what exactly is __build_bug_on_failed?
>
> Well, we haven't added a definition for it in this patch.  I'm sure
> grep will tell you it wasn't defined before hand either.  So any
> reference to it is an error - which will be reported at link time.
>
>>>+#define BUILD_BUG_ON(condition)                                      \
>>>+     do {                                                    \
>>>+             ((void)sizeof(char[1 - 2*!!(condition)]));      \
>>>+             if (condition) __build_bug_on_failed = 1;       \
>
> If "condition" is known false at compile time, gcc -O will eliminate
> the code which refers to __build_bug_on_failed.  If it's not proved to
> be false - it will break the build, which is exactly what we want
> BUILD_BUG_ON to do.

Ah, clever trick! Got it.
Thanks!

Reviewed-by: WANG Cong 
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev

Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-10-22 Thread Hollis Blanchard
On Tue, 2009-10-20 at 14:15 +1030, Rusty Russell wrote:
> BUILD_BUG_ON used to use the optimizer to do code elimination or fail
> at link time; it was changed to first the size of a negative array (a
> nicer compile time error), then (in
> 8c87df457cb58fe75b9b893007917cf8095660a0) to a bitfield.
> 
> bitfields: needs a literal constant at parse time, and can't be put under
>   "if (__builtin_constant_p(x))" for example.
> negative array: can handle anything, but if the compiler can't tell it's
>   a constant, silently has no effect.
> link time: breaks link if the compiler can't determine the value, but the
>   linker output is not usually as informative as a compiler error.
> 
> If we use the negative-array-size method *and* the link time trick,
> we get the ability to use BUILD_BUG_ON() under __builtin_constant_p()
> branches, and maximal ability for the compiler to detect errors at
> build time.
> 
> Signed-off-by: Rusty Russell 

Thanks Rusty, this indeed fixes the problem.

Acked-by: Hollis Blanchard 

-- 
Hollis Blanchard
IBM Linux Technology Center

___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev


Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-10-20 Thread Alan Jenkins
On 10/20/09, Américo Wang  wrote:
> On Tue, Oct 20, 2009 at 02:15:33PM +1030, Rusty Russell wrote:
>>BUILD_BUG_ON used to use the optimizer to do code elimination or fail
>>at link time; it was changed to first the size of a negative array (a
>>nicer compile time error), then (in
>>8c87df457cb58fe75b9b893007917cf8095660a0) to a bitfield.
>>
>>bitfields: needs a literal constant at parse time, and can't be put under
>>  "if (__builtin_constant_p(x))" for example.
>>negative array: can handle anything, but if the compiler can't tell it's
>>  a constant, silently has no effect.
>>link time: breaks link if the compiler can't determine the value, but the
>>  linker output is not usually as informative as a compiler error.
>>
>>If we use the negative-array-size method *and* the link time trick,
>>we get the ability to use BUILD_BUG_ON() under __builtin_constant_p()
>>branches, and maximal ability for the compiler to detect errors at
>>build time.
>>
>>Signed-off-by: Rusty Russell 
>>
>>diff --git a/include/linux/kernel.h b/include/linux/kernel.h
>>--- a/include/linux/kernel.h
>>+++ b/include/linux/kernel.h
>>@@ -683,12 +683,6 @@ struct sysinfo {
>>  char _f[20-2*sizeof(long)-sizeof(int)]; /* Padding: libc5 uses this.. */
>> };
>>
>>-/* Force a compilation error if condition is true */
>>-#define BUILD_BUG_ON(condition) ((void)BUILD_BUG_ON_ZERO(condition))
>>-
>>-/* Force a compilation error if condition is constant and true */
>>-#define MAYBE_BUILD_BUG_ON(cond) ((void)sizeof(char[1 - 2 * !!(cond)]))
>>-
>> /* Force a compilation error if condition is true, but also produce a
>>result (of value 0 and type size_t), so the expression can be used
>>e.g. in a structure initializer (or where-ever else comma expressions
>>@@ -696,6 +690,33 @@ struct sysinfo {
>> #define BUILD_BUG_ON_ZERO(e) (sizeof(struct { int:-!!(e); }))
>> #define BUILD_BUG_ON_NULL(e) ((void *)sizeof(struct { int:-!!(e); }))
>>
>>+/**
>>+ * BUILD_BUG_ON - break compile if a condition is true.
>>+ * @cond: the condition which the compiler should know is false.
>>+ *
>>+ * If you have some code which relies on certain constants being equal, or
>>+ * other compile-time-evaluated condition, you should use BUILD_BUG_ON to
>>+ * detect if someone changes it.
>>+ *
>>+ * The implementation uses gcc's reluctance to create a negative array,
>> but
>>+ * gcc (as of 4.4) only emits that error for obvious cases (eg. not
>> arguments
>>+ * to inline functions).  So as a fallback we use the optimizer; if it
>> can't
>>+ * prove the condition is false, it will cause a link error on the
>> undefined
>>+ * "__build_bug_on_failed".  This error message can be harder to track
>> down
>>+ * though, hence the two different methods.
>>+ */
>>+#ifndef __OPTIMIZE__
>>+#define BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)]))
>>+#else
>>+extern int __build_bug_on_failed;
>
> Hmm, what exactly is __build_bug_on_failed?

Well, we haven't added a definition for it in this patch.  I'm sure
grep will tell you it wasn't defined before hand either.  So any
reference to it is an error - which will be reported at link time.

>>+#define BUILD_BUG_ON(condition)  \
>>+ do {\
>>+ ((void)sizeof(char[1 - 2*!!(condition)]));  \
>>+ if (condition) __build_bug_on_failed = 1;   \

If "condition" is known false at compile time, gcc -O will eliminate
the code which refers to __build_bug_on_failed.  If it's not proved to
be false - it will break the build, which is exactly what we want
BUILD_BUG_ON to do.

>>+ } while(0)
>>+#endif
>>+#define MAYBE_BUILD_BUG_ON(condition) BUILD_BUG_ON(condition)
>>+
>> /* Trap pasters of __FUNCTION__ at compile-time */
>> #define __FUNCTION__ (__func__)
>>
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev


Re: [PATCH] BUILD_BUG_ON: make it handle more cases

2009-10-20 Thread Américo Wang
On Tue, Oct 20, 2009 at 02:15:33PM +1030, Rusty Russell wrote:
>BUILD_BUG_ON used to use the optimizer to do code elimination or fail
>at link time; it was changed to first the size of a negative array (a
>nicer compile time error), then (in
>8c87df457cb58fe75b9b893007917cf8095660a0) to a bitfield.
>
>bitfields: needs a literal constant at parse time, and can't be put under
>   "if (__builtin_constant_p(x))" for example.
>negative array: can handle anything, but if the compiler can't tell it's
>   a constant, silently has no effect.
>link time: breaks link if the compiler can't determine the value, but the
>   linker output is not usually as informative as a compiler error.
>
>If we use the negative-array-size method *and* the link time trick,
>we get the ability to use BUILD_BUG_ON() under __builtin_constant_p()
>branches, and maximal ability for the compiler to detect errors at
>build time.
>
>Signed-off-by: Rusty Russell 
>
>diff --git a/include/linux/kernel.h b/include/linux/kernel.h
>--- a/include/linux/kernel.h
>+++ b/include/linux/kernel.h
>@@ -683,12 +683,6 @@ struct sysinfo {
>   char _f[20-2*sizeof(long)-sizeof(int)]; /* Padding: libc5 uses this.. */
> };
> 
>-/* Force a compilation error if condition is true */
>-#define BUILD_BUG_ON(condition) ((void)BUILD_BUG_ON_ZERO(condition))
>-
>-/* Force a compilation error if condition is constant and true */
>-#define MAYBE_BUILD_BUG_ON(cond) ((void)sizeof(char[1 - 2 * !!(cond)]))
>-
> /* Force a compilation error if condition is true, but also produce a
>result (of value 0 and type size_t), so the expression can be used
>e.g. in a structure initializer (or where-ever else comma expressions
>@@ -696,6 +690,33 @@ struct sysinfo {
> #define BUILD_BUG_ON_ZERO(e) (sizeof(struct { int:-!!(e); }))
> #define BUILD_BUG_ON_NULL(e) ((void *)sizeof(struct { int:-!!(e); }))
> 
>+/**
>+ * BUILD_BUG_ON - break compile if a condition is true.
>+ * @cond: the condition which the compiler should know is false.
>+ *
>+ * If you have some code which relies on certain constants being equal, or
>+ * other compile-time-evaluated condition, you should use BUILD_BUG_ON to
>+ * detect if someone changes it.
>+ *
>+ * The implementation uses gcc's reluctance to create a negative array, but
>+ * gcc (as of 4.4) only emits that error for obvious cases (eg. not arguments
>+ * to inline functions).  So as a fallback we use the optimizer; if it can't
>+ * prove the condition is false, it will cause a link error on the undefined
>+ * "__build_bug_on_failed".  This error message can be harder to track down
>+ * though, hence the two different methods.
>+ */
>+#ifndef __OPTIMIZE__
>+#define BUILD_BUG_ON(condition) ((void)sizeof(char[1 - 2*!!(condition)]))
>+#else
>+extern int __build_bug_on_failed;

Hmm, what exactly is __build_bug_on_failed?

>+#define BUILD_BUG_ON(condition)   \
>+  do {\
>+  ((void)sizeof(char[1 - 2*!!(condition)]));  \
>+  if (condition) __build_bug_on_failed = 1;   \
>+  } while(0)
>+#endif
>+#define MAYBE_BUILD_BUG_ON(condition) BUILD_BUG_ON(condition)
>+
> /* Trap pasters of __FUNCTION__ at compile-time */
> #define __FUNCTION__ (__func__)
> 
>--
>To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
>the body of a message to majord...@vger.kernel.org
>More majordomo info at  http://vger.kernel.org/majordomo-info.html
>Please read the FAQ at  http://www.tux.org/lkml/

-- 
Live like a child, think like the god.
 
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev