cplusplus.hpp 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. #pragma once
  2. #include <types/stdint.h>
  3. #ifdef __cplusplus
  4. namespace types {
  5. template <typename T, T _value>
  6. struct constant_value {
  7. static constexpr T value = _value;
  8. };
  9. using true_type = constant_value<bool, true>;
  10. using false_type = constant_value<bool, false>;
  11. };
  12. namespace types::traits {
  13. template <typename T>
  14. struct remove_pointer {
  15. using type = T;
  16. };
  17. template <typename T>
  18. struct remove_pointer<T*> {
  19. using type = T;
  20. };
  21. template <typename T>
  22. struct remove_reference {
  23. using type = T;
  24. };
  25. template <typename T>
  26. struct remove_reference<T&> {
  27. using type = T;
  28. };
  29. template <typename T>
  30. struct remove_reference<T&&> {
  31. using type = T;
  32. };
  33. template <typename T>
  34. struct add_pointer {
  35. using type = T*;
  36. };
  37. template <typename T>
  38. struct add_reference {
  39. using type = T&;
  40. };
  41. template <typename T>
  42. struct remove_cv {
  43. using type = T;
  44. };
  45. template <typename T>
  46. struct remove_cv<const T> {
  47. using type = T;
  48. };
  49. template <typename T>
  50. struct remove_cv<volatile T> {
  51. using type = T;
  52. };
  53. template <typename T>
  54. struct remove_cv<const volatile T> {
  55. using type = T;
  56. };
  57. template <typename T>
  58. struct is_pointer : false_type {
  59. };
  60. template <typename T>
  61. struct is_pointer<T*> : true_type {
  62. };
  63. template <typename T>
  64. struct decay {
  65. private:
  66. using U = remove_reference<T>;
  67. public:
  68. using type = typename remove_cv<U>::type;
  69. };
  70. } // namespace types::traits
  71. namespace types {
  72. template <typename T>
  73. constexpr typename traits::remove_reference<T>::type&& move(T&& val)
  74. {
  75. return static_cast<typename traits::remove_reference<T>::type&&>(val);
  76. }
  77. template <typename T>
  78. constexpr T&& forward(typename traits::remove_reference<T>::type& val)
  79. {
  80. return static_cast<T&&>(val);
  81. }
  82. template <typename T>
  83. constexpr T&& forward(typename traits::remove_reference<T>::type&& val)
  84. {
  85. return static_cast<T&&>(val);
  86. }
  87. template <typename>
  88. struct template_true_type : public true_type {
  89. };
  90. template <typename>
  91. struct template_false_type : public false_type {
  92. };
  93. template <typename, typename>
  94. struct is_same : false_type {
  95. };
  96. template <typename T>
  97. struct is_same<T, T> : true_type {
  98. };
  99. template <typename T>
  100. struct add_rvalue_reference {
  101. using type = T&&;
  102. };
  103. template <>
  104. struct add_rvalue_reference<void> {
  105. using type = void;
  106. };
  107. template <typename Src, typename Dst>
  108. concept convertible_to = (traits::is_pointer<Src>::value && is_same<Dst, uint32_t>::value)
  109. || (traits::is_pointer<Dst>::value && is_same<Src, uint32_t>::value)
  110. || requires(Src _src)
  111. {
  112. { static_cast<Dst>(_src) };
  113. };
  114. template <typename T>
  115. concept PointerType = traits::is_pointer<T>::value;
  116. template <typename A, typename B>
  117. concept same_as = is_same<A, B>::value;
  118. } // namespace types
  119. #endif