+ if (!DGV && !SGA->hasLocalLinkage()) {
+ DGV = Dest->getGlobalVariable(SGA->getName());
+
+ // If types don't agree due to opaque types, try to resolve them.
+ if (DGV && DGV->getType() != SGA->getType())
+ RecursiveResolveTypes(SGA->getType(), DGV->getType());
+ }
+
+ if (!DGV && !SGA->hasLocalLinkage()) {
+ DGV = Dest->getFunction(SGA->getName());
+
+ // If types don't agree due to opaque types, try to resolve them.
+ if (DGV && DGV->getType() != SGA->getType())
+ RecursiveResolveTypes(SGA->getType(), DGV->getType());
+ }
+
+ // No linking to be performed on internal stuff.
+ if (DGV && DGV->hasLocalLinkage())
+ DGV = NULL;
+
+ if (GlobalAlias *DGA = dyn_cast_or_null<GlobalAlias>(DGV)) {
+ // Types are known to be the same, check whether aliasees equal. As
+ // globals are already linked we just need query ValueMap to find the
+ // mapping.
+ if (DAliasee == DGA->getAliasedGlobal()) {
+ // This is just two copies of the same alias. Propagate linkage, if
+ // necessary.
+ DGA->setLinkage(CalculateAliasLinkage(SGA, DGA));
+
+ NewGA = DGA;
+ // Proceed to 'common' steps
+ } else
+ return Error(Err, "Alias Collision on '" + SGA->getName()+
+ "': aliases have different aliasees");
+ } else if (GlobalVariable *DGVar = dyn_cast_or_null<GlobalVariable>(DGV)) {
+ // The only allowed way is to link alias with external declaration or weak
+ // symbol..
+ if (DGVar->isDeclaration() || DGVar->mayBeOverridden()) {
+ // But only if aliasee is global too...
+ if (!isa<GlobalVariable>(DAliasee))
+ return Error(Err, "Global-Alias Collision on '" + SGA->getName() +
+ "': aliasee is not global variable");
+
+ NewGA = new GlobalAlias(SGA->getType(), SGA->getLinkage(),
+ SGA->getName(), DAliasee, Dest);
+ CopyGVAttributes(NewGA, SGA);
+
+ // Any uses of DGV need to change to NewGA, with cast, if needed.
+ if (SGA->getType() != DGVar->getType())
+ DGVar->replaceAllUsesWith(ConstantExpr::getBitCast(NewGA,
+ DGVar->getType()));
+ else
+ DGVar->replaceAllUsesWith(NewGA);
+
+ // DGVar will conflict with NewGA because they both had the same
+ // name. We must erase this now so ForceRenaming doesn't assert
+ // because DGV might not have internal linkage.
+ DGVar->eraseFromParent();
+
+ // Proceed to 'common' steps
+ } else
+ return Error(Err, "Global-Alias Collision on '" + SGA->getName() +
+ "': symbol multiple defined");
+ } else if (Function *DF = dyn_cast_or_null<Function>(DGV)) {
+ // The only allowed way is to link alias with external declaration or weak
+ // symbol...
+ if (DF->isDeclaration() || DF->mayBeOverridden()) {
+ // But only if aliasee is function too...
+ if (!isa<Function>(DAliasee))
+ return Error(Err, "Function-Alias Collision on '" + SGA->getName() +
+ "': aliasee is not function");
+
+ NewGA = new GlobalAlias(SGA->getType(), SGA->getLinkage(),
+ SGA->getName(), DAliasee, Dest);
+ CopyGVAttributes(NewGA, SGA);
+
+ // Any uses of DF need to change to NewGA, with cast, if needed.
+ if (SGA->getType() != DF->getType())
+ DF->replaceAllUsesWith(ConstantExpr::getBitCast(NewGA,
+ DF->getType()));
+ else
+ DF->replaceAllUsesWith(NewGA);
+
+ // DF will conflict with NewGA because they both had the same
+ // name. We must erase this now so ForceRenaming doesn't assert
+ // because DF might not have internal linkage.
+ DF->eraseFromParent();
+
+ // Proceed to 'common' steps
+ } else
+ return Error(Err, "Function-Alias Collision on '" + SGA->getName() +
+ "': symbol multiple defined");
+ } else {
+ // No linking to be performed, simply create an identical version of the
+ // alias over in the dest module...
+
+ NewGA = new GlobalAlias(SGA->getType(), SGA->getLinkage(),
+ SGA->getName(), DAliasee, Dest);
+ CopyGVAttributes(NewGA, SGA);