https://gcc.gnu.org/bugzilla/show_bug.cgi?id=96042
--- Comment #3 from Jonathan Wakely <redi at gcc dot gnu.org> --- (In reply to gcc-bugs from comment #2) > I think this is too easy to say that this is not a "bug", we can also weaken > the terminology and say "potential-inconsistency". > > Technically you are right, but only because there seems to be a specific > "exception" for the implementation does not mean that this is the right > thing to do. I disagree. In the strongest possible terms. > <unhappy-end-user - ignore this> > I personally don't understand why the standard allows exceptions outside > it's echo-system, I guess the stdlib implementers understand the subject > better when forming the standard, and are lobbing harder for their > necessities which is sometimes different from the needs / expectation of the > end-user. > </unhappy-end-user- ignore this> This has nothing to do with our own necessities, this is to support end users. > Can you help me figure out in which cases `-std=c++2a` would produce this > type? Or asked differently: In which cases, other than this, do I encounter > a `__int128` from using only types and functions defined in the standard? I'm not aware of any others currently. That could change in future if the C and C++ standards are changed to allow types larger than long long to be treated as standard integer types. I would be very happy to see the ideas described in http://www.open-std.org/jtc1/sc22/wg14/www/docs/n2425.pdf happen. > I have the feeling from your answer that this type is an everyday type. No. It's not, and that's exactly why we used it for IOTA-DIFF-T. > Looking at https://eel.is/c++draft/range.iota#view-1, and if I read it > correctly, this is case 3: > > > Otherwise, IOTA-DIFF-T(W) is an unspecified signed-integer-like type > > ([iterator.concept.winc]) of width not less than the width of W. > > > > [Note: It is unspecified whether this type satisfies > > weakly_Âincrementable. — end note] > > It means it would be totally fine to return the signed version of `size_t`, > because it has at least the same width. (This would be a valid option, too) But it wouldn't be totally fine, because that type (i.e. ptrdiff_t) cannot represent the difference between the begin and end iterators of iota_view<size_t, SIZE_MAX>. The whole point of allowing IOTA-DIFF-T to be an unspecified integer-like type is to solve that problem. It has to be a type larger than size_t, otherwise you can't use large iota_view types, and that make a different group of users unhappy. Our implementation will soon be updated to use a custom class type that behaves like an integer, so that we can also represent the maximum difference for iota_view<unsigned __int128, (unsigned __int128)-1>. Will you still complain that "it is unexpected that I get a type that is not described in the standard"? It's **not possible** to represent the difference type of iota_view<W,B> for every W without using a type that isn't in the set of types allowed for W. See http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2019/p1522r1.pdf for the background. Why is using __int128 here a problem? Do you really think we should treat "I am surprised by this" as a more serious concern than "Some specializations of iota_view have undefined bhaviour because the alternative would surprise some people"? You being unhappy because you don't expect something can (I hope) be resolved by explaining the pragmatic engineering reasons behind the decision. Some code being impossible to write cannot really be explained just by saying "we know how to make this work, but it made somebody sad so we decided not to support it, sorry". The problem here seems to be that you expect the difference type of an iota_view to be a normal integer type. Your expectation is wrong. You should change your expectation.