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

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