void LTOModule::addPotentialUndefinedSymbol(GlobalValue* decl, Mangler &mangler) { const char* name = mangler.getValueName(decl).c_str(); // ignore all llvm.* symbols if ( strncmp(name, "llvm.", 5) != 0 ) { _undefines[name] = 1; } }
void LTOModule::addDefinedSymbol(GlobalValue* def, Mangler &mangler, bool isFunction) { // string is owned by _defines const char* symbolName = ::strdup(mangler.getValueName(def).c_str()); // set alignment part log2() can have rounding errors uint32_t align = def->getAlignment(); uint32_t attr = align ? CountTrailingZeros_32(def->getAlignment()) : 0; // set permissions part if ( isFunction ) attr |= LTO_SYMBOL_PERMISSIONS_CODE; else { GlobalVariable* gv = dyn_cast<GlobalVariable>(def); if ( (gv != NULL) && gv->isConstant() ) attr |= LTO_SYMBOL_PERMISSIONS_RODATA; else attr |= LTO_SYMBOL_PERMISSIONS_DATA; } // set definition part if ( def->hasWeakLinkage() || def->hasLinkOnceLinkage() ) { // lvm bitcode does not differenciate between weak def data // and tentative definitions! // HACK HACK HACK // C++ does not use tentative definitions, but does use weak symbols // so guess that anything that looks like a C++ symbol is weak and others // are tentative definitions if ( (strncmp(symbolName, "__Z", 3) == 0) ) attr |= LTO_SYMBOL_DEFINITION_WEAK; else { attr |= LTO_SYMBOL_DEFINITION_TENTATIVE; } } else { attr |= LTO_SYMBOL_DEFINITION_REGULAR; } // set scope part if ( def->hasHiddenVisibility() ) attr |= LTO_SYMBOL_SCOPE_HIDDEN; else if ( def->hasExternalLinkage() || def->hasWeakLinkage() ) attr |= LTO_SYMBOL_SCOPE_DEFAULT; else attr |= LTO_SYMBOL_SCOPE_INTERNAL; // add to table of symbols NameAndAttributes info; info.name = symbolName; info.attributes = (lto_symbol_attributes)attr; _symbols.push_back(info); _defines[info.name] = 1; }
// Find exeternal symbols referenced by VALUE. This is a recursive function. static void findExternalRefs(Value *value, std::set<std::string> &references, Mangler &mangler) { if (GlobalValue *gv = dyn_cast<GlobalValue>(value)) { LTOLinkageTypes lt = getLTOLinkageType(gv); if (lt != LTOInternalLinkage && strncmp (gv->getName().c_str(), "llvm.", 5)) references.insert(mangler.getValueName(gv)); } // GlobalValue, even with InternalLinkage type, may have operands with // ExternalLinkage type. Do not ignore these operands. if (Constant *c = dyn_cast<Constant>(value)) // Handle ConstantExpr, ConstantStruct, ConstantArry etc.. for (unsigned i = 0, e = c->getNumOperands(); i != e; ++i) findExternalRefs(c->getOperand(i), references, mangler); }