Commit 74859ab1 authored by Rusty Russell's avatar Rusty Russell

cast: make sure suncc sees a constant.

cast_const() et. al. are supposed to be a constant expression, so you can do things like:
	static char *p = cast_const(char *, (const char *)"hello");

Unfortunately, a cast to intptr_t and arithmetic makes suncc reject it as
a constant expression.  We need the cast, because (1) the expression could be
a void *, so we can't just add to it, and (2) gcc complains with -Wcast-qual
without it.

So instead of adding BUILD_BUG_OR_ZERO, we use a ? :, which keeps everyone happy.
parent 9bf73235
...@@ -15,8 +15,8 @@ ...@@ -15,8 +15,8 @@
* only differs in signed/unsigned, not in type or const-ness. * only differs in signed/unsigned, not in type or const-ness.
*/ */
#define cast_signed(type, expr) \ #define cast_signed(type, expr) \
((type)(expr) \ (0 ? BUILD_ASSERT_OR_ZERO(cast_sign_compatible(type, (expr))) : \
+ BUILD_ASSERT_OR_ZERO(cast_sign_compatible(type, (expr)))) (type)(expr))
/** /**
* cast_const - remove a const qualifier from a pointer. * cast_const - remove a const qualifier from a pointer.
...@@ -26,6 +26,10 @@ ...@@ -26,6 +26,10 @@
* This ensures that you are only removing the const qualifier from an * This ensures that you are only removing the const qualifier from an
* expression. The expression must otherwise match @type. * expression. The expression must otherwise match @type.
* *
* We cast via intptr_t to suppress gcc's -Wcast-qual (which SAMBA
* uses), and via the ? : so Sun CC doesn't complain about the result
* not being constant.
*
* If @type is a pointer to a pointer, you must use cast_const2 (etc). * If @type is a pointer to a pointer, you must use cast_const2 (etc).
* *
* Example: * Example:
...@@ -40,8 +44,8 @@ ...@@ -40,8 +44,8 @@
* } * }
*/ */
#define cast_const(type, expr) \ #define cast_const(type, expr) \
((type)((intptr_t)(expr) \ (0 ? BUILD_ASSERT_OR_ZERO(cast_const_compat1((expr), type)) : \
+ BUILD_ASSERT_OR_ZERO(cast_const_compat1((expr), type)))) (type)(intptr_t)(expr))
/** /**
* cast_const2 - remove a const qualifier from a pointer to a pointer. * cast_const2 - remove a const qualifier from a pointer to a pointer.
...@@ -52,8 +56,8 @@ ...@@ -52,8 +56,8 @@
* expression. The expression must otherwise match @type. * expression. The expression must otherwise match @type.
*/ */
#define cast_const2(type, expr) \ #define cast_const2(type, expr) \
((type)((intptr_t)(expr) \ (0 ? BUILD_ASSERT_OR_ZERO(cast_const_compat2((expr), type)) : \
+ BUILD_ASSERT_OR_ZERO(cast_const_compat2((expr), type)))) (type)(intptr_t)(expr))
/** /**
* cast_const3 - remove a const from a pointer to a pointer to a pointer.. * cast_const3 - remove a const from a pointer to a pointer to a pointer..
...@@ -64,8 +68,8 @@ ...@@ -64,8 +68,8 @@
* expression. The expression must otherwise match @type. * expression. The expression must otherwise match @type.
*/ */
#define cast_const3(type, expr) \ #define cast_const3(type, expr) \
((type)((intptr_t)(expr) \ (0 ? BUILD_ASSERT_OR_ZERO(cast_const_compat3((expr), type)) : \
+ BUILD_ASSERT_OR_ZERO(cast_const_compat3((expr), type)))) (type)(intptr_t)(expr))
/** /**
......
/* OpenIndiana's CC (aka suncc) has issues with constants: make sure
* we are one! */
#include <ccan/cast/cast.h>
static char *p = cast_const(char *, (const char *)"hello");
int main(int argc, char *argv[])
{
return p[0] == argv[0][0];
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment