1
+ use std:: num:: { NonZeroU16 , NonZeroU32 , NonZeroU8 } ;
2
+
1
3
use crate :: inline:: get_heap_threshold;
2
4
3
5
mod sealed {
4
- pub trait Sealed { }
5
- impl Sealed for u8 { }
6
- impl Sealed for u16 { }
6
+ use std:: num:: { NonZeroU16 , NonZeroU32 , NonZeroU8 } ;
7
+
8
+ pub trait LengthSealed { }
9
+ impl LengthSealed for u8 { }
10
+ impl LengthSealed for u16 { }
7
11
#[ cfg( any( target_pointer_width = "64" , target_pointer_width = "32" ) ) ]
8
- impl Sealed for u32 { }
12
+ impl LengthSealed for u32 { }
13
+
14
+ pub trait NonZeroSealed { }
15
+ impl NonZeroSealed for NonZeroU8 { }
16
+ impl NonZeroSealed for NonZeroU16 { }
17
+ #[ cfg( any( target_pointer_width = "64" , target_pointer_width = "32" ) ) ]
18
+ impl NonZeroSealed for NonZeroU32 { }
9
19
}
10
20
11
21
#[ derive( Debug ) ]
@@ -88,14 +98,42 @@ impl TryFrom<InvalidLength<u8>> for InvalidStrLength {
88
98
}
89
99
}
90
100
101
+ #[ doc( hidden) ]
102
+ pub trait NonZero < Int : ValidLength > :
103
+ sealed:: NonZeroSealed + Into < Int > + Sized + Copy + PartialEq + std:: fmt:: Debug
104
+ {
105
+ fn new ( val : Int ) -> Option < Self > ;
106
+ }
107
+
108
+ impl NonZero < u8 > for NonZeroU8 {
109
+ fn new ( val : u8 ) -> Option < Self > {
110
+ NonZeroU8 :: new ( val)
111
+ }
112
+ }
113
+
114
+ impl NonZero < u16 > for NonZeroU16 {
115
+ fn new ( val : u16 ) -> Option < Self > {
116
+ NonZeroU16 :: new ( val)
117
+ }
118
+ }
119
+
120
+ impl NonZero < u32 > for NonZeroU32 {
121
+ fn new ( val : u32 ) -> Option < Self > {
122
+ NonZeroU32 :: new ( val)
123
+ }
124
+ }
125
+
91
126
/// A sealed trait to represent valid lengths for a [`FixedArray`].
92
127
///
93
128
/// This is implemented on `u32` for non-16 bit platforms, and `u16` on all platforms.
94
129
///
95
130
/// [`FixedArray`]: `crate::array::FixedArray`
96
- pub trait ValidLength : sealed:: Sealed + Default + Copy + TryFrom < usize > + Into < u32 > {
131
+ pub trait ValidLength : sealed:: LengthSealed + Copy + TryFrom < usize > + Into < u32 > {
97
132
const ZERO : Self ;
98
- const MAX : usize ;
133
+ const MAX : Self ;
134
+ const DANGLING : Self :: NonZero ;
135
+
136
+ type NonZero : NonZero < Self > ;
99
137
#[ cfg( feature = "typesize" ) ]
100
138
type InlineStrRepr : Copy + AsRef < [ u8 ] > + AsMut < [ u8 ] > + Default + typesize:: TypeSize ;
101
139
#[ cfg( not( feature = "typesize" ) ) ]
@@ -112,8 +150,10 @@ pub trait ValidLength: sealed::Sealed + Default + Copy + TryFrom<usize> + Into<u
112
150
113
151
impl ValidLength for u8 {
114
152
const ZERO : Self = 0 ;
115
- #[ allow( clippy:: as_conversions) ] // Cannot use `.into()` in const.
116
- const MAX : usize = u8:: MAX as usize ;
153
+ const MAX : Self = Self :: MAX ;
154
+ const DANGLING : Self :: NonZero = Self :: NonZero :: MAX ;
155
+
156
+ type NonZero = NonZeroU8 ;
117
157
type InlineStrRepr = [ u8 ; get_heap_threshold :: < Self > ( ) ] ;
118
158
119
159
fn to_usize ( self ) -> usize {
@@ -123,8 +163,10 @@ impl ValidLength for u8 {
123
163
124
164
impl ValidLength for u16 {
125
165
const ZERO : Self = 0 ;
126
- #[ allow( clippy:: as_conversions) ] // Cannot use `.into()` in const.
127
- const MAX : usize = u16:: MAX as usize ;
166
+ const MAX : Self = Self :: MAX ;
167
+ const DANGLING : Self :: NonZero = Self :: NonZero :: MAX ;
168
+
169
+ type NonZero = NonZeroU16 ;
128
170
type InlineStrRepr = [ u8 ; get_heap_threshold :: < Self > ( ) ] ;
129
171
130
172
fn to_usize ( self ) -> usize {
@@ -135,8 +177,10 @@ impl ValidLength for u16 {
135
177
#[ cfg( any( target_pointer_width = "64" , target_pointer_width = "32" ) ) ]
136
178
impl ValidLength for u32 {
137
179
const ZERO : Self = 0 ;
138
- #[ allow( clippy:: as_conversions) ] // Cannot use `.into()` in const.
139
- const MAX : usize = u32:: MAX as usize ;
180
+ const MAX : Self = Self :: MAX ;
181
+ const DANGLING : Self :: NonZero = Self :: NonZero :: MAX ;
182
+
183
+ type NonZero = NonZeroU32 ;
140
184
type InlineStrRepr = [ u8 ; get_heap_threshold :: < Self > ( ) ] ;
141
185
142
186
fn to_usize ( self ) -> usize {
0 commit comments