[Bug c++/105553] [11/12/13 Regression] [DR1640] Deduction when attempting to create an array with an element type that is an abstract class

2022-05-16 Thread glenjofe at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=105553

--- Comment #3 from Glen Joseph Fernandes  ---
I would have expected this to only take effect in C++20 standards mode, leaving
C++03 through C++17 modes with no change in behavior.

Given the following intention in your commit message:

> This change was moved as a DR, so I'm applying it to all
standard levels.  This could be reconsidered if it causes problems, but I
don't expect it to.

I'm going to assume that in general this wasn't a problem for most users. :)

[Bug c++/105553] New: Deduction when attempting to create an array with an element type that is an abstract class

2022-05-10 Thread glenjofe at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=105553

Bug ID: 105553
   Summary: Deduction when attempting to create an array with an
element type that is an abstract class
   Product: gcc
   Version: 11.0
Status: UNCONFIRMED
  Severity: normal
  Priority: P3
 Component: c++
  Assignee: unassigned at gcc dot gnu.org
  Reporter: glenjofe at gmail dot com
  Target Milestone: ---

Starting with GCC11, the following definition of a trait to check if a type is
abstract no longer works in any standard mode:

template
class is_abstract {
template
static char ((U(*)[1]))[2];
template
static char check(...);
public:
static const bool value = sizeof(check(0)) == sizeof(char);
};
struct abstract {
virtual void function() = 0;
};
static_assert(is_abstract::value, "ok");

The static assertion trigger on GCC11 and above, even in older standard modes.
It compiles fine on GCC10 and below.

Various libraries in Boost use the above definition of is_abstract especially
in C++03. The basis was the following wording in [temp.deduct] until C++17:

"Type deduction may fail for the following reasons:
- Attempting to create an array with an element type that is void, a function
type, a reference type, or an abstract class type, or attempting to create an
array with a size that is zero or negative."

The "or an abstract class type" was absent in C++03, added by CWG337.

[Bug libstdc++/96416] to_address() is broken by static_assert in pointer_traits

2021-03-28 Thread glenjofe at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96416

--- Comment #16 from Glen Joseph Fernandes  ---
> should a wording defect be raised against std::to_address(Ptr), to state that 
> pointer_traits being well-formed is actually a prerequisite?

That's not an omission in the specification of to_address. The function is
intended for pointers, and specified in terms of checking for a
pointer_traits member, and this means pointer_traits must be well-formed. 

Adding an additional text to the specification saying this explicitly is
unlikely to help anyone. The real change that users of iterators[1] would want
is to make pointer_traits SFINAE friendly.

[1] Users of pointers don't care much, since all the pointer types people are
using with to_address(p) already have a well-formed pointer_traits.

[Bug libstdc++/96416] address_of() is broken by static_assert in pointer_traits

2021-03-26 Thread glenjofe at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96416

--- Comment #11 from Glen Joseph Fernandes  ---
> if it can never be used.

You're misunderstanding.   to_address(p) requires that pointer_traits is
valid. It just doesn't need to have a to_address member function.

Example 1. You have a pointer-like type Ptr1. You haven't specialized
pointer_traits, but pointer_traits is valid. Here it will call
to_address(p1.operator->()).

Example 2. You have a pointer-like type Ptr2. You have specialized
pointer_traits with a to_address function. Here it will call
pointer_traits::to_address(p2).

to_address() was intended for used with pointers and pointer-like types (and
pointer_traits was always required to be valid).

It was intended for use with allocator pointers, and the original standard
library implementations had a return type of: typename
pointer_traits::element_type*

If (for contiguous iterators, which came later) you want pointer_traits to
be valid even when X does not have element_type, that is a design change to
pointer_traits.

[Bug libstdc++/96416] address_of() is broken by static_assert in pointer_traits

2020-11-11 Thread glenjofe at gmail dot com via Gcc-bugs
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96416

Glen Joseph Fernandes  changed:

   What|Removed |Added

 CC||glenjofe at gmail dot com

--- Comment #6 from Glen Joseph Fernandes  ---
> Do we then have a spec bug?

The to_address(const P&) overload always assumed a valid pointer_traits.
Even before it was std::to_address in C++20, when it was __to_address in
libstdc++, or boost::to_address, or __to_raw_pointer in libc++, and was used in
C++11 and above, its return type was 'typename
std::pointer_traits::element_type*' which requires a valid pointer_traits.

i.e. Our allocator-aware containers would only ever work with fancy pointer P
for which pointer_traits is valid.

std::to_address being used for more than just raw-or-fancy-pointers came later
(since Casey's P1474 which chose to use it for contiguous iterators). My guess
is they didn't realize pointer_traits wouldn't be valid for those iterator
types.