public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c++/66639] New: Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr
@ 2015-06-23 13:08 simon at gleissner dot de
  2015-06-23 18:55 ` [Bug c++/66639] " msebor at gcc dot gnu.org
                   ` (2 more replies)
  0 siblings, 3 replies; 4+ messages in thread
From: simon at gleissner dot de @ 2015-06-23 13:08 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66639

            Bug ID: 66639
           Summary: Feature request C++: mark __func__ , __FUNCTION__ &
                    __PRETTY_FUNCTION__ as constexpr
           Product: gcc
           Version: 5.1.1
            Status: UNCONFIRMED
          Severity: enhancement
          Priority: P3
         Component: c++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: simon at gleissner dot de
  Target Milestone: ---

Currently, __func__ , __FUNCTION__ and __PRETTY_FUNCTION__ are internally
declared as static constant arrays:

    static const char __func__[] = "function-name";

If compiled as C++11/14, it might be possible to declare them as 'constexpr',
to fully enable them for constexpr functions.

I have written an exception wrapper to precompile the error text (as C++14, see
below). Basically, the following code concatenate strings during compile time,
not at run time. The text is thrown during a std::system_error as the
'what'-argument.

The interesting part is in the THROW_SYSTEM_ERROR macro, where i use
__PRETTY_FUNCTION__. The code works and the output is (as expected)

    Exception in 'int main()' by 'testfunc()': Invalid argument (system:22)

When we look in the compiled code (-O3 or -Os), a precompiled struct object
with the precompiled string "in 'int main()' by 'testfunc()'" is pushed onto
the stack byte for byte:

        call    __cxa_allocate_exception
        movq    %rax, %rbx
        movb    $105, (%rsp)
        movb    $110, 1(%rsp)
        movb    $32, 2(%rsp)
        movb    $39, 3(%rsp)
        movb    $105, 4(%rsp)
        movb    $110, 5(%rsp)
        movb    $116, 6(%rsp)
        movb    $32, 7(%rsp)
        movb    $109, 8(%rsp)
        movb    $97, 9(%rsp)
        movb    $105, 10(%rsp)
        movb    $110, 11(%rsp)
        movb    $40, 12(%rsp)
        movb    $41, 13(%rsp)
        movb    $39, 14(%rsp)
        movb    $32, 15(%rsp)
        movb    $98, 16(%rsp)
        movb    $121, 17(%rsp)
        movb    $32, 18(%rsp)
        movb    $39, 19(%rsp)
        movb    $116, 20(%rsp)
        movb    $101, 21(%rsp)
        movb    $115, 22(%rsp)
        movb    $116, 23(%rsp)
        movb    $102, 24(%rsp)
        movb    $117, 25(%rsp)
        movb    $110, 26(%rsp)
        movb    $99, 27(%rsp)
        movb    $40, 28(%rsp)
        movb    $41, 29(%rsp)
        movb    $39, 30(%rsp)
        movb    $0, 31(%rsp)
        call    _ZNSt3_V215system_categoryEv

This is not really what i have expected, but because i use a temporary object,
it is understandable.

However, when i use a static constexpr object for the precompiled text (enable
the disabled macro in the source), i get the error messages

    ../src/Tests.cpp:112:111: error: the value of ‘__PRETTY_FUNCTION__’ is not
usable in a constant expression
    ../src/Tests.cpp:112:65: note: ‘__PRETTY_FUNCTION__’ was not declared
‘constexpr


As __PRETTY_FUNCTION__ can already be used in constexpr functions at compile
time, i don't think that this change might be very big.



//============================================================================
// Name        : Tests.cpp
// Author      : Simon Gleissner
//============================================================================

#include <iostream>
#include <system_error>
#include <cerrno>
#include <cstring>

namespace MyLib {

template<typename... CHARS>
struct Message
{
        constexpr Message(CHARS... chars)
                : str {chars...,'\0'}
        {}

