Skip to content

Commit 4f67fb7

Browse files
committed
Refactor 'ncount_base<>' into 'nvalue'. Optimized the generated asembly of the 'nvalue' type. Improved the inital API shared across 'ncount' and 'nindex'. More to come.
1 parent 1a5677e commit 4f67fb7

File tree

4 files changed

+229
-212
lines changed

4 files changed

+229
-212
lines changed

source/code/core/collections/public/ice/types/ncount.hxx

Lines changed: 60 additions & 134 deletions
Original file line numberDiff line numberDiff line change
@@ -3,119 +3,33 @@
33

44
#pragma once
55
#include <ice/mem.hxx>
6+
#include <ice/types/nvalue.hxx>
67

78
namespace ice
89
{
910

1011
struct ncount;
1112
struct nindex;
1213

13-
namespace concepts
14+
struct ncount : public ice::nvalue
1415
{
16+
using nvalue::base_type;
17+
using nvalue::base_signed_type;
1518

16-
template<typename T>
17-
concept native_count_type = (std::is_arithmetic_v<T> and not std::is_floating_point_v<T>)
18-
or std::is_same_v<T, ncount>
19-
or std::is_same_v<T, nindex>;
20-
21-
} // namespace concepts
22-
23-
namespace detail
24-
{
25-
26-
#if ISP_ARCH_BITS == 64
27-
using ncount_base_type = u64;
28-
using ncount_base_type_signed = i64;
29-
#elif ISP_ARCH_BITS == 32
30-
using ncount_base_type = u32;
31-
using ncount_base_type_signed = i32;
32-
#else
33-
# error Unhandled architecture!
34-
#endif
35-
36-
template<
37-
typename BaseType = ncount_base_type,
38-
typename BaseTypeSigned = ncount_base_type_signed>
39-
struct ncount_base;
40-
41-
template<>
42-
struct ncount_base<u64, i64>
43-
{
44-
using base_type = u64;
45-
using base_type_signed = i64;
46-
47-
base_type_signed value : 48 = 0;
48-
base_type width : 16 = 0;
49-
50-
constexpr ncount_base() noexcept = default;
51-
constexpr ncount_base(base_type value) noexcept
52-
: value{ static_cast<base_type_signed>(value) }, width{ 1 }
53-
{ }
54-
constexpr explicit ncount_base(base_type value, base_type width) noexcept
55-
: value{ static_cast<base_type_signed>(value) }, width{ width }
56-
{ }
57-
};
58-
59-
template<>
60-
struct ncount_base<u32, i32>
61-
{
62-
using base_type = u32;
63-
using base_type_signed = i32;
64-
65-
base_type_signed value = 0;
66-
base_type width = 0;
67-
68-
constexpr ncount_base() noexcept = default;
69-
constexpr ncount_base(base_type value) noexcept
70-
: value{ static_cast<base_type_signed>(value) }, width{ 1 }
71-
{ }
72-
constexpr explicit ncount_base(base_type value, base_type width) noexcept
73-
: value{ static_cast<base_type_signed>(value) }, width{ width }
74-
{ }
75-
};
76-
77-
constexpr auto ncount_min_value() noexcept -> ncount_base_type
78-
{
79-
return 0;
80-
}
81-
82-
constexpr auto ncount_max_value() noexcept -> ncount_base_type
83-
{
84-
if constexpr (ice::build::is_x64)
85-
{
86-
return 0x0000'7fff'ffff'ffff;
87-
}
88-
else
89-
{
90-
return std::numeric_limits<ncount_base_type_signed>::max();
91-
}
92-
}
93-
94-
} // namespace detail
95-
96-
97-
struct ncount : protected ice::detail::ncount_base<>
98-
{
99-
using ncount_base<>::base_type;
100-
using ncount_base<>::ncount_base;
101-
102-
// Utility
103-
constexpr auto u8() const noexcept { return static_cast<ice::u8>(value); }
104-
constexpr auto u16() const noexcept { return static_cast<ice::u16>(value); }
105-
constexpr auto u32() const noexcept { return static_cast<ice::u32>(value); }
106-
constexpr auto u64() const noexcept { return static_cast<ice::u64>(value); }
107-
constexpr auto native() const noexcept { return static_cast<base_type>(value); }
108-
constexpr auto bytes() const noexcept { return operator ice::usize(); }
19+
constexpr ncount() noexcept = default;
20+
constexpr ncount(nvalue value) noexcept;
21+
constexpr ncount(base_type value) noexcept;
22+
constexpr ncount(base_type value, base_type width) noexcept;
10923

11024
// Arithmetic
111-
constexpr auto operator+(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount;
112-
constexpr auto operator-(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount;
113-
constexpr auto operator*(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount;
114-
constexpr auto operator/(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount;
115-
constexpr auto operator+=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&;
116-
constexpr auto operator-=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&;
117-
constexpr auto operator*=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&;
118-
constexpr auto operator/=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&;
25+
constexpr auto operator+(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount;
26+
constexpr auto operator-(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount;
27+
constexpr auto operator*(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount;
28+
constexpr auto operator/(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount;
29+
constexpr auto operator+=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&;
30+
constexpr auto operator-=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&;
31+
constexpr auto operator*=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&;
32+
constexpr auto operator/=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&;
11933

12034
// Increments
12135
constexpr auto operator++(this ncount& self) noexcept -> ncount&;
@@ -124,16 +38,28 @@ namespace ice
12438
constexpr auto operator--(this ncount& self, int) noexcept -> ncount;
12539

12640
// Comparison
127-
constexpr bool operator==(this ncount self, ice::concepts::native_count_type auto other) noexcept;
128-
constexpr auto operator<=>(this ncount self, ice::concepts::native_count_type auto other) noexcept;
41+
constexpr bool operator==(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept;
42+
constexpr auto operator<=>(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept;
12943

13044
// type colapsing
13145
constexpr explicit operator bool(this ncount self) noexcept;
13246
constexpr operator ice::usize(this ncount self) noexcept;
13347
constexpr operator base_type(this ncount self) noexcept;
134-
constexpr explicit operator base_type_signed(this ncount self) noexcept;
48+
constexpr explicit operator base_signed_type(this ncount self) noexcept;
13549
};
13650

51+
constexpr ncount::ncount(nvalue value) noexcept
52+
: nvalue{ value }
53+
{ }
54+
55+
constexpr ncount::ncount(base_type value) noexcept
56+
: nvalue{ 1, static_cast<base_signed_type>(value) }
57+
{ }
58+
59+
inline constexpr ncount::ncount(base_type value, base_type width) noexcept
60+
: nvalue{ width, static_cast<base_signed_type>(value) }
61+
{ }
62+
13763
struct ncount_invalid_t : ncount {};
13864

13965
static constexpr ice::ncount_invalid_t none_count{ };
@@ -142,104 +68,104 @@ namespace ice
14268

14369
static_assert(ice::size_of<ncount> == 8_B);
14470

145-
constexpr auto ncount::operator+(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount
71+
constexpr auto ncount::operator+(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount
14672
{
147-
return ncount{ static_cast<base_type>(self.value + static_cast<base_type_signed>(other)), self.width };
73+
return ncount{ static_cast<base_type>(self._value + static_cast<base_signed_type>(other)), self._width };
14874
}
14975

150-
constexpr auto ncount::operator-(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount
76+
constexpr auto ncount::operator-(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount
15177
{
152-
return ncount{ static_cast<base_type>(self.value - static_cast<base_type_signed>(other)), self.width };
78+
return ncount{ static_cast<base_type>(self._value - static_cast<base_signed_type>(other)), self._width };
15379
}
15480

155-
constexpr auto ncount::operator*(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount
81+
constexpr auto ncount::operator*(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount
15682
{
157-
return ncount{ static_cast<base_type>(self.value * static_cast<base_type_signed>(other)), self.width };
83+
return ncount{ static_cast<base_type>(self._value * static_cast<base_signed_type>(other)), self._width };
15884
}
15985

160-
constexpr auto ncount::operator/(this ncount self, ice::concepts::native_count_type auto other) noexcept -> ncount
86+
constexpr auto ncount::operator/(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount
16187
{
162-
return ncount{ static_cast<base_type>(self.value / static_cast<base_type_signed>(other)), self.width };
88+
return ncount{ static_cast<base_type>(self._value / static_cast<base_signed_type>(other)), self._width };
16389
}
16490

165-
constexpr auto ncount::operator+=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&
91+
constexpr auto ncount::operator+=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&
16692
{
167-
self.value += static_cast<base_type_signed>(other);
93+
self._value += static_cast<base_signed_type>(other);
16894
return self;
16995
}
17096

171-
constexpr auto ncount::operator-=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&
97+
constexpr auto ncount::operator-=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&
17298
{
173-
self.value -= static_cast<base_type_signed>(other);
99+
self._value -= static_cast<base_signed_type>(other);
174100
return self;
175101
}
176102

177-
constexpr auto ncount::operator*=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&
103+
constexpr auto ncount::operator*=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&
178104
{
179-
self.value *= static_cast<base_type_signed>(other);
105+
self._value *= static_cast<base_signed_type>(other);
180106
return self;
181107
}
182108

183-
constexpr auto ncount::operator/=(this ncount& self, ice::concepts::native_count_type auto other) noexcept -> ncount&
109+
constexpr auto ncount::operator/=(this ncount& self, ice::concepts::NValueCompatibleType auto other) noexcept -> ncount&
184110
{
185-
self.value /= static_cast<base_type_signed>(other);
111+
self._value /= static_cast<base_signed_type>(other);
186112
return self;
187113
}
188114

189115
constexpr auto ncount::operator++(this ncount& self) noexcept -> ncount&
190116
{
191-
self.value += 1;
117+
self._value += 1;
192118
return self;
193119
}
194120

195121
constexpr auto ncount::operator++(this ncount& self, int) noexcept -> ncount
196122
{
197123
const ncount old = self;
198-
self.value += 1;
124+
self._value += 1;
199125
return old;
200126
}
201127

202128
constexpr auto ncount::operator--(this ncount& self) noexcept -> ncount&
203129
{
204-
self.value -= 1;
130+
self._value -= 1;
205131
return self;
206132
}
207133

208134
constexpr auto ncount::operator--(this ncount& self, int) noexcept -> ncount
209135
{
210136
const ncount old = self;
211-
self.value -= 1;
137+
self._value -= 1;
212138
return old;
213139
}
214140

215-
constexpr bool ncount::operator==(this ncount self, ice::concepts::native_count_type auto other) noexcept
141+
constexpr bool ncount::operator==(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept
216142
{
217-
return self.value == static_cast<base_type_signed>(other);
143+
return self._value == static_cast<base_signed_type>(other);
218144
}
219145

220-
constexpr auto ncount::operator<=>(this ncount self, ice::concepts::native_count_type auto other) noexcept
146+
constexpr auto ncount::operator<=>(this ncount self, ice::concepts::NValueCompatibleType auto other) noexcept
221147
{
222-
return self.value <=> static_cast<base_type_signed>(other);
148+
return self._value <=> static_cast<base_signed_type>(other);
223149
}
224150

225151
constexpr ncount::operator bool(this ncount self) noexcept
226152
{
227-
return static_cast<bool>(self.value * self.width);
153+
return static_cast<bool>(self._value * self._width);
228154
}
229155

230156
constexpr ncount::operator ice::usize(this ncount self) noexcept
231157
{
232-
return ice::usize{ static_cast<ice::usize::base_type>(self.value) * self.width };
158+
return ice::usize{ static_cast<ice::usize::base_type>(self._value) * self._width };
233159
}
234160

235161
constexpr ncount::operator ncount::base_type(this ncount self) noexcept
236162
{
237-
return std::max<base_type>(self.value, 0);
163+
return std::max<base_type>(self._value, 0);
238164
}
239165

240-
constexpr ncount::operator ncount::base_type_signed(this ncount self) noexcept
166+
constexpr ncount::operator ncount::base_signed_type(this ncount self) noexcept
241167
{
242-
return self.value;
168+
return self._value;
243169
}
244170

245171
// special operators

0 commit comments

Comments
 (0)