static type traits and kinds

This commit is contained in:
BlackMATov
2021-11-22 14:12:08 +07:00
parent 0cf2a0b07b
commit e729c67b8d
15 changed files with 970 additions and 6 deletions

View File

@@ -6,4 +6,19 @@
#pragma once
#include "meta_fwd.hpp"
#include "meta_base.hpp"
#include "meta_kinds.hpp"
#include "meta_traits.hpp"
#include "meta_traits/array_traits.hpp"
#include "meta_traits/class_traits.hpp"
#include "meta_traits/ctor_traits.hpp"
#include "meta_traits/enum_traits.hpp"
#include "meta_traits/function_traits.hpp"
#include "meta_traits/member_traits.hpp"
#include "meta_traits/method_traits.hpp"
#include "meta_traits/number_traits.hpp"
#include "meta_traits/pointer_traits.hpp"
#include "meta_traits/reference_traits.hpp"
#include "meta_traits/void_traits.hpp"

View File

@@ -0,0 +1,182 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include <cassert>
#include <cstddef>
#include <cstdint>
#include <algorithm>
#include <any>
#include <array>
#include <atomic>
#include <concepts>
#include <functional>
#include <initializer_list>
#include <iosfwd>
#include <map>
#include <memory>
#include <optional>
#include <set>
#include <stdexcept>
#include <string_view>
#include <string>
#include <tuple>
#include <type_traits>
#include <utility>
#include <vector>
#include <enum.hpp/enum.hpp>
#include <enum.hpp/enum_bitflags.hpp>
namespace meta_hpp
{
template < typename Enum >
using bitflags = enum_hpp::bitflags::bitflags<Enum>;
}
namespace meta_hpp
{
template < typename... Types >
struct type_list {};
template < std::size_t Index, typename TypeList >
struct type_list_at;
template < std::size_t Index, typename... Types >
struct type_list_at<Index, type_list<Types...>> {
using type = std::tuple_element_t<Index, std::tuple<Types...>>;
};
template < std::size_t Index, typename TypeList >
using type_list_at_t = typename type_list_at<Index, TypeList>::type;
}
namespace meta_hpp
{
template < typename Signature >
constexpr auto select(Signature* func) noexcept -> Signature* {
return func;
}
template < typename Signature, typename Class >
constexpr auto select(Signature Class::*func) -> decltype(func) {
return func;
}
}
namespace meta_hpp
{
class value;
namespace detail
{
class arg_base;
class arg;
class inst_base;
class inst;
}
}
namespace meta_hpp
{
class ctor;
class evalue;
class function;
class member;
class method;
class scope;
class variable;
namespace detail
{
struct ctor_state;
struct evalue_state;
struct function_state;
struct member_state;
struct method_state;
struct scope_state;
struct variable_state;
using ctor_state_ptr = std::shared_ptr<ctor_state>;
using evalue_state_ptr = std::shared_ptr<evalue_state>;
using function_state_ptr = std::shared_ptr<function_state>;
using member_state_ptr = std::shared_ptr<member_state>;
using method_state_ptr = std::shared_ptr<method_state>;
using scope_state_ptr = std::shared_ptr<scope_state>;
using variable_state_ptr = std::shared_ptr<variable_state>;
}
}
namespace meta_hpp
{
class any_type;
class array_type;
class class_type;
class ctor_type;
class enum_type;
class function_type;
class member_type;
class method_type;
class number_type;
class pointer_type;
class reference_type;
class void_type;
namespace detail
{
struct type_data_base;
struct array_type_data;
struct class_type_data;
struct ctor_type_data;
struct enum_type_data;
struct function_type_data;
struct member_type_data;
struct method_type_data;
struct number_type_data;
struct pointer_type_data;
struct reference_type_data;
struct void_type_data;
using type_data_base_ptr = std::shared_ptr<type_data_base>;
using array_type_data_ptr = std::shared_ptr<array_type_data>;
using class_type_data_ptr = std::shared_ptr<class_type_data>;
using ctor_type_data_ptr = std::shared_ptr<ctor_type_data>;
using enum_type_data_ptr = std::shared_ptr<enum_type_data>;
using function_type_data_ptr = std::shared_ptr<function_type_data>;
using member_type_data_ptr = std::shared_ptr<member_type_data>;
using method_type_data_ptr = std::shared_ptr<method_type_data>;
using number_type_data_ptr = std::shared_ptr<number_type_data>;
using pointer_type_data_ptr = std::shared_ptr<pointer_type_data>;
using reference_type_data_ptr = std::shared_ptr<reference_type_data>;
using void_type_data_ptr = std::shared_ptr<void_type_data>;
}
}
namespace meta_hpp
{
struct ctor_index;
struct evalue_index;
struct function_index;
struct member_index;
struct method_index;
struct variable_index;
using class_set = std::set<class_type, std::less<>>;
using class_map = std::map<std::string, class_type, std::less<>>;
using enum_set = std::set<enum_type, std::less<>>;
using enum_map = std::map<std::string, enum_type, std::less<>>;
using ctor_map = std::map<ctor_index, ctor, std::less<>>;
using evalue_map = std::map<evalue_index, evalue, std::less<>>;
using function_map = std::map<function_index, function, std::less<>>;
using member_map = std::map<member_index, member, std::less<>>;
using method_map = std::map<method_index, method, std::less<>>;
using variable_map = std::map<variable_index, variable, std::less<>>;
}

