This is an archive of the discontinued LLVM Phabricator instance.

[llvm-readobj] - Validate the DT_STRSZ value to avoid crash.
ClosedPublic

Authored by grimar on Jun 19 2020, 8:56 AM.

Details

Summary

It is possible to trigger a crash when a dynamic symbol has a
broken (too large) st_name and the DT_STRSZ is also broken.

We have the following code in the Elf_Sym_Impl<ELFT>::getName:

template <class ELFT>
Expected<StringRef> Elf_Sym_Impl<ELFT>::getName(StringRef StrTab) const {
  uint32_t Offset = this->st_name;
  if (Offset >= StrTab.size())
    return createStringError(object_error::parse_failed,
                             "st_name (0x%" PRIx32
                             ") is past the end of the string table"
                             " of size 0x%zx",
                             Offset, StrTab.size());
...

The problem is that StrTab here is a ELFDumper::DynamicStringTab member
which is not validated properly on initialization. So it is possible to bypass the
if even when the st_name is huge.

This patch fixes the issue.

Diff Detail

Event Timeline

grimar created this revision.Jun 19 2020, 8:56 AM
Herald added a project: Restricted Project. · View Herald Transcript
MaskRay accepted this revision.Jun 19 2020, 9:46 AM

Thanks!

This revision is now accepted and ready to land.Jun 19 2020, 9:46 AM
jhenderson added inline comments.Jun 22 2020, 12:31 AM
llvm/test/tools/llvm-readobj/ELF/dyn-symbols.test
485–486

This comment implies you should have a check showing we don't dump the next symbol, but I don't see such a check.

I'd expect to see some sort of -NOT line after the error to show that we don't dump the next symbol.

grimar marked an inline comment as done.Jun 22 2020, 3:02 AM
grimar added inline comments.
llvm/test/tools/llvm-readobj/ELF/dyn-symbols.test
485–486

I check the "error:..." line. Which currently means the application terminates.
If we had a warning, I'd use something like -NOT.

Does it makes sense?

jhenderson added inline comments.Jun 22 2020, 3:14 AM
llvm/test/tools/llvm-readobj/ELF/dyn-symbols.test
485–486

It makes sense, but I therefore don't think we need this symbol currently.

grimar marked 3 inline comments as done.Jun 22 2020, 3:47 AM
grimar added inline comments.
llvm/test/tools/llvm-readobj/ELF/dyn-symbols.test
485–486

We could have a logic that, for example, collects a vector with an information about symbols and then prints this information.
(We have something like this in a few places already. For example, in getVersionDependencies: https://github.com/llvm/llvm-project/blob/master/llvm/tools/llvm-readobj/ELFDumper.cpp#L634).

So technically, a error can be reported either before the symbols/after them (if we had such vector) or in the middle (with the current logic).
Here I document we report it "in the middle". Isn't it useful?

jhenderson accepted this revision.Jun 22 2020, 4:20 AM

LGTM.

llvm/test/tools/llvm-readobj/ELF/dyn-symbols.test
485–486

Okay, thanks for the explanation.

This revision was automatically updated to reflect the committed changes.
grimar marked an inline comment as done.