public inbox for gcc-help@gcc.gnu.org
 help / color / mirror / Atom feed
* __builtin_choose_expr
@ 2011-10-10 15:00 Andy Gibbs
  2011-10-10 19:16 ` __builtin_choose_expr Ian Lance Taylor
  0 siblings, 1 reply; 3+ messages in thread
From: Andy Gibbs @ 2011-10-10 15:00 UTC (permalink / raw)
  To: gcc-help

Hi,

There is a very useful feature in gcc, namely __builtin_choose_expr, which 
isn't available in g++.  I expect that this is simply down to the fact that 
it had a very obvious use relating to overloading functions in C which isn't 
necessary in C++, and therefore it simply didn't get implemented.

Assuming that this was indeed the only reason, I thought rather than 
whinging that this wasn't available in C++, I'd have a go at implementing 
it.

Attached below, therefore, is a simple patch to GCC 4.6.1 which implements 
__builtin_choose_expr for C++.  From my testing, it "seems to work fine", 
but I'm afraid this is my first time hacking GCC, so I would be very 
grateful if someone much more knowledgeable than me could check over my 
patch (it should be very easy to follow) to see whether my approach is valid 
or not.

If it seems to people that this is a useful / suitable addition to GCC 
generally, then I would be happy to supplement my patch with test-cases and 
proper documentation and see whether it can be merged into the GCC trunk. 
Obviously I have uses for this feature, but I don't know whether it has a 
broader appeal!  ;o)

Thanks

Andy

--- <snip> ---

--- gcc-4.6.1-orig/gcc/c-family/c-common.c
+++ gcc-4.6.1/gcc/c-family/c-common.c
@@ -420,7 +420,7 @@ const struct c_common_resword c_common_r
   { "__asm__",  RID_ASM, 0 },
   { "__attribute", RID_ATTRIBUTE, 0 },
   { "__attribute__", RID_ATTRIBUTE, 0 },
-  { "__builtin_choose_expr", RID_CHOOSE_EXPR, D_CONLY },
+  { "__builtin_choose_expr", RID_CHOOSE_EXPR, 0 },
   { "__builtin_offsetof", RID_OFFSETOF, 0 },
   { "__builtin_types_compatible_p", RID_TYPES_COMPATIBLE_P, D_CONLY },
   { "__builtin_va_arg", RID_VA_ARG, 0 },
--- gcc-4.6.1-orig/gcc/cp/parser.c
+++ gcc-4.6.1/gcc/cp/parser.c
@@ -1837,6 +1837,8 @@ static tree cp_parser_expression
   (cp_parser *, bool, cp_id_kind *);
 static tree cp_parser_constant_expression
   (cp_parser *, bool, bool *);
+static tree cp_parser_builtin_choose_expr
+  (cp_parser *);
 static tree cp_parser_builtin_offsetof
   (cp_parser *);
 static tree cp_parser_lambda_expression
@@ -3850,6 +3852,9 @@ cp_parser_primary_expression (cp_parser
  case RID_OFFSETOF:
    return cp_parser_builtin_offsetof (parser);

+ case RID_CHOOSE_EXPR:
+   return cp_parser_builtin_choose_expr (parser);
+
  case RID_HAS_NOTHROW_ASSIGN:
  case RID_HAS_NOTHROW_CONSTRUCTOR:
  case RID_HAS_NOTHROW_COPY:
@@ -7403,6 +7408,43 @@ cp_parser_builtin_offsetof (cp_parser *p
   return expr;
 }

+/* Parse __builtin_choose_expr.
+
+     __builtin_choose_expr ( constant-expression ,
+        assignment-expression ,
+        assignment-expression )  */
+
+static tree
+cp_parser_builtin_choose_expr (cp_parser *parser)
+{
+  tree condition, expr_true, expr_false;
+
+  /* Consume the "__builtin_choose_expr" token.  */
+  cp_lexer_consume_token (parser->lexer);
+
+  /* Parse expressions. */
+  cp_parser_require (parser, CPP_OPEN_PAREN, RT_OPEN_PAREN);
+  condition = cp_parser_constant_expression (parser, false, NULL);
+  cp_parser_require (parser, CPP_COMMA, RT_COMMA);
+  expr_true = cp_parser_assignment_expression (parser, false, NULL);
+  cp_parser_require (parser, CPP_COMMA, RT_COMMA);
+  expr_false = cp_parser_assignment_expression (parser, false, NULL);
+  if (!cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN))
+ cp_parser_skip_to_closing_parenthesis (parser, true, false, true);
+
+  /* Fold the condition expression and convert it to a boolean value. */
+  condition = fold_non_dependent_expr (condition);
+  condition = cp_convert (boolean_type_node, condition);
+  condition = maybe_constant_value (condition);
+
+  if (TREE_CODE (condition) == INTEGER_CST)
+ return integer_zerop (condition) ? expr_false : expr_true;
+
+  error ("non-constant condition for %<__builtin_choose_expr%>");
+  cxx_constant_value (condition);
+  return error_mark_node;
+}
+
 /* Parse a trait expression.

    Returns a representation of the expression, the underlying type

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: __builtin_choose_expr
  2011-10-10 15:00 __builtin_choose_expr Andy Gibbs
@ 2011-10-10 19:16 ` Ian Lance Taylor
  2011-10-11 16:48   ` __builtin_choose_expr Andy Gibbs
  0 siblings, 1 reply; 3+ messages in thread
From: Ian Lance Taylor @ 2011-10-10 19:16 UTC (permalink / raw)
  To: Andy Gibbs; +Cc: gcc-help

Andy Gibbs <andyg1001@hotmail.co.uk> writes:

> Attached below, therefore, is a simple patch to GCC 4.6.1 which
> implements __builtin_choose_expr for C++.  From my testing, it "seems
> to work fine", but I'm afraid this is my first time hacking GCC, so I
> would be very grateful if someone much more knowledgeable than me
> could check over my patch (it should be very easy to follow) to see
> whether my approach is valid or not.
>
> If it seems to people that this is a useful / suitable addition to GCC
> generally, then I would be happy to supplement my patch with
> test-cases and proper documentation and see whether it can be merged
> into the GCC trunk. Obviously I have uses for this feature, but I
> don't know whether it has a broader appeal!  ;o)

The patch looks fine to me.  You should move it to trunk and submit it
to gcc-patches.  You will probably need to sign a copyright assignment;
let me know if you want to start that process.

Thanks!

Ian

^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: __builtin_choose_expr
  2011-10-10 19:16 ` __builtin_choose_expr Ian Lance Taylor