View File

@@ -0,0 +1,154 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "meta_base.hpp"
namespace meta_hpp
{
template < typename T >
concept array_kind = std::is_array_v<T>;
template < typename T >
concept class_kind = std::is_class_v<T>;
template < typename T >
concept enum_kind = std::is_enum_v<T>;
template < typename T >
concept function_kind = std::is_pointer_v<T> && std::is_function_v<std::remove_pointer_t<T>>;
template < typename T >
concept member_kind = std::is_member_object_pointer_v<T>;
template < typename T >
concept method_kind = std::is_member_function_pointer_v<T>;
template < typename T >
concept number_kind = std::is_arithmetic_v<T>;
template < typename T >
concept pointer_kind = std::is_pointer_v<T> && !std::is_function_v<std::remove_pointer_t<T>>;
template < typename T >
concept reference_kind = std::is_reference_v<T>;
template < typename T >
concept void_kind = std::is_void_v<T>;
}
namespace meta_hpp
{
enum class type_kind : std::uint32_t {
array_,
class_,
ctor_,
enum_,
function_,
member_,
method_,
number_,
pointer_,
reference_,
void_,
};
template < typename T >
constexpr type_kind make_type_kind() noexcept {
if constexpr ( array_kind<T> ) { return type_kind::array_; }
if constexpr ( class_kind<T> ) { return type_kind::class_; }
if constexpr ( enum_kind<T> ) { return type_kind::enum_; }
if constexpr ( function_kind<T> ) { return type_kind::function_; }
if constexpr ( member_kind<T> ) { return type_kind::member_; }
if constexpr ( method_kind<T> ) { return type_kind::method_; }
if constexpr ( number_kind<T> ) { return type_kind::number_; }
if constexpr ( pointer_kind<T> ) { return type_kind::pointer_; }
if constexpr ( reference_kind<T> ) { return type_kind::reference_; }
if constexpr ( void_kind<T> ) { return type_kind::void_; }
}
}
namespace meta_hpp::detail
{
template < type_kind Kind >
struct type_kind_traits;
template <>
struct type_kind_traits<type_kind::array_> {
using kind_type = array_type;
using kind_type_data = array_type_data;
};
template <>
struct type_kind_traits<type_kind::class_> {
using kind_type = class_type;
using kind_type_data = class_type_data;
};
template <>
struct type_kind_traits<type_kind::ctor_> {
using kind_type = ctor_type;
using kind_type_data = ctor_type_data;
};
template <>
struct type_kind_traits<type_kind::enum_> {
using kind_type = enum_type;
using kind_type_data = enum_type_data;
};
template <>
struct type_kind_traits<type_kind::function_> {
using kind_type = function_type;
using kind_type_data = function_type_data;
};
template <>
struct type_kind_traits<type_kind::member_> {
using kind_type = member_type;
using kind_type_data = member_type_data;
};
template <>
struct type_kind_traits<type_kind::method_> {
using kind_type = method_type;
using kind_type_data = method_type_data;
};
template <>
struct type_kind_traits<type_kind::number_> {
using kind_type = number_type;
using kind_type_data = number_type_data;
};
template <>
struct type_kind_traits<type_kind::pointer_> {
using kind_type = pointer_type;
using kind_type_data = pointer_type_data;
};
template <>
struct type_kind_traits<type_kind::reference_> {
using kind_type = reference_type;
using kind_type_data = reference_type_data;
};
template <>
struct type_kind_traits<type_kind::void_> {
using kind_type = void_type;
using kind_type_data = void_type_data;
};
template < typename T >
using kind_type = typename type_kind_traits<make_type_kind<T>()>::kind_type;
template < typename T >
using kind_type_data = typename type_kind_traits<make_type_kind<T>()>::kind_type_data;
template < typename T >
using kind_type_data_ptr = std::shared_ptr<kind_type_data<T>>;
}

