1#![allow(non_snake_case)]
21#![stable(feature = "rust1", since = "1.0.0")]
22
23mod convert;
24mod decode;
25mod methods;
26
27#[rustfmt::skip]
29#[stable(feature = "try_from", since = "1.34.0")]
30pub use self::convert::CharTryFromError;
31#[stable(feature = "char_from_str", since = "1.20.0")]
32#[cfg(not(feature = "ferrocene_subset"))]
33pub use self::convert::ParseCharError;
34#[stable(feature = "decode_utf16", since = "1.9.0")]
35pub use self::decode::{DecodeUtf16, DecodeUtf16Error};
36
37#[rustfmt::skip]
39#[unstable(feature = "char_internals", reason = "exposed only for libstd", issue = "none")]
40#[cfg(not(feature = "ferrocene_subset"))]
41pub use self::methods::encode_utf16_raw; #[unstable(feature = "char_internals", reason = "exposed only for libstd", issue = "none")]
43pub use self::methods::{encode_utf8_raw, encode_utf8_raw_unchecked}; #[rustfmt::skip]
46#[cfg(not(feature = "ferrocene_subset"))]
47use crate::ascii;
48#[cfg(not(feature = "ferrocene_subset"))]
49pub(crate) use self::methods::EscapeDebugExtArgs;
50#[cfg(not(feature = "ferrocene_subset"))]
51use crate::error::Error;
52#[cfg(not(feature = "ferrocene_subset"))]
53use crate::escape::{AlwaysEscaped, EscapeIterInner, MaybeEscaped};
54#[cfg(not(feature = "ferrocene_subset"))]
55use crate::fmt::{self, Write};
56#[cfg(not(feature = "ferrocene_subset"))]
57use crate::iter::{FusedIterator, TrustedLen, TrustedRandomAccess, TrustedRandomAccessNoCoerce};
58#[cfg(not(feature = "ferrocene_subset"))]
59use crate::num::NonZero;
60
61const TAG_CONT: u8 = 0b1000_0000;
63const TAG_TWO_B: u8 = 0b1100_0000;
64const TAG_THREE_B: u8 = 0b1110_0000;
65const TAG_FOUR_B: u8 = 0b1111_0000;
66const MAX_ONE_B: u32 = 0x80;
67const MAX_TWO_B: u32 = 0x800;
68const MAX_THREE_B: u32 = 0x10000;
69
70#[stable(feature = "rust1", since = "1.0.0")]
105#[cfg(not(feature = "ferrocene_subset"))]
106pub const MAX: char = char::MAX;
107
108#[unstable(feature = "char_max_len", issue = "121714")]
111#[cfg(not(feature = "ferrocene_subset"))]
112pub const MAX_LEN_UTF8: usize = char::MAX_LEN_UTF8;
113
114#[unstable(feature = "char_max_len", issue = "121714")]
117#[cfg(not(feature = "ferrocene_subset"))]
118pub const MAX_LEN_UTF16: usize = char::MAX_LEN_UTF16;
119
120#[stable(feature = "decode_utf16", since = "1.9.0")]
123#[cfg(not(feature = "ferrocene_subset"))]
124pub const REPLACEMENT_CHARACTER: char = char::REPLACEMENT_CHARACTER;
125
126#[stable(feature = "unicode_version", since = "1.45.0")]
129#[cfg(not(feature = "ferrocene_subset"))]
130pub const UNICODE_VERSION: (u8, u8, u8) = char::UNICODE_VERSION;
131
132#[stable(feature = "decode_utf16", since = "1.9.0")]
135#[inline]
136#[cfg(not(feature = "ferrocene_subset"))]
137pub fn decode_utf16<I: IntoIterator<Item = u16>>(iter: I) -> DecodeUtf16<I::IntoIter> {
138 self::decode::decode_utf16(iter)
139}
140
141#[stable(feature = "rust1", since = "1.0.0")]
143#[rustc_const_stable(feature = "const_char_convert", since = "1.67.0")]
144#[must_use]
145#[inline]
146#[cfg(not(feature = "ferrocene_subset"))]
147pub const fn from_u32(i: u32) -> Option<char> {
148 self::convert::from_u32(i)
149}
150
151#[stable(feature = "char_from_unchecked", since = "1.5.0")]
154#[rustc_const_stable(feature = "const_char_from_u32_unchecked", since = "1.81.0")]
155#[must_use]
156#[inline]
157#[cfg(not(feature = "ferrocene_subset"))]
158pub const unsafe fn from_u32_unchecked(i: u32) -> char {
159 unsafe { self::convert::from_u32_unchecked(i) }
161}
162
163#[stable(feature = "rust1", since = "1.0.0")]
165#[rustc_const_stable(feature = "const_char_convert", since = "1.67.0")]
166#[must_use]
167#[inline]
168#[cfg(not(feature = "ferrocene_subset"))]
169pub const fn from_digit(num: u32, radix: u32) -> Option<char> {
170 self::convert::from_digit(num, radix)
171}
172
173#[derive(Clone, Debug)]
181#[stable(feature = "rust1", since = "1.0.0")]
182#[cfg(not(feature = "ferrocene_subset"))]
183pub struct EscapeUnicode(EscapeIterInner<10, AlwaysEscaped>);
184
185#[cfg(not(feature = "ferrocene_subset"))]
186impl EscapeUnicode {
187 #[inline]
188 const fn new(c: char) -> Self {
189 Self(EscapeIterInner::unicode(c))
190 }
191}
192
193#[stable(feature = "rust1", since = "1.0.0")]
194#[cfg(not(feature = "ferrocene_subset"))]
195impl Iterator for EscapeUnicode {
196 type Item = char;
197
198 #[inline]
199 fn next(&mut self) -> Option<char> {
200 self.0.next().map(char::from)
201 }
202
203 #[inline]
204 fn size_hint(&self) -> (usize, Option<usize>) {
205 let n = self.0.len();
206 (n, Some(n))
207 }
208
209 #[inline]
210 fn count(self) -> usize {
211 self.0.len()
212 }
213
214 #[inline]
215 fn last(mut self) -> Option<char> {
216 self.0.next_back().map(char::from)
217 }
218
219 #[inline]
220 fn advance_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
221 self.0.advance_by(n)
222 }
223}
224
225#[stable(feature = "exact_size_escape", since = "1.11.0")]
226#[cfg(not(feature = "ferrocene_subset"))]
227impl ExactSizeIterator for EscapeUnicode {
228 #[inline]
229 fn len(&self) -> usize {
230 self.0.len()
231 }
232}
233
234#[stable(feature = "fused", since = "1.26.0")]
235#[cfg(not(feature = "ferrocene_subset"))]
236impl FusedIterator for EscapeUnicode {}
237
238#[stable(feature = "char_struct_display", since = "1.16.0")]
239#[cfg(not(feature = "ferrocene_subset"))]
240impl fmt::Display for EscapeUnicode {
241 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
242 fmt::Display::fmt(&self.0, f)
243 }
244}
245
246#[derive(Clone, Debug)]
253#[stable(feature = "rust1", since = "1.0.0")]
254#[cfg(not(feature = "ferrocene_subset"))]
255pub struct EscapeDefault(EscapeIterInner<10, AlwaysEscaped>);
256
257#[cfg(not(feature = "ferrocene_subset"))]
258impl EscapeDefault {
259 #[inline]
260 const fn printable(c: ascii::Char) -> Self {
261 Self(EscapeIterInner::ascii(c.to_u8()))
262 }
263
264 #[inline]
265 const fn backslash(c: ascii::Char) -> Self {
266 Self(EscapeIterInner::backslash(c))
267 }
268
269 #[inline]
270 const fn unicode(c: char) -> Self {
271 Self(EscapeIterInner::unicode(c))
272 }
273}
274
275#[stable(feature = "rust1", since = "1.0.0")]
276#[cfg(not(feature = "ferrocene_subset"))]
277impl Iterator for EscapeDefault {
278 type Item = char;
279
280 #[inline]
281 fn next(&mut self) -> Option<char> {
282 self.0.next().map(char::from)
283 }
284
285 #[inline]
286 fn size_hint(&self) -> (usize, Option<usize>) {
287 let n = self.0.len();
288 (n, Some(n))
289 }
290
291 #[inline]
292 fn count(self) -> usize {
293 self.0.len()
294 }
295
296 #[inline]
297 fn last(mut self) -> Option<char> {
298 self.0.next_back().map(char::from)
299 }
300
301 #[inline]
302 fn advance_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
303 self.0.advance_by(n)
304 }
305}
306
307#[stable(feature = "exact_size_escape", since = "1.11.0")]
308#[cfg(not(feature = "ferrocene_subset"))]
309impl ExactSizeIterator for EscapeDefault {
310 #[inline]
311 fn len(&self) -> usize {
312 self.0.len()
313 }
314}
315
316#[stable(feature = "fused", since = "1.26.0")]
317#[cfg(not(feature = "ferrocene_subset"))]
318impl FusedIterator for EscapeDefault {}
319
320#[stable(feature = "char_struct_display", since = "1.16.0")]
321#[cfg(not(feature = "ferrocene_subset"))]
322impl fmt::Display for EscapeDefault {
323 #[inline]
324 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
325 fmt::Display::fmt(&self.0, f)
326 }
327}
328
329#[stable(feature = "char_escape_debug", since = "1.20.0")]
336#[derive(Clone, Debug)]
337#[cfg(not(feature = "ferrocene_subset"))]
338pub struct EscapeDebug(EscapeIterInner<10, MaybeEscaped>);
339
340#[cfg(not(feature = "ferrocene_subset"))]
341impl EscapeDebug {
342 #[inline]
343 const fn printable(chr: char) -> Self {
344 Self(EscapeIterInner::printable(chr))
345 }
346
347 #[inline]
348 const fn backslash(c: ascii::Char) -> Self {
349 Self(EscapeIterInner::backslash(c))
350 }
351
352 #[inline]
353 const fn unicode(c: char) -> Self {
354 Self(EscapeIterInner::unicode(c))
355 }
356}
357
358#[stable(feature = "char_escape_debug", since = "1.20.0")]
359#[cfg(not(feature = "ferrocene_subset"))]
360impl Iterator for EscapeDebug {
361 type Item = char;
362
363 #[inline]
364 fn next(&mut self) -> Option<char> {
365 self.0.next()
366 }
367
368 #[inline]
369 fn size_hint(&self) -> (usize, Option<usize>) {
370 let n = self.len();
371 (n, Some(n))
372 }
373
374 #[inline]
375 fn count(self) -> usize {
376 self.len()
377 }
378}
379
380#[stable(feature = "char_escape_debug", since = "1.20.0")]
381#[cfg(not(feature = "ferrocene_subset"))]
382impl ExactSizeIterator for EscapeDebug {
383 fn len(&self) -> usize {
384 self.0.len()
385 }
386}
387
388#[stable(feature = "fused", since = "1.26.0")]
389#[cfg(not(feature = "ferrocene_subset"))]
390impl FusedIterator for EscapeDebug {}
391
392#[stable(feature = "char_escape_debug", since = "1.20.0")]
393#[cfg(not(feature = "ferrocene_subset"))]
394impl fmt::Display for EscapeDebug {
395 #[inline]
396 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
397 fmt::Display::fmt(&self.0, f)
398 }
399}
400
401#[cfg(not(feature = "ferrocene_subset"))]
402macro_rules! casemappingiter_impls {
403 ($(#[$attr:meta])* $ITER_NAME:ident) => {
404 $(#[$attr])*
405 #[stable(feature = "rust1", since = "1.0.0")]
406 #[derive(Debug, Clone)]
407 pub struct $ITER_NAME(CaseMappingIter);
408
409 #[stable(feature = "rust1", since = "1.0.0")]
410 impl Iterator for $ITER_NAME {
411 type Item = char;
412 fn next(&mut self) -> Option<char> {
413 self.0.next()
414 }
415
416 fn size_hint(&self) -> (usize, Option<usize>) {
417 self.0.size_hint()
418 }
419
420 fn fold<Acc, Fold>(self, init: Acc, fold: Fold) -> Acc
421 where
422 Fold: FnMut(Acc, Self::Item) -> Acc,
423 {
424 self.0.fold(init, fold)
425 }
426
427 fn count(self) -> usize {
428 self.0.count()
429 }
430
431 fn last(self) -> Option<Self::Item> {
432 self.0.last()
433 }
434
435 fn advance_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
436 self.0.advance_by(n)
437 }
438
439 unsafe fn __iterator_get_unchecked(&mut self, idx: usize) -> Self::Item {
440 unsafe { self.0.__iterator_get_unchecked(idx) }
442 }
443 }
444
445 #[stable(feature = "case_mapping_double_ended", since = "1.59.0")]
446 impl DoubleEndedIterator for $ITER_NAME {
447 fn next_back(&mut self) -> Option<char> {
448 self.0.next_back()
449 }
450
451 fn rfold<Acc, Fold>(self, init: Acc, rfold: Fold) -> Acc
452 where
453 Fold: FnMut(Acc, Self::Item) -> Acc,
454 {
455 self.0.rfold(init, rfold)
456 }
457
458 fn advance_back_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
459 self.0.advance_back_by(n)
460 }
461 }
462
463 #[stable(feature = "fused", since = "1.26.0")]
464 impl FusedIterator for $ITER_NAME {}
465
466 #[stable(feature = "exact_size_case_mapping_iter", since = "1.35.0")]
467 impl ExactSizeIterator for $ITER_NAME {
468 fn len(&self) -> usize {
469 self.0.len()
470 }
471
472 fn is_empty(&self) -> bool {
473 self.0.is_empty()
474 }
475 }
476
477 #[unstable(feature = "trusted_len", issue = "37572")]
479 unsafe impl TrustedLen for $ITER_NAME {}
480
481 #[doc(hidden)]
483 #[unstable(feature = "std_internals", issue = "none")]
484 unsafe impl TrustedRandomAccessNoCoerce for $ITER_NAME {
485 const MAY_HAVE_SIDE_EFFECT: bool = false;
486 }
487
488 #[doc(hidden)]
490 #[unstable(feature = "std_internals", issue = "none")]
491 unsafe impl TrustedRandomAccess for $ITER_NAME {}
492
493 #[stable(feature = "char_struct_display", since = "1.16.0")]
494 impl fmt::Display for $ITER_NAME {
495 #[inline]
496 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
497 fmt::Display::fmt(&self.0, f)
498 }
499 }
500 }
501}
502
503#[cfg(not(feature = "ferrocene_subset"))]
504casemappingiter_impls! {
505 ToLowercase
512}
513
514#[cfg(not(feature = "ferrocene_subset"))]
515casemappingiter_impls! {
516 ToUppercase
523}
524
525#[derive(Debug, Clone)]
526#[cfg(not(feature = "ferrocene_subset"))]
527struct CaseMappingIter(core::array::IntoIter<char, 3>);
528
529#[cfg(not(feature = "ferrocene_subset"))]
530impl CaseMappingIter {
531 #[inline]
532 fn new(chars: [char; 3]) -> CaseMappingIter {
533 let mut iter = chars.into_iter();
534 if chars[2] == '\0' {
535 iter.next_back();
536 if chars[1] == '\0' {
537 iter.next_back();
538
539 }
542 }
543 CaseMappingIter(iter)
544 }
545}
546
547#[cfg(not(feature = "ferrocene_subset"))]
548impl Iterator for CaseMappingIter {
549 type Item = char;
550
551 fn next(&mut self) -> Option<char> {
552 self.0.next()
553 }
554
555 fn size_hint(&self) -> (usize, Option<usize>) {
556 self.0.size_hint()
557 }
558
559 fn fold<Acc, Fold>(self, init: Acc, fold: Fold) -> Acc
560 where
561 Fold: FnMut(Acc, Self::Item) -> Acc,
562 {
563 self.0.fold(init, fold)
564 }
565
566 fn count(self) -> usize {
567 self.0.count()
568 }
569
570 fn last(self) -> Option<Self::Item> {
571 self.0.last()
572 }
573
574 fn advance_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
575 self.0.advance_by(n)
576 }
577
578 unsafe fn __iterator_get_unchecked(&mut self, idx: usize) -> Self::Item {
579 unsafe { self.0.__iterator_get_unchecked(idx) }
581 }
582}
583
584#[cfg(not(feature = "ferrocene_subset"))]
585impl DoubleEndedIterator for CaseMappingIter {
586 fn next_back(&mut self) -> Option<char> {
587 self.0.next_back()
588 }
589
590 fn rfold<Acc, Fold>(self, init: Acc, rfold: Fold) -> Acc
591 where
592 Fold: FnMut(Acc, Self::Item) -> Acc,
593 {
594 self.0.rfold(init, rfold)
595 }
596
597 fn advance_back_by(&mut self, n: usize) -> Result<(), NonZero<usize>> {
598 self.0.advance_back_by(n)
599 }
600}
601
602#[cfg(not(feature = "ferrocene_subset"))]
603impl ExactSizeIterator for CaseMappingIter {
604 fn len(&self) -> usize {
605 self.0.len()
606 }
607
608 fn is_empty(&self) -> bool {
609 self.0.is_empty()
610 }
611}
612
613#[cfg(not(feature = "ferrocene_subset"))]
614impl FusedIterator for CaseMappingIter {}
615
616#[cfg(not(feature = "ferrocene_subset"))]
618unsafe impl TrustedLen for CaseMappingIter {}
619
620#[cfg(not(feature = "ferrocene_subset"))]
622unsafe impl TrustedRandomAccessNoCoerce for CaseMappingIter {
623 const MAY_HAVE_SIDE_EFFECT: bool = false;
624}
625
626#[cfg(not(feature = "ferrocene_subset"))]
628unsafe impl TrustedRandomAccess for CaseMappingIter {}
629
630#[cfg(not(feature = "ferrocene_subset"))]
631impl fmt::Display for CaseMappingIter {
632 #[inline]
633 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
634 for c in self.0.clone() {
635 f.write_char(c)?;
636 }
637 Ok(())
638 }
639}
640
641#[stable(feature = "u8_from_char", since = "1.59.0")]
643#[derive(Debug, Copy, Clone, PartialEq, Eq)]
644#[cfg(not(feature = "ferrocene_subset"))]
645pub struct TryFromCharError(pub(crate) ());
646
647#[stable(feature = "u8_from_char", since = "1.59.0")]
648#[cfg(not(feature = "ferrocene_subset"))]
649impl fmt::Display for TryFromCharError {
650 fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result {
651 "unicode code point out of range".fmt(fmt)
652 }
653}
654
655#[stable(feature = "u8_from_char", since = "1.59.0")]
656#[cfg(not(feature = "ferrocene_subset"))]
657impl Error for TryFromCharError {}