Index: llvm/include/llvm/Object/ELFObjectFile.h =================================================================== --- llvm/include/llvm/Object/ELFObjectFile.h +++ llvm/include/llvm/Object/ELFObjectFile.h @@ -96,6 +96,8 @@ std::vector, uint64_t>> getPltAddresses() const; + + virtual bool checkMagic() const = 0; }; class ELFSectionRef : public SectionRef { @@ -229,6 +231,7 @@ uint16_t getEMachine() const override; uint16_t getEType() const override; uint64_t getSymbolSize(DataRefImpl Sym) const override; + bool checkMagic() const override; public: LLVM_ELF_IMPORT_TYPES_ELFT(ELFT) @@ -623,6 +626,10 @@ return (*SymOrErr)->st_size; } +template bool ELFObjectFile::checkMagic() const { + return EF.getHeader().checkMagic(); +} + template uint64_t ELFObjectFile::getCommonSymbolSizeImpl(DataRefImpl Symb) const { return getSymbolSize(Symb); Index: llvm/unittests/Object/ELFObjectFileTest.cpp =================================================================== --- llvm/unittests/Object/ELFObjectFileTest.cpp +++ llvm/unittests/Object/ELFObjectFileTest.cpp @@ -23,8 +23,8 @@ std::vector Data; template - std::vector makeElfData(uint8_t Class, uint8_t Encoding, - uint16_t Machine) { + static std::vector makeElfData(uint8_t Class, uint8_t Encoding, + uint16_t Machine) { T Ehdr{}; // Zero-initialise the header. Ehdr.e_ident[ELF::EI_MAG0] = 0x7f; Ehdr.e_ident[ELF::EI_MAG1] = 'E'; @@ -590,3 +590,25 @@ DoCheck(OverLimitNumBlocks, "ULEB128 value at offset 0x8 exceeds UINT32_MAX (0x100000000)"); } + +TEST(ELFObjectFileTest, InvalidMagicTest) { + std::vector Data = DataForTest::makeElfData( + ELF::ELFCLASS32, ELF::ELFDATA2LSB, ELF::EM_NONE); + // Replace the ELF with an ORC. + Data[ELF::EI_MAG1] = 'O'; + Data[ELF::EI_MAG2] = 'R'; + Data[ELF::EI_MAG3] = 'C'; + + // In the current implementation the data is still recognized + // as an ELF even though it is an ORC. + Expected> ELFObjOrErr = + object::ObjectFile::createELFObjectFile( + MemoryBufferRef(toStringRef(Data), "dummyELF")); + ASSERT_THAT_EXPECTED(ELFObjOrErr, Succeeded()); + + auto *Object = dyn_cast(ELFObjOrErr->get()); + // It should be a valid ELFObjectFileBase object. + EXPECT_TRUE(Object != nullptr); + // checkMagic() recognizes a real ELF. + EXPECT_TRUE(!Object->checkMagic()); +}