@@ -268,33 +268,24 @@ impl OutputTypes {
268268// DO NOT switch BTreeMap or BTreeSet out for an unsorted container type! That
269269// would break dependency tracking for command-line arguments.
270270#[ derive( Clone , Hash ) ]
271- pub struct Externs ( BTreeMap < String , BTreeSet < Option < String > > > ) ;
271+ pub struct Externs ( BTreeMap < String , BTreeSet < ExternEntry > > ) ;
272272
273+ #[ derive( Clone , Hash , Eq , PartialEq , Ord , PartialOrd , Debug ) ]
274+ pub struct ExternEntry {
275+ pub location : Option < String > ,
276+ pub public : bool
277+ }
273278
274279impl Externs {
275- pub fn new ( data : BTreeMap < String , BTreeSet < Option < String > > > ) -> Externs {
280+ pub fn new ( data : BTreeMap < String , BTreeSet < ExternEntry > > ) -> Externs {
276281 Externs ( data)
277282 }
278283
279- pub fn get ( & self , key : & str ) -> Option < & BTreeSet < Option < String > > > {
280- self . 0 . get ( key)
281- }
282-
283- pub fn iter < ' a > ( & ' a self ) -> BTreeMapIter < ' a , String , BTreeSet < Option < String > > > {
284- self . 0 . iter ( )
285- }
286- }
287-
288- // Similar to 'Externs', but used for the '--extern-private' option
289- #[ derive( Clone , Hash ) ]
290- pub struct ExternPrivates ( BTreeMap < String , BTreeSet < String > > ) ;
291-
292- impl ExternPrivates {
293- pub fn get ( & self , key : & str ) -> Option < & BTreeSet < String > > {
284+ pub fn get ( & self , key : & str ) -> Option < & BTreeSet < ExternEntry > > {
294285 self . 0 . get ( key)
295286 }
296287
297- pub fn iter < ' a > ( & ' a self ) -> BTreeMapIter < ' a , String , BTreeSet < String > > {
288+ pub fn iter < ' a > ( & ' a self ) -> BTreeMapIter < ' a , String , BTreeSet < ExternEntry > > {
298289 self . 0 . iter ( )
299290 }
300291}
@@ -431,7 +422,7 @@ top_level_options!(
431422
432423 // The crates to consider private when
433424 // checking leaked private dependency types in public interfaces
434- extern_private: ExternPrivates [ UNTRACKED ] ,
425+ // extern_private: ExternPrivates [UNTRACKED],
435426 }
436427) ;
437428
@@ -634,7 +625,7 @@ impl Default for Options {
634625 cli_forced_thinlto_off : false ,
635626 remap_path_prefix : Vec :: new ( ) ,
636627 edition : DEFAULT_EDITION ,
637- extern_private : ExternPrivates ( BTreeMap :: new ( ) )
628+ // extern_private: ExternPrivates(BTreeMap::new())
638629 }
639630 }
640631}
@@ -2304,7 +2295,7 @@ pub fn build_session_options_and_crate_config(
23042295 )
23052296 }
23062297
2307- let mut extern_private: BTreeMap < _ , BTreeSet < _ > > = BTreeMap :: new ( ) ;
2298+ /* let mut extern_private: BTreeMap<_, BTreeSet<_>> = BTreeMap::new();
23082299
23092300 for arg in matches.opt_strs("extern-private").into_iter() {
23102301 let mut parts = arg.splitn(2, '=');
@@ -2319,10 +2310,16 @@ pub fn build_session_options_and_crate_config(
23192310 .or_default()
23202311 .insert(location);
23212312
2322- }
2313+ }*/
2314+
2315+ // We start out with a Vec<(Option<String>, bool)>>,
2316+ // and later convert it into a BTreeSet<(Option<String>, bool)>
2317+ // This allows to modify entries in-place to set their correct
2318+ // 'public' value
2319+ let mut externs: BTreeMap < _ , BTreeMap < Option < String > , bool > > = BTreeMap :: new ( ) ;
2320+ for ( arg, public) in matches. opt_strs ( "extern" ) . into_iter ( ) . map ( |v| ( v, true ) )
2321+ . chain ( matches. opt_strs ( "extern-private" ) . into_iter ( ) . map ( |v| ( v, false ) ) ) {
23232322
2324- let mut externs: BTreeMap < _ , BTreeSet < _ > > = BTreeMap :: new ( ) ;
2325- for arg in matches. opt_strs ( "extern" ) . into_iter ( ) {
23262323 let mut parts = arg. splitn ( 2 , '=' ) ;
23272324 let name = parts. next ( ) . unwrap_or_else ( ||
23282325 early_error ( error_format, "--extern value must not be empty" ) ) ;
@@ -2335,11 +2332,37 @@ pub fn build_session_options_and_crate_config(
23352332 ) ;
23362333 } ;
23372334
2335+
2336+ // Externsl crates start out public,
2337+ // and become private if we later see
2338+ // an '--extern-private' key. They never
2339+ // go back to being public once we've seen
2340+ // '--extern-private', so we logical-AND
2341+ // their current and new 'public' value together
2342+
23382343 externs
23392344 . entry ( name. to_owned ( ) )
23402345 . or_default ( )
2341- . insert ( location) ;
2342- }
2346+ . entry ( location)
2347+ . and_modify ( |e| * e &= public)
2348+ . or_insert ( public) ;
2349+ }
2350+
2351+ // Now that we've determined the 'public' status of each extern,
2352+ // collect them into a set of ExternEntry
2353+ let externs: BTreeMap < String , BTreeSet < ExternEntry > > = externs. into_iter ( )
2354+ . map ( |( k, v) | {
2355+ let values =v. into_iter ( ) . map ( |( location, public) | {
2356+ ExternEntry {
2357+ location,
2358+ public
2359+ }
2360+ } ) . collect :: < BTreeSet < ExternEntry > > ( ) ;
2361+ ( k, values)
2362+ } )
2363+ . collect ( ) ;
2364+
2365+
23432366
23442367 let crate_name = matches. opt_str ( "crate-name" ) ;
23452368
@@ -2390,7 +2413,7 @@ pub fn build_session_options_and_crate_config(
23902413 cli_forced_thinlto_off : disable_thinlto,
23912414 remap_path_prefix,
23922415 edition,
2393- extern_private : ExternPrivates ( extern_private)
2416+ // extern_private: ExternPrivates(extern_private)
23942417 } ,
23952418 cfg,
23962419 )
0 commit comments