mimic++ v6
Loading...
Searching...
No Matches
Utility.hpp
Go to the documentation of this file.
1// Copyright Dominic (DNKpp) Koepke 2024 - 2025.
2// Distributed under the Boost Software License, Version 1.0.
3// (See accompanying file LICENSE_1_0.txt or copy at
4// https://www.boost.org/LICENSE_1_0.txt)
5
6#ifndef MIMICPP_UTILITY_HPP
7#define MIMICPP_UTILITY_HPP
8
9#pragma once
10
11#include "mimic++/Fwd.hpp"
12
13#include <array>
14#include <cassert>
15#include <source_location>
16#include <string_view>
17#include <tuple>
18#include <utility>
19
20namespace mimicpp
21{
22 template <typename...>
24 : public std::bool_constant<false>
25 {
26 };
27
28 template <std::size_t priority>
31 : public priority_tag<priority - 1>
33 {
34 };
35
36 template <>
37 struct priority_tag<0>
38 {
39 };
40
41 [[nodiscard]]
43 const std::source_location& lhs,
44 const std::source_location& rhs) noexcept
45 {
46 return std::string_view{lhs.file_name()} == std::string_view{rhs.file_name()}
47 && std::string_view{lhs.function_name()} == std::string_view{rhs.function_name()}
48 && lhs.line() == rhs.line()
49 && lhs.column() == rhs.column();
50 }
51
52 template <typename From, typename To>
54 requires {
55 static_cast<To>(std::declval<From>());
56 };
57
58 template <typename From, typename To>
61 && requires {
62 { static_cast<To>(std::declval<From>()) } noexcept;
63 };
64
65 template <typename T, typename... Others>
66 concept same_as_any = (... || std::same_as<T, Others>);
67
68 template <typename T>
69 requires std::is_enum_v<T>
70 [[nodiscard]]
71 constexpr std::underlying_type_t<T> to_underlying(const T value) noexcept
72 {
73 return static_cast<std::underlying_type_t<T>>(value);
74 }
75
76 template <typename T, template <typename> typename Trait>
77 concept satisfies = Trait<T>::value;
78
79 // GCOVR_EXCL_START
80
81#ifdef __cpp_lib_unreachable
82 using std::unreachable;
83#else
84
90 [[noreturn]]
91 inline void unreachable()
92 {
93 assert(false);
94
95 // Uses compiler specific extensions if possible.
96 // Even if no extension is used, undefined behavior is still raised by
97 // an empty function body and the noreturn attribute.
98 #if defined(_MSC_VER) && !defined(__clang__) // MSVC
99 __assume(false);
100 #else // GCC, Clang
101 __builtin_unreachable();
102 #endif
103 }
104#endif
105
106 // GCOVR_EXCL_STOP
107
108 [[nodiscard]]
109 constexpr bool is_matching(const Constness lhs, const Constness rhs) noexcept
110 {
111 return std::cmp_not_equal(0, to_underlying(lhs) & to_underlying(rhs));
112 }
113
114 [[nodiscard]]
115 constexpr bool is_matching(const ValueCategory lhs, const ValueCategory rhs) noexcept
116 {
117 return std::cmp_not_equal(0, to_underlying(lhs) & to_underlying(rhs));
118 }
119}
120
121namespace mimicpp::detail
122{
123 template <typename Parsed, typename... Rest>
124 struct unique;
125
126 template <typename... Uniques, typename First, typename... Others>
127 struct unique<
128 type_list<Uniques...>,
129 First,
130 Others...>
131 {
132 using current_t = std::conditional_t<
133 same_as_any<First, Uniques...>,
134 type_list<Uniques...>,
135 type_list<Uniques..., First>>;
136
137 using type_t = typename unique<
138 current_t,
139 Others...>::type_t;
140 };
141
142 template <typename... Uniques>
143 struct unique<type_list<Uniques...>>
144 {
145 using type_t = type_list<Uniques...>;
146 };
147
148 template <typename... Types>
149 using unique_list_t = typename unique<type_list<>, Types...>::type_t;
150
151 template <std::default_initializable FillElement, std::size_t n, typename... Elements>
152 requires(sizeof...(Elements) <= n)
153 [[nodiscard]]
154 constexpr auto expand_tuple(std::tuple<Elements...>&& tuple)
155 {
156 // prior to c++23, tuple_cat does not officially support tuple-like types,
157 // thus we transform the generated array manually
158 return std::tuple_cat(
159 std::move(tuple),
160 std::apply(
161 [](auto&&... elements) { return std::make_tuple(std::move(elements)...); },
162 std::array<FillElement, n - sizeof...(Elements)>{}));
163 }
164}
165
166#endif
Definition Utility.hpp:53
Definition Utility.hpp:66
Definition Utility.hpp:77
Definition BoostTest.hpp:20
void unreachable()
Invokes undefined behavior.
Definition Utility.hpp:91
constexpr bool is_same_source_location(const std::source_location &lhs, const std::source_location &rhs) noexcept
Definition Utility.hpp:42
ValueCategory
Definition Fwd.hpp:32
constexpr bool is_matching(const Constness lhs, const Constness rhs) noexcept
Definition Utility.hpp:109
Constness
Definition Fwd.hpp:25
constexpr std::underlying_type_t< T > to_underlying(const T value) noexcept
Definition Utility.hpp:71
Definition Utility.hpp:25
Definition Utility.hpp:33