typeid.h revision 12391
112391Sjason@lowepower.com/*
212391Sjason@lowepower.com    pybind11/detail/typeid.h: Compiler-independent access to type identifiers
312391Sjason@lowepower.com
412391Sjason@lowepower.com    Copyright (c) 2016 Wenzel Jakob <wenzel.jakob@epfl.ch>
512391Sjason@lowepower.com
612391Sjason@lowepower.com    All rights reserved. Use of this source code is governed by a
712391Sjason@lowepower.com    BSD-style license that can be found in the LICENSE file.
812391Sjason@lowepower.com*/
912391Sjason@lowepower.com
1012391Sjason@lowepower.com#pragma once
1112391Sjason@lowepower.com
1212391Sjason@lowepower.com#include <cstdio>
1312391Sjason@lowepower.com#include <cstdlib>
1412391Sjason@lowepower.com
1512391Sjason@lowepower.com#if defined(__GNUG__)
1612391Sjason@lowepower.com#include <cxxabi.h>
1712391Sjason@lowepower.com#endif
1812391Sjason@lowepower.com
1912391Sjason@lowepower.comNAMESPACE_BEGIN(PYBIND11_NAMESPACE)
2012391Sjason@lowepower.comNAMESPACE_BEGIN(detail)
2112391Sjason@lowepower.com/// Erase all occurrences of a substring
2212391Sjason@lowepower.cominline void erase_all(std::string &string, const std::string &search) {
2312391Sjason@lowepower.com    for (size_t pos = 0;;) {
2412391Sjason@lowepower.com        pos = string.find(search, pos);
2512391Sjason@lowepower.com        if (pos == std::string::npos) break;
2612391Sjason@lowepower.com        string.erase(pos, search.length());
2712391Sjason@lowepower.com    }
2812391Sjason@lowepower.com}
2912391Sjason@lowepower.com
3012391Sjason@lowepower.comPYBIND11_NOINLINE inline void clean_type_id(std::string &name) {
3112391Sjason@lowepower.com#if defined(__GNUG__)
3212391Sjason@lowepower.com    int status = 0;
3312391Sjason@lowepower.com    std::unique_ptr<char, void (*)(void *)> res {
3412391Sjason@lowepower.com        abi::__cxa_demangle(name.c_str(), nullptr, nullptr, &status), std::free };
3512391Sjason@lowepower.com    if (status == 0)
3612391Sjason@lowepower.com        name = res.get();
3712391Sjason@lowepower.com#else
3812391Sjason@lowepower.com    detail::erase_all(name, "class ");
3912391Sjason@lowepower.com    detail::erase_all(name, "struct ");
4012391Sjason@lowepower.com    detail::erase_all(name, "enum ");
4112391Sjason@lowepower.com#endif
4212391Sjason@lowepower.com    detail::erase_all(name, "pybind11::");
4312391Sjason@lowepower.com}
4412391Sjason@lowepower.comNAMESPACE_END(detail)
4512391Sjason@lowepower.com
4612391Sjason@lowepower.com/// Return a string representation of a C++ type
4712391Sjason@lowepower.comtemplate <typename T> static std::string type_id() {
4812391Sjason@lowepower.com    std::string name(typeid(T).name());
4912391Sjason@lowepower.com    detail::clean_type_id(name);
5012391Sjason@lowepower.com    return name;
5112391Sjason@lowepower.com}
5212391Sjason@lowepower.com
5312391Sjason@lowepower.comNAMESPACE_END(PYBIND11_NAMESPACE)
54