@@ -187,11 +187,19 @@ impl AtomType {
187187 // which would cause divisions by zero in rust-phf.
188188 self . atoms . insert ( String :: new ( ) ) ;
189189
190- let atoms: Vec < & str > = self . atoms . iter ( ) . map ( |s| & * * s) . collect ( ) ;
191- let hash_state = phf_generator:: generate_hash ( & atoms) ;
190+ // Strings over 7 bytes + empty string added to static set.
191+ // Otherwise stored inline.
192+ let ( static_strs, inline_strs) : ( Vec < _ > , Vec < _ > ) = self
193+ . atoms
194+ . iter ( )
195+ . map ( String :: as_str)
196+ . partition ( |s| s. len ( ) > 7 || s. is_empty ( ) ) ;
197+
198+ // Static strings
199+ let hash_state = phf_generator:: generate_hash ( & static_strs) ;
192200 let phf_generator:: HashState { key, disps, map } = hash_state;
193201 let ( disps0, disps1) : ( Vec < _ > , Vec < _ > ) = disps. into_iter ( ) . unzip ( ) ;
194- let atoms: Vec < & str > = map. iter ( ) . map ( |& idx| atoms [ idx] ) . collect ( ) ;
202+ let atoms: Vec < & str > = map. iter ( ) . map ( |& idx| static_strs [ idx] ) . collect ( ) ;
195203 let empty_string_index = atoms. iter ( ) . position ( |s| s. is_empty ( ) ) . unwrap ( ) as u32 ;
196204 let indices = 0 ..atoms. len ( ) as u32 ;
197205
@@ -228,16 +236,33 @@ impl AtomType {
228236 let macro_name = new_term ( & * self . macro_name ) ;
229237 let module = module. parse :: < proc_macro2:: TokenStream > ( ) . unwrap ( ) ;
230238 let atom_prefix = format ! ( "ATOM_{}_" , type_name. to_string( ) . to_uppercase( ) ) ;
231- let const_names: Vec < _ > = atoms
239+ let new_const_name = |atom : & str | {
240+ let mut name = atom_prefix. clone ( ) ;
241+ for c in atom. chars ( ) {
242+ name. push_str ( & format ! ( "_{:02X}" , c as u32 ) )
243+ }
244+ new_term ( & name)
245+ } ;
246+ let const_names: Vec < _ > = atoms. iter ( ) . copied ( ) . map ( new_const_name) . collect ( ) ;
247+
248+ // Inline strings
249+ let ( inline_const_names, inline_values_and_lengths) : ( Vec < _ > , Vec < _ > ) = inline_strs
232250 . iter ( )
233- . map ( |atom| {
234- let mut name = atom_prefix. clone ( ) ;
235- for c in atom. chars ( ) {
236- name. push_str ( & format ! ( "_{:02X}" , c as u32 ) )
251+ . map ( |s| {
252+ let const_name = new_const_name ( s) ;
253+
254+ let mut value = 0u64 ;
255+ for ( index, c) in s. bytes ( ) . enumerate ( ) {
256+ value = value | ( ( c as u64 ) << ( index * 8 + 8 ) ) ;
237257 }
238- new_term ( & name)
258+
259+ let len = s. len ( ) as u8 ;
260+
261+ ( const_name, ( value, len) )
239262 } )
240- . collect ( ) ;
263+ . unzip ( ) ;
264+ let ( inline_values, inline_lengths) : ( Vec < _ > , Vec < _ > ) =
265+ inline_values_and_lengths. into_iter ( ) . unzip ( ) ;
241266
242267 quote ! {
243268 #atom_doc
@@ -265,13 +290,19 @@ impl AtomType {
265290 #(
266291 pub const #const_names: #type_name = #type_name:: pack_static( #indices) ;
267292 ) *
293+ #(
294+ pub const #inline_const_names: #type_name = #type_name:: pack_inline( #inline_values, #inline_lengths) ;
295+ ) *
268296
269297 #macro_doc
270298 #[ macro_export]
271299 macro_rules! #macro_name {
272300 #(
273301 ( #atoms) => { #module:: #const_names } ;
274302 ) *
303+ #(
304+ ( #inline_strs) => { #module:: #inline_const_names } ;
305+ ) *
275306 }
276307 }
277308 }
0 commit comments