@@ -548,42 +548,92 @@ static void parseModuleDefs(StringRef Path) {
548
548
}
549
549
}
550
550
551
- // Get a set of symbols not to automatically export
552
- // when exporting all global symbols for MinGW.
553
- static StringSet<> getExportExcludeSymbols () {
554
- if (Config->Machine == I386)
555
- return {
556
- " __NULL_IMPORT_DESCRIPTOR" ,
557
- " __pei386_runtime_relocator" ,
558
- " _do_pseudo_reloc" ,
559
- " _impure_ptr" ,
560
- " __impure_ptr" ,
561
- " __fmode" ,
562
- " _environ" ,
563
- " ___dso_handle" ,
564
- // These are the MinGW names that differ from the standard
565
- // ones (lacking an extra underscore).
566
- " _DllMain@12" ,
567
- " _DllEntryPoint@12" ,
568
- " _DllMainCRTStartup@12" ,
569
- };
570
-
571
- return {
572
- " _NULL_IMPORT_DESCRIPTOR" ,
573
- " _pei386_runtime_relocator" ,
574
- " do_pseudo_reloc" ,
575
- " impure_ptr" ,
576
- " _impure_ptr" ,
577
- " _fmode" ,
578
- " environ" ,
579
- " __dso_handle" ,
580
- // These are the MinGW names that differ from the standard
581
- // ones (lacking an extra underscore).
582
- " DllMain" ,
583
- " DllEntryPoint" ,
584
- " DllMainCRTStartup" ,
551
+ // Logic for deciding what symbols to export, when exporting all
552
+ // symbols for MinGW.
553
+ class AutoExporter {
554
+ public:
555
+ AutoExporter () {
556
+ if (Config->Machine == I386)
557
+ ExcludeSymbols = {
558
+ " __NULL_IMPORT_DESCRIPTOR" ,
559
+ " __pei386_runtime_relocator" ,
560
+ " _do_pseudo_reloc" ,
561
+ " _impure_ptr" ,
562
+ " __impure_ptr" ,
563
+ " __fmode" ,
564
+ " _environ" ,
565
+ " ___dso_handle" ,
566
+ // These are the MinGW names that differ from the standard
567
+ // ones (lacking an extra underscore).
568
+ " _DllMain@12" ,
569
+ " _DllEntryPoint@12" ,
570
+ " _DllMainCRTStartup@12" ,
571
+ };
572
+ else
573
+ ExcludeSymbols = {
574
+ " _NULL_IMPORT_DESCRIPTOR" ,
575
+ " _pei386_runtime_relocator" ,
576
+ " do_pseudo_reloc" ,
577
+ " impure_ptr" ,
578
+ " _impure_ptr" ,
579
+ " _fmode" ,
580
+ " environ" ,
581
+ " __dso_handle" ,
582
+ // These are the MinGW names that differ from the standard
583
+ // ones (lacking an extra underscore).
584
+ " DllMain" ,
585
+ " DllEntryPoint" ,
586
+ " DllMainCRTStartup" ,
587
+ };
588
+ }
589
+
590
+ StringSet<> ExcludeSymbols;
591
+ StringSet<> ExcludeLibs = {
592
+ " libgcc" ,
593
+ " libgcc_s" ,
594
+ " libstdc++" ,
595
+ " libmingw32" ,
596
+ " libmingwex" ,
597
+ " libg2c" ,
598
+ " libsupc++" ,
599
+ " libobjc" ,
600
+ " libgcj" ,
601
+ " libclang_rt.builtins-aarch64" ,
602
+ " libclang_rt.builtins-arm" ,
603
+ " libclang_rt.builtins-i386" ,
604
+ " libclang_rt.builtins-x86_64" ,
605
+ };
606
+ StringSet<> ExcludeObjects = {
607
+ " crt0.o" ,
608
+ " crt1.o" ,
609
+ " crt1u.o" ,
610
+ " crt2.o" ,
611
+ " crt2u.o" ,
612
+ " dllcrt1.o" ,
613
+ " dllcrt2.o" ,
614
+ " gcrt0.o" ,
615
+ " gcrt1.o" ,
616
+ " gcrt2.o" ,
617
+ " crtbegin.o" ,
618
+ " crtend.o" ,
585
619
};
586
- }
620
+
621
+ bool shouldExport (Defined *Sym) const {
622
+ if (!Sym || !Sym->isLive () || !Sym->getChunk ())
623
+ return false ;
624
+ if (ExcludeSymbols.count (Sym->getName ()))
625
+ return false ;
626
+ StringRef LibName = sys::path::filename (Sym->getFile ()->ParentName );
627
+ // Drop the file extension.
628
+ LibName = LibName.substr (0 , LibName.rfind (' .' ));
629
+ if (ExcludeLibs.count (LibName))
630
+ return false ;
631
+ StringRef FileName = sys::path::filename (Sym->getFile ()->getName ());
632
+ if (LibName.empty () && ExcludeObjects.count (FileName))
633
+ return false ;
634
+ return true ;
635
+ }
636
+ };
587
637
588
638
// This is MinGW specific.
589
639
static void writeDefFile (StringRef Name) {
@@ -1259,13 +1309,11 @@ void LinkerDriver::link(ArrayRef<const char *> ArgsArr) {
1259
1309
// are chosen to be exported.
1260
1310
if (Config->DLL && ((Config->MinGW && Config->Exports .empty ()) ||
1261
1311
Args.hasArg (OPT_export_all_symbols))) {
1262
- StringSet<> ExcludeSymbols = getExportExcludeSymbols () ;
1312
+ AutoExporter Exporter ;
1263
1313
1264
1314
Symtab->forEachSymbol ([=](Symbol *S) {
1265
1315
auto *Def = dyn_cast<Defined>(S->body ());
1266
- if (!Def || !Def->isLive () || !Def->getChunk ())
1267
- return ;
1268
- if (ExcludeSymbols.count (Def->getName ()))
1316
+ if (!Exporter.shouldExport (Def))
1269
1317
return ;
1270
1318
Export E;
1271
1319
E.Name = Def->getName ();
0 commit comments