@@ -29,6 +29,14 @@ pub(crate) enum LexError {
2929 Fallback ( fallback:: LexError ) ,
3030}
3131
32+ impl LexError {
33+ fn call_site ( ) -> Self {
34+ LexError :: Fallback ( fallback:: LexError {
35+ span : fallback:: Span :: call_site ( ) ,
36+ } )
37+ }
38+ }
39+
3240fn mismatch ( ) -> ! {
3341 panic ! ( "stable/nightly mismatch" )
3442}
@@ -108,11 +116,7 @@ impl FromStr for TokenStream {
108116// Work around https://github.com/rust-lang/rust/issues/58736.
109117fn proc_macro_parse ( src : & str ) -> Result < proc_macro:: TokenStream , LexError > {
110118 let result = panic:: catch_unwind ( || src. parse ( ) . map_err ( LexError :: Compiler ) ) ;
111- result. unwrap_or_else ( |_| {
112- Err ( LexError :: Fallback ( fallback:: LexError {
113- span : fallback:: Span :: call_site ( ) ,
114- } ) )
115- } )
119+ result. unwrap_or_else ( |_| Err ( LexError :: call_site ( ) ) )
116120}
117121
118122impl Display for TokenStream {
@@ -912,6 +916,30 @@ impl From<fallback::Literal> for Literal {
912916 }
913917}
914918
919+ impl FromStr for Literal {
920+ type Err = LexError ;
921+
922+ fn from_str ( repr : & str ) -> Result < Self , Self :: Err > {
923+ if inside_proc_macro ( ) {
924+ // TODO: use libproc_macro's FromStr impl once it is available in
925+ // rustc. https://github.com/rust-lang/rust/pull/84717
926+ let tokens = proc_macro_parse ( repr) ?;
927+ let mut iter = tokens. into_iter ( ) ;
928+ if let ( Some ( proc_macro:: TokenTree :: Literal ( literal) ) , None ) =
929+ ( iter. next ( ) , iter. next ( ) )
930+ {
931+ if literal. to_string ( ) . len ( ) == repr. len ( ) {
932+ return Ok ( Literal :: Compiler ( literal) ) ;
933+ }
934+ }
935+ Err ( LexError :: call_site ( ) )
936+ } else {
937+ let literal = fallback:: Literal :: from_str ( repr) ?;
938+ Ok ( Literal :: Fallback ( literal) )
939+ }
940+ }
941+ }
942+
915943impl Display for Literal {
916944 fn fmt ( & self , f : & mut fmt:: Formatter ) -> fmt:: Result {
917945 match self {
0 commit comments