@@ -517,6 +517,22 @@ static void embedBitcode(llvm::Module *M, const IRGenOptions &Opts)
517
517
if (Opts.EmbedMode == IRGenEmbedMode::None)
518
518
return ;
519
519
520
+ // Save llvm.compiler.used and remove it.
521
+ SmallVector<llvm::Constant*, 2 > UsedArray;
522
+ SmallSet<llvm::GlobalValue*, 4 > UsedGlobals;
523
+ auto *UsedElementType =
524
+ llvm::Type::getInt8Ty (M->getContext ())->getPointerTo (0 );
525
+ llvm::GlobalVariable *Used =
526
+ collectUsedGlobalVariables (*M, UsedGlobals, true );
527
+ for (auto *GV : UsedGlobals) {
528
+ if (GV->getName () != " llvm.embedded.module" &&
529
+ GV->getName () != " llvm.cmdline" )
530
+ UsedArray.push_back (
531
+ ConstantExpr::getPointerBitCastOrAddrSpaceCast (GV, UsedElementType));
532
+ }
533
+ if (Used)
534
+ Used->eraseFromParent ();
535
+
520
536
// Embed the bitcode for the llvm module.
521
537
std::string Data;
522
538
llvm::raw_string_ostream OS (Data);
@@ -526,14 +542,15 @@ static void embedBitcode(llvm::Module *M, const IRGenOptions &Opts)
526
542
ArrayRef<uint8_t > ModuleData ((uint8_t *)OS.str ().data (), OS.str ().size ());
527
543
llvm::Constant *ModuleConstant =
528
544
llvm::ConstantDataArray::get (M->getContext (), ModuleData);
529
- // Use Appending linkage so it doesn't get optimized out.
530
545
llvm::GlobalVariable *GV = new llvm::GlobalVariable (*M,
531
546
ModuleConstant->getType (), true ,
532
- llvm::GlobalValue::AppendingLinkage ,
547
+ llvm::GlobalValue::PrivateLinkage ,
533
548
ModuleConstant);
549
+ UsedArray.push_back (
550
+ llvm::ConstantExpr::getPointerBitCastOrAddrSpaceCast (GV, UsedElementType));
534
551
GV->setSection (" __LLVM,__bitcode" );
535
552
if (llvm::GlobalVariable *Old =
536
- M->getGlobalVariable (" llvm.embedded.module" )) {
553
+ M->getGlobalVariable (" llvm.embedded.module" , true )) {
537
554
GV->takeName (Old);
538
555
Old->replaceAllUsesWith (GV);
539
556
delete Old;
@@ -547,16 +564,28 @@ static void embedBitcode(llvm::Module *M, const IRGenOptions &Opts)
547
564
llvm::Constant *CmdConstant =
548
565
llvm::ConstantDataArray::get (M->getContext (), CmdData);
549
566
GV = new llvm::GlobalVariable (*M, CmdConstant->getType (), true ,
550
- llvm::GlobalValue::AppendingLinkage ,
567
+ llvm::GlobalValue::PrivateLinkage ,
551
568
CmdConstant);
552
569
GV->setSection (" __LLVM,__swift_cmdline" );
553
- if (llvm::GlobalVariable *Old = M->getGlobalVariable (" llvm.cmdline" )) {
570
+ UsedArray.push_back (
571
+ llvm::ConstantExpr::getPointerBitCastOrAddrSpaceCast (GV, UsedElementType));
572
+ if (llvm::GlobalVariable *Old = M->getGlobalVariable (" llvm.cmdline" , true )) {
554
573
GV->takeName (Old);
555
574
Old->replaceAllUsesWith (GV);
556
575
delete Old;
557
576
} else {
558
577
GV->setName (" llvm.cmdline" );
559
578
}
579
+
580
+ if (UsedArray.empty ())
581
+ return ;
582
+
583
+ // Recreate llvm.compiler.used.
584
+ auto *ATy = llvm::ArrayType::get (UsedElementType, UsedArray.size ());
585
+ auto *NewUsed = new GlobalVariable (
586
+ *M, ATy, false , llvm::GlobalValue::AppendingLinkage,
587
+ llvm::ConstantArray::get (ATy, UsedArray), " llvm.compiler.used" );
588
+ NewUsed->setSection (" llvm.metadata" );
560
589
}
561
590
562
591
static void initLLVMModule (const IRGenModule &IGM) {
0 commit comments