@@ -116,10 +116,7 @@ impl<'tcx> SymbolMangler<'tcx> {
116116 /// * `x > 0` is encoded as `x - 1` in base 62, followed by `"_"`,
117117 /// e.g. `1` becomes `"0_"`, `62` becomes `"Z_"`, etc.
118118 fn push_integer_62 ( & mut self , x : u64 ) {
119- if let Some ( x) = x. checked_sub ( 1 ) {
120- base_n:: push_str ( x as u128 , 62 , & mut self . out ) ;
121- }
122- self . push ( "_" ) ;
119+ push_integer_62 ( x, & mut self . out )
123120 }
124121
125122 /// Push a `tag`-prefixed base 62 integer, when larger than `0`, that is:
@@ -138,45 +135,7 @@ impl<'tcx> SymbolMangler<'tcx> {
138135 }
139136
140137 fn push_ident ( & mut self , ident : & str ) {
141- let mut use_punycode = false ;
142- for b in ident. bytes ( ) {
143- match b {
144- b'_' | b'a' ..=b'z' | b'A' ..=b'Z' | b'0' ..=b'9' => { }
145- 0x80 ..=0xff => use_punycode = true ,
146- _ => bug ! ( "symbol_names: bad byte {} in ident {:?}" , b, ident) ,
147- }
148- }
149-
150- let punycode_string;
151- let ident = if use_punycode {
152- self . push ( "u" ) ;
153-
154- // FIXME(eddyb) we should probably roll our own punycode implementation.
155- let mut punycode_bytes = match punycode:: encode ( ident) {
156- Ok ( s) => s. into_bytes ( ) ,
157- Err ( ( ) ) => bug ! ( "symbol_names: punycode encoding failed for ident {:?}" , ident) ,
158- } ;
159-
160- // Replace `-` with `_`.
161- if let Some ( c) = punycode_bytes. iter_mut ( ) . rfind ( |& & mut c| c == b'-' ) {
162- * c = b'_' ;
163- }
164-
165- // FIXME(eddyb) avoid rechecking UTF-8 validity.
166- punycode_string = String :: from_utf8 ( punycode_bytes) . unwrap ( ) ;
167- & punycode_string
168- } else {
169- ident
170- } ;
171-
172- let _ = write ! ( self . out, "{}" , ident. len( ) ) ;
173-
174- // Write a separating `_` if necessary (leading digit or `_`).
175- if let Some ( '_' | '0' ..='9' ) = ident. chars ( ) . next ( ) {
176- self . push ( "_" ) ;
177- }
178-
179- self . push ( ident) ;
138+ push_ident ( ident, & mut self . out )
180139 }
181140
182141 fn path_append_ns (
@@ -836,3 +795,62 @@ impl<'tcx> Printer<'tcx> for SymbolMangler<'tcx> {
836795 Ok ( ( ) )
837796 }
838797}
798+ /// Push a `_`-terminated base 62 integer, using the format
799+ /// specified in the RFC as `<base-62-number>`, that is:
800+ /// * `x = 0` is encoded as just the `"_"` terminator
801+ /// * `x > 0` is encoded as `x - 1` in base 62, followed by `"_"`,
802+ /// e.g. `1` becomes `"0_"`, `62` becomes `"Z_"`, etc.
803+ pub ( crate ) fn push_integer_62 ( x : u64 , output : & mut String ) {
804+ if let Some ( x) = x. checked_sub ( 1 ) {
805+ base_n:: push_str ( x as u128 , 62 , output) ;
806+ }
807+ output. push ( '_' ) ;
808+ }
809+
810+ pub ( crate ) fn encode_integer_62 ( x : u64 ) -> String {
811+ let mut output = String :: new ( ) ;
812+ push_integer_62 ( x, & mut output) ;
813+ output
814+ }
815+
816+ pub ( crate ) fn push_ident ( ident : & str , output : & mut String ) {
817+ let mut use_punycode = false ;
818+ for b in ident. bytes ( ) {
819+ match b {
820+ b'_' | b'a' ..=b'z' | b'A' ..=b'Z' | b'0' ..=b'9' => { }
821+ 0x80 ..=0xff => use_punycode = true ,
822+ _ => bug ! ( "symbol_names: bad byte {} in ident {:?}" , b, ident) ,
823+ }
824+ }
825+
826+ let punycode_string;
827+ let ident = if use_punycode {
828+ output. push ( 'u' ) ;
829+
830+ // FIXME(eddyb) we should probably roll our own punycode implementation.
831+ let mut punycode_bytes = match punycode:: encode ( ident) {
832+ Ok ( s) => s. into_bytes ( ) ,
833+ Err ( ( ) ) => bug ! ( "symbol_names: punycode encoding failed for ident {:?}" , ident) ,
834+ } ;
835+
836+ // Replace `-` with `_`.
837+ if let Some ( c) = punycode_bytes. iter_mut ( ) . rfind ( |& & mut c| c == b'-' ) {
838+ * c = b'_' ;
839+ }
840+
841+ // FIXME(eddyb) avoid rechecking UTF-8 validity.
842+ punycode_string = String :: from_utf8 ( punycode_bytes) . unwrap ( ) ;
843+ & punycode_string
844+ } else {
845+ ident
846+ } ;
847+
848+ let _ = write ! ( output, "{}" , ident. len( ) ) ;
849+
850+ // Write a separating `_` if necessary (leading digit or `_`).
851+ if let Some ( '_' | '0' ..='9' ) = ident. chars ( ) . next ( ) {
852+ output. push ( '_' ) ;
853+ }
854+
855+ output. push_str ( ident) ;
856+ }
0 commit comments