public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
From: "daniel.kruegler at googlemail dot com" <gcc-bugzilla@gcc.gnu.org>
To: gcc-bugs@gcc.gnu.org
Subject: [Bug c++/52892] Function pointer loses constexpr qualification
Date: Sat, 07 Apr 2012 13:16:00 -0000	[thread overview]
Message-ID: <bug-52892-4-HSSCvuatky@http.gcc.gnu.org/bugzilla/> (raw)
In-Reply-To: <bug-52892-4@http.gcc.gnu.org/bugzilla/>

http://gcc.gnu.org/bugzilla/show_bug.cgi?id=52892

--- Comment #1 from Daniel Krügler <daniel.kruegler at googlemail dot com> 2012-04-07 13:15:13 UTC ---
(In reply to comment #0)
[..]
> Based on my reading of the standard, this should be allowed behavior, and 
> works as expected with clang 3.1 (152539).

I agree that this should work, this was the clear intention for the core
language defect

http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_defects.html#1193 

I tried to break down the example to understand what's going wrong and here is
one simpler example:

//---------------
constexpr bool is_negative(int x) { return x < 0; }

struct Defer
{
#if 0
  typedef bool (*Function)(int);
  Function func;
  constexpr Defer(Function func) : func(func) {}
#else
  bool (*func)(int);
  constexpr Defer(bool (* func)(int)) : func(func) {}
#endif
  template<class... Args>
  constexpr auto operator()(const Args&... args) -> decltype(func(args...))
  {
    return func(args...);
  }
};

template<class Function>
constexpr Defer make_deferred(Function func)
{
  return Defer(func);
}

int main()
{
  constexpr Defer deferred(make_deferred(is_negative));
  static_assert(deferred(-2), "Error");
}
//---------------

As written, this example is well-formed. But once we change the pre-processor
directive "#if 0" to "#if 1", we have a similar error. It seems that after
introduction of the typedef for the function pointer type gcc no longer
attempts to consider the track the constness.

It is possible to construct an even simpler example. Consider the code example
from CWG defect 1193 again:

constexpr bool is_negative(int x) { return x < 0; }
constexpr bool check(int x, bool (*p)(int)) { return p(x); }
static_assert(check(-2, is_negative), "Error");

gcc accepts it as it should. Now lets introduce a typedef for the function
pointer used in check:

constexpr bool is_negative(int x) { return x < 0; }
typedef bool (*Function)(int);
constexpr bool check(int x, Function p) { return p(x); }
static_assert(check(-2, is_negative), "Error");

Now we get a similar error as in your example:

"4|error: non-constant condition for static assertion|
 4|  in constexpr expansion of 'check(-2, is_negative)'|
 3|error: expression 'is_negative' does not designate a constexpr function"

The template parameter in your example has similar effects as a typedef. Both
use cases should not invalidate the constexpr character.


  reply	other threads:[~2012-04-07 13:16 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2012-04-06 18:58 [Bug c++/52892] New: " EricMCornelius at gmail dot com
2012-04-07 13:16 ` daniel.kruegler at googlemail dot com [this message]
2012-05-29  9:28 ` [Bug c++/52892] " adrien at guinet dot me
2013-05-02 14:57 ` paolo.carlini at oracle dot com
2014-08-27 17:04 ` paolo at gcc dot gnu.org
2014-08-27 17:05 ` paolo.carlini at oracle dot com

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=bug-52892-4-HSSCvuatky@http.gcc.gnu.org/bugzilla/ \
    --to=gcc-bugzilla@gcc.gnu.org \
    --cc=gcc-bugs@gcc.gnu.org \
    /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 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).