alpaka-group / alpaka

Abstraction Library for Parallel Kernel Acceleration :llama:
https://alpaka.readthedocs.io
Mozilla Public License 2.0
356 stars 74 forks source link

remove boost demangle #2405

Open psychocoderHPC opened 1 month ago

psychocoderHPC commented 1 month ago

https://github.com/alpaka-group/alpaka/blob/e20236d86be9a8093fa2efae44eaf2db79dc38db/include/alpaka/core/DemangleTypeNames.hpp#L18-L19

We aim to remove boost completely. With clang 15+ and gcc 11+ we can remove this code with the following code. These versions support std::source_location.

#include <source_location>
#include <string>
#include <string_view>
    /// \file
    /// use source_location to derive the demangled type name
    /// based on:
    /// https://www.reddit.com/r/cpp/comments/lfi6jt/finally_a_possibly_portable_way_to_convert_types/?utm_source=share&utm_medium=web3x&utm_name=web3xcss&utm_term=1&utm_content=share_button

    struct DummyType
    {
    };

    template<typename T>
    inline auto EmbedTypeIntoSignature()
    {
        return std::string_view{std::source_location::current().function_name()};
    }

    template<typename T>
    struct Demangled
    {
        static auto name()
        {
            constexpr size_t testSignatureLength = sizeof("DummyType") - 1;
            auto const DummySignature = EmbedTypeIntoSignature<DummyType>();
            // count char's until the type name starts
            auto const startPosition = DummySignature.find("DummyType");
            // count char's after the type information by removing type name information and pre information
            auto const tailLength = DummySignature.size() - startPosition - testSignatureLength;
            auto const EmbeddingSignature = EmbedTypeIntoSignature<T>();
            auto const typeLength = EmbeddingSignature.size() - startPosition - tailLength;
            return EmbeddingSignature.substr(startPosition, typeLength);
        }
    };

    template<typename T>
    auto demangled = Demangled<T>::name();
fwyzard commented 1 month ago

Can it be constexpr ?

fwyzard commented 1 month ago

In general, I do not share the "remove boost at all costs" goal, so to me the new implementation needs to be at least as good as the old one, or possibly better.

SimeonEhrig commented 1 month ago

std::source_location::current() is actual pretty well. I think it is more a question if we want remove the compilers, which does not support std::source_location::current().

SimeonEhrig commented 1 month ago

@fwyzard If you want, you can test it here: https://godbolt.org/z/P6MsrKTKv

Update: a more advanced example with namespace: https://godbolt.org/z/159Gs313h

SimeonEhrig commented 1 month ago

Can it be constexpr ?

Yes. My minimal example produces only 15 lines assembler including printing: https://godbolt.org/z/YhxKx6n3W (looks like there is a small bug with the string termination symbol \0).

fwyzard commented 1 month ago

Can it be constexpr ?

Yes: https://godbolt.org/z/cbKdEPz4q .

psychocoderHPC commented 1 month ago

Can it be constexpr ?

It was first constexpr but in some places, it produced some issues.

psychocoderHPC commented 1 month ago

In general, I do not share the "remove boost at all costs" goal, so to me the new implementation needs to be at least as good as the old one, or possibly better.

I understand, the motivation was always that boost is not testing nvcc and HIP and this produced in the past many issues. Nevertheless this implementation is doing what it should. Removing boost will reduce the test complexity a lot.

fwyzard commented 1 month ago

Note that GCC and clang produce different output in some cases, for example for std::string:

gcc

the name is: std::__cxx11::basic_string<char>

clang

the name is: std::basic_string<char>

But maybe the old one was also doing this ?

fwyzard commented 1 month ago

Ah, looks like the two give a different output for inline namespaces.

inline namespace nested {
    struct Type {};
}

int main(){
    std::cout << "the name is: " << demangled<Type> << '\n';
}

Gives:

gcc

the name is: nested::Type

clang

the name is: Type