Skip to content

Commit

Permalink
Mark Ident::new_raw as no longer semver-exempt
Browse files Browse the repository at this point in the history
The previous Compiler behaviour appears to have been broken, in that it
would return a non-raw string literal, so it was replaced with the
fallback code from quote [1].

[1]: https://github.com/dtolnay/quote/blob/eeabf0d42ed68418741542ab5cfa8a9d339f8a79/src/runtime.rs#L409-L422
  • Loading branch information
mystor committed Jun 19, 2022
1 parent 11dea16 commit 2ecccd0
Show file tree
Hide file tree
Showing 4 changed files with 19 additions and 13 deletions.
4 changes: 4 additions & 0 deletions build.rs
Expand Up @@ -84,6 +84,10 @@ fn main() {
println!("cargo:rustc-cfg=no_hygiene");
}

if version.minor < 47 {
println!("cargo:rustc-cfg=no_ident_new_raw");
}

if version.minor < 54 {
println!("cargo:rustc-cfg=no_literal_from_str");
}
Expand Down
4 changes: 0 additions & 4 deletions src/lib.rs
Expand Up @@ -953,10 +953,6 @@ impl Ident {
}

/// Same as `Ident::new`, but creates a raw identifier (`r#ident`).
///
/// This method is semver exempt and not exposed by default.
#[cfg(procmacro2_semver_exempt)]
#[cfg_attr(doc_cfg, doc(cfg(procmacro2_semver_exempt)))]
pub fn new_raw(string: &str, span: Span) -> Self {
Ident::_new_raw(string, span)
}
Expand Down
23 changes: 15 additions & 8 deletions src/wrapper.rs
Expand Up @@ -694,16 +694,23 @@ impl Ident {

pub fn new_raw(string: &str, span: Span) -> Self {
match span {
#[cfg(not(no_ident_new_raw))]
Span::Compiler(s) => Ident::Compiler(proc_macro::Ident::new_raw(string, s)),
#[cfg(no_ident_new_raw)]
Span::Compiler(s) => {
let p: proc_macro::TokenStream = string.parse().unwrap();
let ident = match p.into_iter().next() {
Some(proc_macro::TokenTree::Ident(mut i)) => {
i.set_span(s);
i
let _ = proc_macro::Ident::new(string, s);
// At this point, the identifier is raw, and the unraw-ed version of it was
// successfully converted into an identifier. Try to produce a valid raw
// identifier by running the `TokenStream` parser, and unwrapping the first
// token as an `Ident`.
if let Ok(ts) = format!("r#{}", string).parse::<proc_macro::TokenStream>() {
let mut iter = ts.into_iter();
if let (Some(proc_macro::TokenTree::Ident(mut id)), None) = (iter.next(), iter.next()) {
id.set_span(s);
return Ident::Compiler(id);
}
_ => panic!(),
};
Ident::Compiler(ident)
}
panic!("not allowed as a raw identifier: {}", string)
}
Span::Fallback(s) => Ident::Fallback(fallback::Ident::new_raw(string, s)),
}
Expand Down
1 change: 0 additions & 1 deletion tests/test.rs
Expand Up @@ -15,7 +15,6 @@ fn idents() {
}

#[test]
#[cfg(procmacro2_semver_exempt)]
fn raw_idents() {
assert_eq!(
Ident::new_raw("String", Span::call_site()).to_string(),
Expand Down

0 comments on commit 2ecccd0

Please sign in to comment.