vn-verdnaturachat/ios/Pods/Flipper-Folly/folly/lang/Pretty.h

160 lines
4.2 KiB
C++

/*
* Copyright (c) Facebook, Inc. and its affiliates.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#pragma once
#include <cstddef>
#include <type_traits>
#include <folly/Portability.h>
namespace folly {
namespace detail {
template <std::size_t S>
struct pretty_carray {
char data[S];
};
template <std::size_t S>
static constexpr pretty_carray<S> pretty_carray_from(char const (&in)[S]) {
pretty_carray<S> out{};
for (std::size_t i = 0; i < S; ++i) {
out.data[i] = in[i];
}
return out;
}
struct pretty_info {
std::size_t b;
std::size_t e;
};
template <typename To, std::size_t S>
static constexpr To pretty_info_to(pretty_info info, char const (&name)[S]) {
return To(name + info.b, info.e - info.b);
}
template <std::size_t S>
static constexpr std::size_t pretty_lfind(
char const (&haystack)[S],
char const needle) {
for (std::size_t i = 0; i < S - 1; ++i) {
if (haystack[i] == needle) {
return i;
}
}
return ~std::size_t(0);
}
template <std::size_t S>
static constexpr std::size_t pretty_rfind(
char const (&haystack)[S],
char const needle) {
for (std::size_t i = S; i != 0; --i) {
if (haystack[i - 1] == needle) {
return i - 1;
}
}
return ~std::size_t(0);
}
struct pretty_tag_msc {};
struct pretty_tag_gcc {};
using pretty_default_tag = std::conditional_t< //
kMscVer && !kIsClang,
pretty_tag_msc,
pretty_tag_gcc>;
template <typename T>
static constexpr auto pretty_raw(pretty_tag_msc) {
#if defined(_MSC_VER)
return pretty_carray_from(__FUNCSIG__);
#endif
}
template <typename T>
static constexpr auto pretty_raw(pretty_tag_gcc) {
#if defined(__GNUC__) || defined(__clang__)
return pretty_carray_from(__PRETTY_FUNCTION__);
#endif
}
template <std::size_t S>
static constexpr pretty_info pretty_parse(
pretty_tag_msc,
char const (&name)[S]) {
// void __cdecl folly::detail::pretty_raw<{...}>(
// folly::detail::pretty_tag_msc)
auto const la = pretty_lfind(name, '<');
auto const rp = pretty_rfind(name, '>');
return pretty_info{la + 1, rp};
}
template <std::size_t S>
static constexpr pretty_info pretty_parse(
pretty_tag_gcc,
char const (&name)[S]) {
// void folly::detail::pretty_raw(
// folly::detail::pretty_tag_gcc) [T = {...}]
auto const eq = pretty_lfind(name, '=');
auto const br = pretty_rfind(name, ']');
return pretty_info{eq + 2, br};
}
template <typename T, typename Tag>
struct pretty_name_zarray {
static constexpr auto raw_() {
constexpr auto const raw_ = pretty_raw<T>(Tag{});
return raw_;
}
static constexpr auto raw = raw_(); // indirection b/c of gcc-5.3 ice, gh#1105
static constexpr auto info = pretty_parse(Tag{}, raw.data);
static constexpr auto size = info.e - info.b;
static constexpr auto zarray_() {
pretty_carray<size + 1> data{};
for (std::size_t i = 0; i < size; ++i) {
data.data[i] = raw.data[info.b + i];
}
data.data[size] = 0;
return data;
}
static constexpr pretty_carray<size + 1> zarray = zarray_();
};
template <typename T, typename Tag>
constexpr pretty_carray<pretty_name_zarray<T, Tag>::size + 1>
pretty_name_zarray<T, Tag>::zarray;
} // namespace detail
// pretty_name
//
// Returns a statically-allocated C string containing the pretty name of T.
//
// The pretty name of a type varies by compiler, may include tokens which
// would not be present in the type name as it is spelled in the source code
// or as it would be symbolized, and may not include tokens which would be
// present in the type name as it would be symbolized.
template <typename T>
constexpr char const* pretty_name() {
return detail::pretty_name_zarray<T, detail::pretty_default_tag>::zarray.data;
}
} // namespace folly