LLVM 22.0.0git
TypeName.h
Go to the documentation of this file.
1//===- TypeName.h -----------------------------------------------*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef LLVM_SUPPORT_TYPENAME_H
10#define LLVM_SUPPORT_TYPENAME_H
11
12#include <string_view>
13
14#include "llvm/ADT/StringRef.h"
15
16// Versions of GCC prior to GCC 9 don't declare __PRETTY_FUNCTION__ as constexpr
17#if defined(__clang__) || defined(_MSC_VER) || \
18 (defined(__GNUC__) && __GNUC__ >= 9)
19#define LLVM_GET_TYPE_NAME_CONSTEXPR constexpr
20#define LLVM_GET_TYPE_NAME_STATIC_ASSERT 1
21#else
22#define LLVM_GET_TYPE_NAME_CONSTEXPR
23#define LLVM_GET_TYPE_NAME_STATIC_ASSERT 0
24#include <cassert>
25#endif
26
27namespace llvm {
28
29/// We provide a function which tries to compute the (demangled) name of a type
30/// statically.
31///
32/// This routine may fail on some platforms or for particularly unusual types.
33/// Do not use it for anything other than logging and debugging aids. It isn't
34/// portable or dependendable in any real sense.
35///
36/// The returned StringRef will point into a static storage duration string.
37/// However, it may not be null terminated and may be some strangely aligned
38/// inner substring of a larger string.
39template <typename DesiredTypeName>
41#if defined(__clang__) || defined(__GNUC__)
42 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view Name = __PRETTY_FUNCTION__;
43
44 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view Key = "DesiredTypeName = ";
45 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view TemplateParamsStart =
46 Name.substr(Name.find(Key));
47#if LLVM_GET_TYPE_NAME_STATIC_ASSERT
48 static_assert(!TemplateParamsStart.empty(),
49 "Unable to find the template parameter!");
50#else
51 assert(!TemplateParamsStart.empty() &&
52 "Unable to find the template parameter!");
53#endif
54
55 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view SubstitutionKey =
56 TemplateParamsStart.substr(Key.size());
57
58#if LLVM_GET_TYPE_NAME_STATIC_ASSERT
59 // ends_with() is only available in c++20
60 static_assert(!SubstitutionKey.empty() && SubstitutionKey.back() == ']',
61 "Name doesn't end in the substitution key!");
62#else
63 assert(!SubstitutionKey.empty() && SubstitutionKey.back() == ']' &&
64 "Name doesn't end in the substitution key!");
65#endif
66
67 return SubstitutionKey.substr(0, SubstitutionKey.size() - 1);
68#elif defined(_MSC_VER)
69 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view Name = __FUNCSIG__;
70
71 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view Key = "getTypeName<";
72 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view GetTypeNameStart =
73 Name.substr(Name.find(Key));
74 static_assert(!GetTypeNameStart.empty(),
75 "Unable to find the template parameter!");
76 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view SubstitutionKey =
77 GetTypeNameStart.substr(Key.size());
78
79 // starts_with() only available in c++20
80 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view RmPrefixClass =
81 SubstitutionKey.find("class ") == 0
82 ? SubstitutionKey.substr(sizeof("class ") - 1)
83 : SubstitutionKey;
84 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view RmPrefixStruct =
85 RmPrefixClass.find("struct ") == 0
86 ? RmPrefixClass.substr(sizeof("struct ") - 1)
87 : RmPrefixClass;
88 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view RmPrefixUnion =
89 RmPrefixStruct.find("union ") == 0
90 ? RmPrefixStruct.substr(sizeof("union ") - 1)
91 : RmPrefixStruct;
92 LLVM_GET_TYPE_NAME_CONSTEXPR std::string_view RmPrefixEnum =
93 RmPrefixUnion.find("enum ") == 0
94 ? RmPrefixUnion.substr(sizeof("enum ") - 1)
95 : RmPrefixUnion;
96
97 LLVM_GET_TYPE_NAME_CONSTEXPR auto AnglePos = RmPrefixEnum.rfind('>');
98 static_assert(AnglePos != std::string_view::npos,
99 "Unable to find the closing '>'!");
100 return RmPrefixEnum.substr(0, AnglePos);
101#else
102 // No known technique for statically extracting a type name on this compiler.
103 // We return a string that is unlikely to look like any type in LLVM.
104 return "UNKNOWN_TYPE";
105#endif
106}
107
108} // namespace llvm
109
110// Don't leak out of this header file
111#undef LLVM_GET_TYPE_NAME_CONSTEXPR
112#undef LLVM_GET_TYPE_NAME_STATIC_ASSERT
113
114#endif
assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")
std::string Name
#define LLVM_GET_TYPE_NAME_CONSTEXPR
Definition: TypeName.h:22
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:55
This is an optimization pass for GlobalISel generic memory operations.
Definition: AddressRanges.h:18
LLVM_GET_TYPE_NAME_CONSTEXPR StringRef getTypeName()
We provide a function which tries to compute the (demangled) name of a type statically.
Definition: TypeName.h:40