View File

@@ -0,0 +1,116 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "meta_base.hpp"
#include "meta_kinds.hpp"
namespace meta_hpp::detail
{
template < array_kind Array >
struct array_traits;
template < class_kind T >
struct class_traits;
template < class_kind Class, typename... Args >
struct ctor_traits;
template < enum_kind Enum >
struct enum_traits;
template < function_kind Function >
struct function_traits;
template < member_kind Member >
struct member_traits;
template < method_kind Method >
struct method_traits;
template < number_kind Number >
struct number_traits;
template < pointer_kind Pointer >
struct pointer_traits;
template < reference_kind Reference >
struct reference_traits;
template < void_kind Void >
struct void_traits;
}
namespace meta_hpp
{
enum class array_flags : std::uint32_t {
is_bounded = 1 << 0,
is_unbounded = 1 << 1,
};
enum class class_flags : std::uint32_t {
is_empty = 1 << 1,
is_final = 1 << 2,
is_abstract = 1 << 3,
is_polymorphic = 1 << 4,
is_template_instantiation = 1 << 5,
};
enum class ctor_flags : std::uint32_t {
is_noexcept = 1 << 0,
};
enum class enum_flags : std::uint32_t {
};
enum class function_flags : std::uint32_t {
is_noexcept = 1 << 0,
};
enum class member_flags : std::uint32_t {
};
enum class method_flags : std::uint32_t {
is_const = 1 << 0,
is_noexcept = 1 << 1,
is_volatile = 1 << 2,
is_lvalue_qualified = 1 << 3,
is_rvalue_qualified = 1 << 4,
};
enum class number_flags : std::uint32_t {
is_signed = 1 << 1,
is_unsigned = 1 << 2,
is_integral = 1 << 3,
is_floating_point = 1 << 4,
};
enum class pointer_flags : std::uint32_t {
is_readonly = 1 << 0,
};
enum class reference_flags : std::uint32_t {
is_readonly = 1 << 0,
is_lvalue = 1 << 1,
is_rvalue = 1 << 2,
};
enum class void_flags : std::uint32_t {
};
ENUM_HPP_OPERATORS_DECL(array_flags)
ENUM_HPP_OPERATORS_DECL(class_flags)
ENUM_HPP_OPERATORS_DECL(ctor_flags)
ENUM_HPP_OPERATORS_DECL(enum_flags)
ENUM_HPP_OPERATORS_DECL(function_flags)
ENUM_HPP_OPERATORS_DECL(member_flags)
ENUM_HPP_OPERATORS_DECL(method_flags)
ENUM_HPP_OPERATORS_DECL(number_flags)
ENUM_HPP_OPERATORS_DECL(pointer_flags)
ENUM_HPP_OPERATORS_DECL(reference_flags)
ENUM_HPP_OPERATORS_DECL(void_flags)
}

