rosa/inc/tmp/debug.h
2021-05-10 18:14:24 +02:00

79 lines
2.0 KiB
C++

#ifndef TMP_DEBUG_H
#define TMP_DEBUG_H
/**
* @file tmp/debug.h
* @brief compile-time typename to string resolution
*
* see: https://stackoverflow.com/questions/81870/is-it-possible-to-print-a-variables-type-in-standard-c
* see: https://stackoverflow.com/a/20170989
*
* Adapted, minimal C++ version supported is C++14
*/
#include <cstdio>
#include "stringview.h"
namespace tmp {
namespace detail {
constexpr unsigned strlen(char const*str) {
unsigned l = 0;
while(*str++) ++l;
return l;
}
}
/**
* @brief compile-time typename to string resolution
*
* @param[in] T type to resolve
*
* @return constexpr string_view containing the typename
*
* TODO this function has not been tested for Windows
*/
template<typename T>
constexpr string_view typeName() {
#if defined(__clang__)
string_view p = __PRETTY_FUNCTION__;
constexpr auto leftDummy = detail::strlen("tmp::string_view tmp::typeName() [T = ");
constexpr auto rightDummy = detail::strlen("]");
#elif defined(__GNUC__)
string_view p = __PRETTY_FUNCTION__;
constexpr auto leftDummy = detail::strlen("constexpr tmp::string_view tmp::typeName() [with T = ");
constexpr auto rightDummy = detail::strlen("]");
#elif defined(_MSC_VER)
string_view p = __FUNCSIG__;
constexpr auto leftDummy = detail::strlen("");
constexpr auto rightDummy = detail::strlen("");
#else
return {"[err: tmp::typeNameF is not implemented for your compiler]"};
#endif
#if defined(__clang__) || defined(__GNUC__) || defined(__MSC_VER)
return string_view(p.data() + leftDummy, p.size() - leftDummy - rightDummy);
#endif
}
template<typename... As, typename... Ts>
std::string strTypes(Ts...) {
using Fold = int[];
std::string result;
static_cast<void>(Fold{(result += std::string{typeName<As>()} + ", ", 0)...});
static_cast<void>(Fold{(result += std::string{typeName<Ts>()} + ", ", 0)...});
if(result.empty()) return "";
else return result.substr(0, result.size()-2);
}
template<typename... As, typename... Ts>
void printTypes(Ts...) {
std::puts(strTypes<As..., Ts...>().c_str());
}
}
#endif