const_str/__ctfe/
is_ascii.rs1pub struct IsAscii<T>(pub T);
2
3impl IsAscii<&[u8]> {
4 pub const fn const_eval(&self) -> bool {
5 let bytes = self.0;
6 let mut i = 0;
7 while i < bytes.len() {
8 if !bytes[i].is_ascii() {
9 return false;
10 }
11 i += 1;
12 }
13 true
14 }
15}
16
17impl IsAscii<&str> {
18 pub const fn const_eval(&self) -> bool {
19 IsAscii(self.0.as_bytes()).const_eval()
20 }
21}
22
23impl<const N: usize> IsAscii<&[u8; N]> {
24 pub const fn const_eval(&self) -> bool {
25 IsAscii(self.0.as_slice()).const_eval()
26 }
27}
28
29#[macro_export]
52macro_rules! is_ascii {
53 ($s:expr) => {
54 $crate::__ctfe::IsAscii($s).const_eval()
55 };
56}
57
58#[cfg(test)]
59mod tests {
60 #[test]
61 fn test_is_ascii() {
62 const S1: &str = "hello!\n";
63 const S2: &str = "你好!";
64 const S3: &str = "";
65 const S4: &str = "ASCII123";
66
67 let r1 = is_ascii!(S1);
68 let r2 = is_ascii!(S2);
69 let r3 = is_ascii!(S3);
70 let r4 = is_ascii!(S4);
71
72 assert!(r1);
73 assert!(!r2);
74 assert!(r3); assert!(r4);
76
77 const B1: &[u8] = b"hello";
79 const B2: &[u8] = b"\x80\x00";
80
81 let rb1 = is_ascii!(B1);
82 let rb2 = is_ascii!(B2);
83
84 assert!(rb1);
85 assert!(!rb2);
86
87 const A1: &[u8; 5] = b"hello";
89 const A2: &[u8; 2] = b"\x80\x00";
90
91 let ra1 = is_ascii!(A1);
92 let ra2 = is_ascii!(A2);
93
94 assert!(ra1);
95 assert!(!ra2);
96 }
97}