View File

@@ -0,0 +1,27 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < array_kind Array >
struct array_traits {
static constexpr std::size_t extent{std::extent_v<Array>};
using data_type = std::remove_extent_t<Array>;
static bitflags<array_flags> make_flags() noexcept {
bitflags<array_flags> flags;
if ( std::is_bounded_array_v<Array> ) flags.set(array_flags::is_bounded);
if ( std::is_unbounded_array_v<Array> ) flags.set(array_flags::is_unbounded);
return flags;
}
};
}

View File

@@ -0,0 +1,60 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
namespace impl
{
template < class_kind T >
struct class_traits_base {
static constexpr std::size_t arity{0};
using argument_types = type_list<>;
static bitflags<class_flags> make_flags() noexcept {
return {};
}
static std::vector<any_type> make_argument_types() {
return {};
}
};
template < template < typename... > typename T, typename... Args >
struct class_traits_base<T<Args...>> {
static constexpr std::size_t arity{sizeof...(Args)};
using argument_types = type_list<Args...>;
static bitflags<class_flags> make_flags() noexcept {
return class_flags::is_template_instantiation;
}
static std::vector<any_type> make_argument_types() {
return { resolve_type<Args>()... };
}
};
}
template < class_kind T >
struct class_traits : impl::class_traits_base<T> {
static constexpr std::size_t size{sizeof(T)};
static bitflags<class_flags> make_flags() noexcept {
bitflags<class_flags> flags;
if constexpr ( std::is_empty_v<T> ) flags.set(class_flags::is_empty);
if constexpr ( std::is_final_v<T> ) flags.set(class_flags::is_final);
if constexpr ( std::is_abstract_v<T> ) flags.set(class_flags::is_abstract);
if constexpr ( std::is_polymorphic_v<T> ) flags.set(class_flags::is_polymorphic);
return flags | impl::class_traits_base<T>::make_flags();
}
};
}

View File

@@ -0,0 +1,31 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < class_kind Class, typename... Args >
struct ctor_traits {
static constexpr std::size_t arity{sizeof...(Args)};
using class_type = Class;
using argument_types = type_list<Args...>;
static bitflags<ctor_flags> make_flags() noexcept {
bitflags<ctor_flags> flags;
if constexpr ( std::is_nothrow_constructible_v<Class, Args...> ) flags.set(ctor_flags::is_noexcept);
return flags;
}
static std::vector<any_type> make_argument_types() {
return { resolve_type<Args>()... };
}
};
}

View File

@@ -4,11 +4,19 @@
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#include "meta_tests.hpp"
#pragma once
namespace
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
}
template < enum_kind Enum >
struct enum_traits {
using underlying_type = std::underlying_type_t<Enum>;
TEST_CASE("meta") {
static bitflags<enum_flags> make_flags() noexcept {
return {};
}
};
}

View File

@@ -0,0 +1,39 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < function_kind Function >
struct function_traits;
template < typename R, typename... Args >
struct function_traits<R(*)(Args...)> {
static constexpr std::size_t arity{sizeof...(Args)};
using return_type = R;
using argument_types = type_list<Args...>;
static bitflags<function_flags> make_flags() noexcept {
return {};
}
static std::vector<any_type> make_argument_types() {
return { resolve_type<Args>()... };
}
};
template < typename R, typename... Args >
struct function_traits<R(*)(Args...) noexcept> : function_traits<R(*)(Args...)> {
static bitflags<function_flags> make_flags() noexcept {
return function_flags::is_noexcept;
}
};
}

View File

