Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
torvalds
GitHub Repository: torvalds/linux
Path: blob/master/rust/quote/ident_fragment.rs
38271 views
1
// SPDX-License-Identifier: Apache-2.0 OR MIT
2
3
use alloc::borrow::Cow;
4
use core::fmt;
5
use proc_macro2::{Ident, Span};
6
7
/// Specialized formatting trait used by `format_ident!`.
8
///
9
/// [`Ident`] arguments formatted using this trait will have their `r#` prefix
10
/// stripped, if present.
11
///
12
/// See [`format_ident!`] for more information.
13
///
14
/// [`format_ident!`]: crate::format_ident
15
pub trait IdentFragment {
16
/// Format this value as an identifier fragment.
17
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result;
18
19
/// Span associated with this `IdentFragment`.
20
///
21
/// If non-`None`, may be inherited by formatted identifiers.
22
fn span(&self) -> Option<Span> {
23
None
24
}
25
}
26
27
impl<T: IdentFragment + ?Sized> IdentFragment for &T {
28
fn span(&self) -> Option<Span> {
29
<T as IdentFragment>::span(*self)
30
}
31
32
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
33
IdentFragment::fmt(*self, f)
34
}
35
}
36
37
impl<T: IdentFragment + ?Sized> IdentFragment for &mut T {
38
fn span(&self) -> Option<Span> {
39
<T as IdentFragment>::span(*self)
40
}
41
42
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
43
IdentFragment::fmt(*self, f)
44
}
45
}
46
47
impl IdentFragment for Ident {
48
fn span(&self) -> Option<Span> {
49
Some(self.span())
50
}
51
52
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
53
let id = self.to_string();
54
if let Some(id) = id.strip_prefix("r#") {
55
fmt::Display::fmt(id, f)
56
} else {
57
fmt::Display::fmt(&id[..], f)
58
}
59
}
60
}
61
62
impl<T> IdentFragment for Cow<'_, T>
63
where
64
T: IdentFragment + ToOwned + ?Sized,
65
{
66
fn span(&self) -> Option<Span> {
67
T::span(self)
68
}
69
70
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
71
T::fmt(self, f)
72
}
73
}
74
75
// Limited set of types which this is implemented for, as we want to avoid types
76
// which will often include non-identifier characters in their `Display` impl.
77
macro_rules! ident_fragment_display {
78
($($T:ty),*) => {
79
$(
80
impl IdentFragment for $T {
81
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
82
fmt::Display::fmt(self, f)
83
}
84
}
85
)*
86
};
87
}
88
89
ident_fragment_display!(bool, str, String, char);
90
ident_fragment_display!(u8, u16, u32, u64, u128, usize);
91
92