        const char str[sizeof...(CHARS)+1];
};

// we can not specialize a function template parially,
// therefore we have to wrap it statically inside a class
// (which can partially be specialized)
template<unsigned COUNTDOWN_A, unsigned COUNTDOWN_B, unsigned COUNTDOWN_C>
struct CharIndexer
{
        template<unsigned SIZE_A, unsigned SIZE_B, unsigned SIZE_C, typename...
CHARS>
        static constexpr auto CreateChars(
                        const char (&str_a)[SIZE_A],
                        const char (&str_b)[SIZE_B],
                        const char (&str_c)[SIZE_C],
                        CHARS... chars)
        {
                return CharIndexer<COUNTDOWN_A-1, COUNTDOWN_B,
COUNTDOWN_C>::CreateChars(str_a, str_b, str_c, chars...,
str_a[SIZE_A-COUNTDOWN_A]);
        }
};

template<unsigned COUNTDOWN_B, unsigned COUNTDOWN_C>
struct CharIndexer<1, COUNTDOWN_B, COUNTDOWN_C>
{
        template<unsigned SIZE_A, unsigned SIZE_B, unsigned SIZE_C, typename...
CHARS>
        static constexpr auto CreateChars(
                        const char (&str_a)[SIZE_A],
                        const char (&str_b)[SIZE_B],
                        const char (&str_c)[SIZE_C],
                        CHARS... chars)
        {
                return CharIndexer<1, COUNTDOWN_B-1,
COUNTDOWN_C>::CreateChars(str_a, str_b, str_c, chars...,
str_b[SIZE_B-COUNTDOWN_B]);
        }
};

template<unsigned COUNTDOWN_C>
struct CharIndexer<1, 1, COUNTDOWN_C>
{
        template<unsigned SIZE_A, unsigned SIZE_B, unsigned SIZE_C, typename...
CHARS>
        static constexpr auto CreateChars(
                        const char (&str_a)[SIZE_A],
                        const char (&str_b)[SIZE_B],
                        const char (&str_c)[SIZE_C],
                        CHARS... chars)
        {
                return CharIndexer<1, 1, COUNTDOWN_C-1>::CreateChars(str_a,
str_b, str_c, chars..., str_c[SIZE_C-COUNTDOWN_C]);
        }
};

template<>
struct CharIndexer<1, 1, 1>
{
        template<unsigned SIZE_A, unsigned SIZE_B, unsigned SIZE_C, typename...
CHARS>
        static constexpr auto CreateChars(
                        const char (&str_a)[SIZE_A],
                        const char (&str_b)[SIZE_B],
                        const char (&str_c)[SIZE_C],
                        CHARS... chars)
        {
                return Message<CHARS...>(chars...);
        }
};

template<unsigned A, unsigned B, unsigned C>
constexpr auto concatenate(const char (&a)[A], const char (&b)[B], const char
(&c)[C])
{
        return CharIndexer<A,B,C>::CreateChars(a,b,c);
}

} // namespace MyLib

#if 0
#define THROW_SYSTEM_ERROR(ERROR_NO, CAUSE)                     \
do {                                                            \
        constexpr static auto what = MyLib::concatenate(        \
                "in '", __PRETTY_FUNCTION__, "' by '" CAUSE "'");       \
        throw std::system_error(ERROR_NO,                       \
                        std::system_category(), what.str);      \
} while(0)
#endif


#define THROW_SYSTEM_ERROR(ERROR_NO, CAUSE)                             \
        throw std::system_error(ERROR_NO, std::system_category(),       \
                MyLib::concatenate("in '", __PRETTY_FUNCTION__, "' by '" CAUSE
"'").str)