@ 2011-10-11 16:48   ` Andy Gibbs
  0 siblings, 0 replies; 3+ messages in thread
From: Andy Gibbs @ 2011-10-11 16:48 UTC (permalink / raw)
  To: Ian Lance Taylor, gcc-help

On Monday, October 10, 2011 9:16 PM, Ian Lance Taylor wrote:

> The patch looks fine to me.  You should move it to trunk and submit it
> to gcc-patches.

Thanks for checking it for me!  I have done more work on it today so that it 
works correctly with templates as well.  I will merge the patch now across 
to trunk and check that all my test-cases still work correctly and then put 
it forward to gcc-patches.

The only area which I haven't successfully managed to implement 
__builting_choose_expr is in within an auto return type, for example:

template <int i>
constexpr auto test() -> decltype(__builtin_choose_expr(i, 1, 2))
  { return __builtin_choose_expr(i, 1, 2); }

GCC gives up with "sorry, unimplemented: mangling choose_expr" since I 
didn't think myself qualified to make alterations to GCC in this area.  In 
honest, I'm not entirely sure that alterations should be necessary... but 
how to solve this, I don't know.

> You will probably need to sign a copyright assignment;
> let me know if you want to start that process.

Yes, please, if you could point me in the right direction to do this.

Many thanks

Andy


^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2011-10-11 16:48 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-10-10 15:00 __builtin_choose_expr Andy Gibbs
2011-10-10 19:16 ` __builtin_choose_expr Ian Lance Taylor
2011-10-11 16:48   ` __builtin_choose_expr Andy Gibbs

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).