diff --git a/lld/ELF/Relocations.cpp b/lld/ELF/Relocations.cpp --- a/lld/ELF/Relocations.cpp +++ b/lld/ELF/Relocations.cpp @@ -714,12 +714,19 @@ // Suggest an alternative spelling of an "undefined symbol" diagnostic. Returns // the suggested symbol, which is either in the symbol table, or in the same // file of sym. +template static const Symbol *getAlternativeSpelling(const Undefined &sym, std::string &pre_hint, std::string &post_hint) { - // Build a map of local defined symbols. DenseMap map; - if (sym.file && !isa(sym.file)) { + if (auto *file = dyn_cast_or_null>(sym.file)) { + // If sym is a symbol defined in a discarded section, maybeReportDiscarded() + // will give an error. Don't suggest an alternative spelling. + if (file && sym.discardedSecIdx != 0 && + file->getSections()[sym.discardedSecIdx] == &InputSection::discarded) + return nullptr; + + // Build a map of local defined symbols. for (const Symbol *s : sym.file->getSymbols()) if (s->isLocal() && s->isDefined()) map.try_emplace(s->getName(), s); @@ -865,8 +872,8 @@ if (correctSpelling) { std::string pre_hint = ": ", post_hint; - if (const Symbol *corrected = - getAlternativeSpelling(cast(sym), pre_hint, post_hint)) { + if (const Symbol *corrected = getAlternativeSpelling( + cast(sym), pre_hint, post_hint)) { msg += "\n>>> did you mean" + pre_hint + toString(*corrected) + post_hint; if (corrected->file) msg += "\n>>> defined in: " + toString(corrected->file); diff --git a/lld/test/ELF/undef-not-suggest.test b/lld/test/ELF/undef-not-suggest.test new file mode 100644 --- /dev/null +++ b/lld/test/ELF/undef-not-suggest.test @@ -0,0 +1,56 @@ +## Check we don't suggest alternative spelling for relocations to symbols +## defined in discarded sections. + +# RUN: yaml2obj %s -o %t.o +# RUN: not ld.lld %t.o %t.o -o /dev/null 2>&1 | FileCheck %s + +# CHECK-NOT: did you mean: + +--- !ELF +FileHeader: + Class: ELFCLASS64 + Data: ELFDATA2LSB + Type: ET_REL + Machine: EM_X86_64 +Sections: + - Name: .group + Type: SHT_GROUP + Link: .symtab + Info: foo + Members: + - SectionOrType: GRP_COMDAT + - SectionOrType: .text.foo + - Name: .text.foo + Type: SHT_PROGBITS + Flags: [ SHF_ALLOC, SHF_EXECINSTR, SHF_GROUP ] + - Name: .rodata + Type: SHT_PROGBITS + Flags: [ SHF_ALLOC ] + - Name: .rela.rodata + Type: SHT_RELA + Link: .symtab + Info: .rodata + Relocations: + ## Relocation which references ".text.foo". Check we don't suggest the + ## section symbol for ".data", which has an empty name. + - Offset: 0x0 + ## .text.foo + Symbol: 1 + Type: R_X86_64_64 + ## Relocation which references "foo". Check we don't suggest "for". + - Offset: 0x8 + Symbol: foo + Type: R_X86_64_64 + - Name: .data + Type: SHT_PROGBITS +Symbols: + - Name: "" + Type: STT_SECTION + Section: .text.foo + - Name: "" + Type: STT_SECTION + Section: .data + - Name: foo + Section: .text.foo + - Name: for + Section: .data