int main()
{
        try
        {
                THROW_SYSTEM_ERROR(EINVAL, "testfunc()");
        }
        catch(const std::system_error& exception)
        {
                std::cerr << "Exception " << exception.what() << " (" <<
exception.code() << ")" << std::endl;
        }

        return 0;
}
>From gcc-bugs-return-489961-listarch-gcc-bugs=gcc.gnu.org@gcc.gnu.org Tue Jun 23 13:19:07 2015
Return-Path: <gcc-bugs-return-489961-listarch-gcc-bugs=gcc.gnu.org@gcc.gnu.org>
Delivered-To: listarch-gcc-bugs@gcc.gnu.org
Received: (qmail 36803 invoked by alias); 23 Jun 2015 13:19:06 -0000
Mailing-List: contact gcc-bugs-help@gcc.gnu.org; run by ezmlm
Precedence: bulk
List-Id: <gcc-bugs.gcc.gnu.org>
List-Archive: <http://gcc.gnu.org/ml/gcc-bugs/>
List-Post: <mailto:gcc-bugs@gcc.gnu.org>
List-Help: <mailto:gcc-bugs-help@gcc.gnu.org>
Sender: gcc-bugs-owner@gcc.gnu.org
Delivered-To: mailing list gcc-bugs@gcc.gnu.org
Received: (qmail 36724 invoked by uid 48); 23 Jun 2015 13:19:03 -0000
From: "ramana at gcc dot gnu.org" <gcc-bugzilla@gcc.gnu.org>
To: gcc-bugs@gcc.gnu.org
Subject: [Bug target/65375] aarch64: poor codegen for vld2q_f32 and vst2q_f32
Date: Tue, 23 Jun 2015 13:19:00 -0000
X-Bugzilla-Reason: CC
X-Bugzilla-Type: changed
X-Bugzilla-Watch-Reason: None
X-Bugzilla-Product: gcc
X-Bugzilla-Component: target
X-Bugzilla-Version: 5.0
X-Bugzilla-Keywords:
X-Bugzilla-Severity: normal
X-Bugzilla-Who: ramana at gcc dot gnu.org
X-Bugzilla-Status: ASSIGNED
X-Bugzilla-Resolution:
X-Bugzilla-Priority: P3
X-Bugzilla-Assigned-To: kugan at gcc dot gnu.org
X-Bugzilla-Target-Milestone: ---
X-Bugzilla-Flags:
X-Bugzilla-Changed-Fields: cc
Message-ID: <bug-65375-4-KrvCNICs4j@http.gcc.gnu.org/bugzilla/>
In-Reply-To: <bug-65375-4@http.gcc.gnu.org/bugzilla/>
References: <bug-65375-4@http.gcc.gnu.org/bugzilla/>
Content-Type: text/plain; charset="UTF-8"
Content-Transfer-Encoding: 7bit
X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/
Auto-Submitted: auto-generated
MIME-Version: 1.0
X-SW-Source: 2015-06/txt/msg02293.txt.bz2
Content-length: 473

https://gcc.gnu.org/bugzilla/show_bug.cgi?ide375

Ramana Radhakrishnan <ramana at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |ramana at gcc dot gnu.org

--- Comment #9 from Ramana Radhakrishnan <ramana at gcc dot gnu.org> ---
Fixed by this then ?

https://gcc.gnu.org/ml/gcc-patches/2015-05/msg01776.html


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

* [Bug c++/66639] Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr
  2015-06-23 13:08 [Bug c++/66639] New: Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr simon at gleissner dot de
@ 2015-06-23 18:55 ` msebor at gcc dot gnu.org
  2015-06-24  9:26 ` simon at gleissner dot de
  2015-06-24 13:29 ` [Bug c++/66639] declare " manu at gcc dot gnu.org
  2 siblings, 0 replies; 4+ messages in thread
From: msebor at gcc dot gnu.org @ 2015-06-23 18:55 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66639

Martin Sebor <msebor at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |msebor at gcc dot gnu.org

--- Comment #2 from Martin Sebor <msebor at gcc dot gnu.org> ---
See also pr66561.

It might make sense to propose making __func__ constexpr as an enhancement or
even an unintended omission to WG21 (assuming making it constexpr doesn't break
anything).


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

* [Bug c++/66639] Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr
  2015-06-23 13:08 [Bug c++/66639] New: Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr simon at gleissner dot de
  2015-06-23 18:55 ` [Bug c++/66639] " msebor at gcc dot gnu.org
