@@ -25,10 +25,9 @@ use std::{cmp, fs};
2525
2626use syntax:: ast;
2727use syntax:: attr;
28- use syntax:: ext:: allocator:: AllocatorKind ;
28+ use syntax:: ext:: allocator:: { global_allocator_spans , AllocatorKind } ;
2929use syntax:: ext:: base:: { SyntaxExtension , SyntaxExtensionKind } ;
3030use syntax:: symbol:: { Symbol , sym} ;
31- use syntax:: visit;
3231use syntax:: { span_err, span_fatal} ;
3332use syntax_pos:: { Span , DUMMY_SP } ;
3433use log:: { debug, info, log_enabled} ;
@@ -888,7 +887,14 @@ impl<'a> CrateLoader<'a> {
888887 }
889888
890889 fn inject_allocator_crate ( & mut self , krate : & ast:: Crate ) {
891- let has_global_allocator = has_global_allocator ( krate) ;
890+ let has_global_allocator = match & * global_allocator_spans ( krate) {
891+ [ span1, span2, ..] => {
892+ self . sess . struct_span_err ( * span2, "cannot define multiple global allocators" )
893+ . span_note ( * span1, "the previous global allocator is defined here" ) . emit ( ) ;
894+ true
895+ }
896+ spans => !spans. is_empty ( )
897+ } ;
892898 self . sess . has_global_allocator . set ( has_global_allocator) ;
893899
894900 // Check to see if we actually need an allocator. This desire comes
@@ -975,25 +981,8 @@ impl<'a> CrateLoader<'a> {
975981 that implements the GlobalAlloc trait.") ;
976982 }
977983 self . sess . allocator_kind . set ( Some ( AllocatorKind :: DefaultLib ) ) ;
978-
979- fn has_global_allocator ( krate : & ast:: Crate ) -> bool {
980- struct Finder ( bool ) ;
981- let mut f = Finder ( false ) ;
982- visit:: walk_crate ( & mut f, krate) ;
983- return f. 0 ;
984-
985- impl < ' ast > visit:: Visitor < ' ast > for Finder {
986- fn visit_item ( & mut self , i : & ' ast ast:: Item ) {
987- if attr:: contains_name ( & i. attrs , sym:: global_allocator) {
988- self . 0 = true ;
989- }
990- visit:: walk_item ( self , i)
991- }
992- }
993- }
994984 }
995985
996-
997986 fn inject_dependency_if ( & self ,
998987 krate : CrateNum ,
999988 what : & str ,
0 commit comments