121 lines · cpp
1//===- BuildIDTest.cpp - Tests for getBuildID ----------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9#include "llvm/Object/BuildID.h"10#include "llvm/ADT/SmallString.h"11#include "llvm/ADT/StringRef.h"12#include "llvm/Object/ELFObjectFile.h"13#include "llvm/ObjectYAML/yaml2obj.h"14#include "llvm/Support/YAMLTraits.h"15#include "llvm/Testing/Support/Error.h"16 17#include "gtest/gtest.h"18 19using namespace llvm;20using namespace llvm::object;21 22template <class ELFT>23static Expected<ELFObjectFile<ELFT>> toBinary(SmallVectorImpl<char> &Storage,24 StringRef Yaml) {25 raw_svector_ostream OS(Storage);26 yaml::Input YIn(Yaml);27 if (!yaml::convertYAML(YIn, OS, [](const Twine &Msg) {}))28 return createStringError(std::errc::invalid_argument,29 "unable to convert YAML");30 return ELFObjectFile<ELFT>::create(MemoryBufferRef(OS.str(), "dummyELF"));31}32 33static StringRef getInvalidNoteELF(bool WithShdr) {34 static std::string WithSection(R"(35--- !ELF36FileHeader:37 Class: ELFCLASS6438 Data: ELFDATA2LSB39 Type: ET_EXEC40 Machine: EM_X86_6441ProgramHeaders:42 - Type: PT_NOTE43 FileSize: 0x1a44 FirstSec: .note.gnu.build-id45 LastSec: .note.gnu.build-id46Sections:47 - Name: .note.gnu.build-id48 Type: SHT_NOTE49 AddressAlign: 0x0450 Notes:51 - Name: "GNU"52 Desc: "abb50d82b6bdc861"53 Type: 354)");55 static std::string WithoutSection(WithSection + R"(56 - Type: SectionHeaderTable57 NoHeaders: true58)");59 if (WithShdr)60 return WithSection;61 return WithoutSection;62}63 64// The BuildID can be looked up from a section header, if there is no program65// header.66TEST(BuildIDTest, InvalidPhdrFileSizeWithShdrs) {67 SmallString<0> Storage;68 Expected<ELFObjectFile<ELF64LE>> ElfOrErr =69 toBinary<ELF64LE>(Storage, getInvalidNoteELF(true));70 ASSERT_THAT_EXPECTED(ElfOrErr, Succeeded());71 BuildIDRef BuildID = getBuildID(&ElfOrErr.get());72 EXPECT_EQ(73 StringRef(reinterpret_cast<const char *>(BuildID.data()), BuildID.size()),74 "\xAB\xB5\x0D\x82\xB6\xBD\xC8\x61");75}76 77// The code handles a malformed program header that points at data outside the78// file.79TEST(BuildIDTest, InvalidPhdrFileSizeNoShdrs) {80 SmallString<0> Storage;81 Expected<ELFObjectFile<ELF64LE>> ElfOrErr =82 toBinary<ELF64LE>(Storage, getInvalidNoteELF(false));83 ASSERT_THAT_EXPECTED(ElfOrErr, Succeeded());84 BuildIDRef BuildID = getBuildID(&ElfOrErr.get());85 EXPECT_EQ(86 StringRef(reinterpret_cast<const char *>(BuildID.data()), BuildID.size()),87 "");88}89 90// The code handles a malformed section header that points at data outside the91// file.92TEST(BuildIDTest, InvalidSectionHeader) {93 SmallString<0> Storage;94 Expected<ELFObjectFile<ELF64LE>> ElfOrErr = toBinary<ELF64LE>(Storage, R"(95--- !ELF96FileHeader:97 Class: ELFCLASS6498 Data: ELFDATA2LSB99 Type: ET_EXEC100 Machine: EM_X86_64101ProgramHeaders:102 - Type: PT_NOTE103 FirstSec: .note.gnu.build-id104 LastSec: .note.gnu.build-id105Sections:106 - Name: .note.gnu.build-id107 Type: SHT_NOTE108 AddressAlign: 0x04109 ShOffset: 0x1a1110 Notes:111 - Name: "GNU"112 Desc: "abb50d82b6bdc861"113 Type: 3114)");115 ASSERT_THAT_EXPECTED(ElfOrErr, Succeeded());116 BuildIDRef BuildID = getBuildID(&ElfOrErr.get());117 EXPECT_EQ(118 StringRef(reinterpret_cast<const char *>(BuildID.data()), BuildID.size()),119 "\xAB\xB5\x0D\x82\xB6\xBD\xC8\x61");120}121