@ 2015-06-24  9:26 ` simon at gleissner dot de
  2015-06-24 13:29 ` [Bug c++/66639] declare " manu at gcc dot gnu.org
  2 siblings, 0 replies; 4+ messages in thread
From: simon at gleissner dot de @ 2015-06-24  9:26 UTC (permalink / raw)
  To: gcc-bugs

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66639

--- Comment #3 from Simon Gleissner <simon at gleissner dot de> ---
Hi *

> If at all, this could only be provided as compiler extension.

Good point. Yes, i think this would be a adequate solution.

> (assuming making it constexpr doesn't break anything)

... which IMHO could only be tested safely with an optional compiler switch.

I have modified the test program (see below), instead of __PRETTY_FUNCTION__ i
have declared a 'static constexpr const char testarray[]'. This works
perfectly, the concatenated string is now stored as a constant object in
section .rodata:

        .section        .rodata
        .align 32
        .type   _ZZ4mainE4what, @object
        .size   _ZZ4mainE4what, 37
_ZZ4mainE4what:
        .byte   105
        .byte   110
        .byte   32
        .byte   39
...

As 'testarray[]' is no longer needed after evaluating 'what', it is removed
completely (i have not found it in the .S file), therefore only the final
string is stored.


#define THROW_SYSTEM_ERROR(ERROR_NO, CAUSE)                     \
do{                                                             \
        constexpr static auto what = MyLib::concatenate(        \
                "in '", testarray, "' by '" CAUSE "'");         \
        throw std::system_error(ERROR_NO,                       \
                std::system_category(), what.str);              \
} while(0)

int main()
{
        try
        {
                static constexpr const char testarray[] = "constexprFunc()";

                THROW_SYSTEM_ERROR(EINVAL, "testfunc()");
        }
        catch(const std::system_error& exception)
        {
                std::cerr << "Exception " << exception.what() << " (" <<
exception.code() << ")" << std::endl;
        }

        return 0;
}


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

* [Bug c++/66639] declare __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr
  2015-06-23 13:08 [Bug c++/66639] New: Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr simon at gleissner dot de
  2015-06-23 18:55 ` [Bug c++/66639] " msebor at gcc dot gnu.org
  2015-06-24  9:26 ` simon at gleissner dot de
@ 2015-06-24 13:29 ` manu at gcc dot gnu.org
  2 siblings, 0 replies; 4+ messages in thread
From: manu at gcc dot gnu.org @ 2015-06-24 13:29 UTC (permalink / raw)
  To: gcc-bugs

[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1: Type: text/plain; charset="UTF-8", Size: 7108 bytes --]

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=66639

Manuel López-Ibáñez <manu at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
            Version|5.1.1                       |6.0
            Summary|Feature request C++: mark   |declare __func__ ,
                   |__func__ , __FUNCTION__ &   |__FUNCTION__ &
                   |__PRETTY_FUNCTION__ as      |__PRETTY_FUNCTION__ as
                   |constexpr                   |constexpr

--- Comment #4 from Manuel López-Ibáñez <manu at gcc dot gnu.org> ---
(In reply to Simon Gleissner from comment #3)
> > If at all, this could only be provided as compiler extension.
> 
> Good point. Yes, i think this would be a adequate solution.
> 
> > (assuming making it constexpr doesn't break anything)
> 
> ... which IMHO could only be tested safely with an optional compiler switch.

Due to past negative experiences, compiler extensions are only accepted under
very careful consideration and if they do not conflict with an existing (or
future) standard. Extensions accepted under an optional compiler switch are
even more rare: They add another very rarely tested point of failure and
increment the complexity of the compiler for very little benefit. The best
option is: create a tentative implementation, test it (by compiling and testing
GCC, libstdc++, boost, QT, Clang and other large C++ code bases) and propose
its standardization.
>From gcc-bugs-return-490068-listarch-gcc-bugs=gcc.gnu.org@gcc.gnu.org Wed Jun 24 13:34:46 2015
Return-Path: <gcc-bugs-return-490068-listarch-gcc-bugs=gcc.gnu.org@gcc.gnu.org>
Delivered-To: listarch-gcc-bugs@gcc.gnu.org
Received: (qmail 15159 invoked by alias); 24 Jun 2015 13:34:45 -0000
Mailing-List: contact gcc-bugs-help@gcc.gnu.org; run by ezmlm
Precedence: bulk
List-Id: <gcc-bugs.gcc.gnu.org>
List-Archive: <http://gcc.gnu.org/ml/gcc-bugs/>
List-Post: <mailto:gcc-bugs@gcc.gnu.org>
List-Help: <mailto:gcc-bugs-help@gcc.gnu.org>
Sender: gcc-bugs-owner@gcc.gnu.org
Delivered-To: mailing list gcc-bugs@gcc.gnu.org
Received: (qmail 15133 invoked by uid 48); 24 Jun 2015 13:34:41 -0000
From: "public at alisdairm dot net" <gcc-bugzilla@gcc.gnu.org>
To: gcc-bugs@gcc.gnu.org
Subject: [Bug c++/66649] New: variable template specializations not being found
Date: Wed, 24 Jun 2015 13:34:00 -0000
X-Bugzilla-Reason: CC
X-Bugzilla-Type: new
X-Bugzilla-Watch-Reason: None
X-Bugzilla-Product: gcc
X-Bugzilla-Component: c++
X-Bugzilla-Version: 5.1.1
X-Bugzilla-Keywords:
X-Bugzilla-Severity: normal
X-Bugzilla-Who: public at alisdairm dot net
X-Bugzilla-Status: UNCONFIRMED
X-Bugzilla-Resolution:
X-Bugzilla-Priority: P3
X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org
X-Bugzilla-Target-Milestone: ---
X-Bugzilla-Flags:
X-Bugzilla-Changed-Fields: bug_id short_desc product version bug_status bug_severity priority component assigned_to reporter target_milestone attachments.created
Message-ID: <bug-66649-4@http.gcc.gnu.org/bugzilla/>
Content-Type: text/plain; charset="UTF-8"
Content-Transfer-Encoding: 7bit
X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/
Auto-Submitted: auto-generated
MIME-Version: 1.0
X-SW-Source: 2015-06/txt/msg02400.txt.bz2
Content-length: 3672

https://gcc.gnu.org/bugzilla/show_bug.cgi?idf649

            Bug ID: 66649
           Summary: variable template specializations not being found
           Product: gcc
           Version: 5.1.1
            Status: UNCONFIRMED
          Severity: normal
          Priority: P3
         Component: c++
          Assignee: unassigned at gcc dot gnu.org
          Reporter: public at alisdairm dot net
  Target Milestone: ---

Created attachment 35841
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id5841&actioníit
C++ code that should compile in C++14 mode, but fails

The attached file shows a simple test case for variable templates that I
believe is correct, and passes with Clang:

template <typename T, typename U>
constexpr bool is_same_v = false;

template <typename T>
constexpr bool is_same_v<T, T> = true;

template <typename T>
auto make() -> T;

template <typename T>
void AssertMakeSame() {
   static_assert( is_same_v<T, T>, "Type should be the same as itself");
   static_assert( is_same_v<decltype(make<T>()), T>, "make should produce the
same type");
};

int main() {
   AssertMakeSame<int>();
// AssertMakeSame<int const>();  // Should be an error
   AssertMakeSame<int *>();
}


In gcc 5, I get an error that the partial specialization must be at namespace
scope, but this appears to be fixed in trunk.  However, all 4 static asserts
fire in both trunk and 5.

Tested with:
g++ -v
Using built-in specs.
COLLECT_GCC=g++
COLLECT_LTO_WRAPPER=/opt/local/libexec/gcc/x86_64-apple-darwin14/6.0.0/lto-wrapper
Target: x86_64-apple-darwin14
Configured with:
/opt/local/var/macports/build/_opt_local_var_macports_sources_rsync.macports.org_release_tarballs_ports_lang_gcc6/gcc6/work/gcc-6-20150614/configure
--prefix=/opt/local --build=x86_64-apple-darwin14
--enable-languages=c,c++,objc,obj-c++,lto,fortran,java
--libdir=/opt/local/lib/gcc6 --includedir=/opt/local/include/gcc6
--infodir=/opt/local/share/info --mandir=/opt/local/share/man
--datarootdir=/opt/local/share/gcc-6 --with-local-prefix=/opt/local
--with-system-zlib --disable-nls --program-suffix=-mp-6
--with-gxx-include-dir=/opt/local/include/gcc6/c++/ --with-gmp=/opt/local
--with-mpfr=/opt/local --with-mpc=/opt/local --with-isl=/opt/local
--enable-stage1-checking --disable-multilib --enable-lto
--enable-libstdcxx-time --with-as=/opt/local/bin/as --with-ld=/opt/local/bin/ld
--with-ar=/opt/local/bin/ar --with-bugurl=https://trac.macports.org/newticket
--with-pkgversion='MacPorts gcc6 6-20150614_0'
Thread model: posix
gcc version 6.0.0 20150614 (experimental) (MacPorts gcc6 6-20150614_0)


and with:
g++ -v
Using built-in specs.
COLLECT_GCC=g++
COLLECT_LTO_WRAPPER=/opt/local/libexec/gcc/x86_64-apple-darwin14/5.1.0/lto-wrapper
Target: x86_64-apple-darwin14
Configured with:
/opt/local/var/macports/build/_opt_mports_dports_lang_gcc5/gcc5/work/gcc-5.1.0/configure
--prefix=/opt/local --build=x86_64-apple-darwin14
--enable-languages=c,c++,objc,obj-c++,lto,fortran,java
--libdir=/opt/local/lib/gcc5 --includedir=/opt/local/include/gcc5
--infodir=/opt/local/share/info --mandir=/opt/local/share/man
--datarootdir=/opt/local/share/gcc-5 --with-local-prefix=/opt/local
--with-system-zlib --disable-nls --program-suffix=-mp-5
--with-gxx-include-dir=/opt/local/include/gcc5/c++/ --with-gmp=/opt/local
--with-mpfr=/opt/local --with-mpc=/opt/local --with-isl=/opt/local
--enable-stage1-checking --disable-multilib --enable-lto
--enable-libstdcxx-time --with-as=/opt/local/bin/as --with-ld=/opt/local/bin/ld
--with-ar=/opt/local/bin/ar --with-bugurl=https://trac.macports.org/newticket
--with-pkgversion='MacPorts gcc5 5.1.0_1'
Thread model: posix
gcc version 5.1.0 (MacPorts gcc5 5.1.0_1)


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

end of thread, other threads:[~2015-06-24 13:29 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-06-23 13:08 [Bug c++/66639] New: Feature request C++: mark __func__ , __FUNCTION__ & __PRETTY_FUNCTION__ as constexpr simon at gleissner dot de
2015-06-23 18:55 ` [Bug c++/66639] " msebor at gcc dot gnu.org
2015-06-24  9:26 ` simon at gleissner dot de
2015-06-24 13:29 ` [Bug c++/66639] declare " manu at gcc dot gnu.org

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).