@@ -0,0 +1,26 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < member_kind Member >
struct member_traits;
template < typename V, typename C >
struct member_traits<V C::*> {
using class_type = C;
using value_type = V;
static bitflags<member_flags> make_flags() noexcept {
return {};
}
};
}

View File

@@ -0,0 +1,220 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < method_kind Method >
struct method_traits;
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...)> {
static constexpr std::size_t arity{sizeof...(Args)};
using class_type = C;
using return_type = R;
using qualified_type = C;
using argument_types = type_list<Args...>;
static bitflags<method_flags> make_flags() noexcept {
return {};
}
static std::vector<any_type> make_argument_types() {
return { resolve_type<Args>()... };
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_noexcept;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const | method_flags::is_noexcept;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) &> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) & noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_noexcept | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const &> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const & noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const | method_flags::is_noexcept | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) &&> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) && noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_noexcept | method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const &&> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const | method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) const && noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_const | method_flags::is_noexcept | method_flags::is_rvalue_qualified;
}
};
//
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile> : method_traits<R(C::*)(Args...)> {
using qualified_type = C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_noexcept;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const | method_flags::is_noexcept;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile &> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile & noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_noexcept | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const &> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const & noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const | method_flags::is_noexcept | method_flags::is_lvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile &&> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile && noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_noexcept | method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const &&> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const | method_flags::is_rvalue_qualified;
}
};
template < typename R, typename C, typename... Args >
struct method_traits<R(C::*)(Args...) volatile const && noexcept> : method_traits<R(C::*)(Args...)> {
using qualified_type = const C&&;
static bitflags<method_flags> make_flags() noexcept {
return method_flags::is_volatile | method_flags::is_const | method_flags::is_noexcept | method_flags::is_rvalue_qualified;
}
};
}

View File

@@ -0,0 +1,27 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < number_kind Number >
struct number_traits {
static constexpr std::size_t size{sizeof(Number)};
static bitflags<number_flags> make_flags() noexcept {
bitflags<number_flags> flags;
if ( std::is_signed_v<Number> ) flags.set(number_flags::is_signed);
if ( std::is_unsigned_v<Number> ) flags.set(number_flags::is_unsigned);
if ( std::is_integral_v<Number> ) flags.set(number_flags::is_integral);
if ( std::is_floating_point_v<Number> ) flags.set(number_flags::is_floating_point);
return flags;
}
};
}

View File

@@ -0,0 +1,24 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < pointer_kind Pointer >
struct pointer_traits {
using data_type = std::remove_pointer_t<Pointer>;
static bitflags<pointer_flags> make_flags() noexcept {
bitflags<pointer_flags> flags;
if constexpr ( std::is_const_v<data_type> ) flags.set(pointer_flags::is_readonly);
return flags;
}
};
}

View File

@@ -0,0 +1,26 @@
/*******************************************************************************
* This file is part of the "https://github.com/blackmatov/meta.hpp"
* For conditions of distribution and use, see copyright notice in LICENSE.md
* Copyright (C) 2021, by Matvey Cherevko (blackmatov@gmail.com)
******************************************************************************/
#pragma once
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < reference_kind Reference >
struct reference_traits {
using data_type = std::remove_reference_t<Reference>;
static bitflags<reference_flags> make_flags() noexcept {
bitflags<reference_flags> flags;
if constexpr ( std::is_const_v<data_type> ) flags.set(reference_flags::is_readonly);
if constexpr ( std::is_lvalue_reference_v<Reference> ) flags.set(reference_flags::is_lvalue);
if constexpr ( std::is_rvalue_reference_v<Reference> ) flags.set(reference_flags::is_rvalue);
return flags;
}
};
}

View File

@@ -6,6 +6,15 @@
#pragma once
namespace meta_hpp
#include "../meta_base.hpp"
#include "../meta_traits.hpp"
namespace meta_hpp::detail
{
template < void_kind Void >
struct void_traits {
static bitflags<void_flags> make_flags() noexcept {
return {};
}
};
}