--- src/ld/OutputFile.cpp +++ src/ld/OutputFile.cpp @@ -4461,14 +4461,18 @@ void OutputFile::addClassicRelocs(ld::Internal& state, ld::Internal::FinalSectio assert(minusTarget->definition() != ld::Atom::definitionProxy); assert(target != NULL); assert(target->definition() != ld::Atom::definitionProxy); - // make sure target is not global and weak - if ( (target->scope() == ld::Atom::scopeGlobal) && (target->combine() == ld::Atom::combineByName) - && (atom->section().type() != ld::Section::typeCFI) - && (atom->section().type() != ld::Section::typeDtraceDOF) - && (atom->section().type() != ld::Section::typeUnwindInfo) - && (minusTarget != target) ) { - // ok for __eh_frame and __uwind_info to use pointer diffs to global weak symbols - throwf("bad codegen, pointer diff in %s to global weak symbol %s", atom->name(), target->name()); + // check if target of pointer-diff is global and weak + if ( (target->scope() == ld::Atom::scopeGlobal) && (target->combine() == ld::Atom::combineByName) && (target->definition() == ld::Atom::definitionRegular) ) { + if ( (atom->section().type() == ld::Section::typeCFI) + || (atom->section().type() == ld::Section::typeDtraceDOF) + || (atom->section().type() == ld::Section::typeUnwindInfo) ) { + // ok for __eh_frame and __uwind_info to use pointer diffs to global weak symbols + return; + } + // Have direct reference to weak-global. This should be an indrect reference + warning("direct access in %s to global weak symbol %s means the weak symbol cannot be overriden at runtime. " + "This was likely caused by different translation units being compiled with different visiblity settings.", + atom->name(), target->name()); } return; } -- 2.10.1