Run DCE after a LoopFlatten test to reduce spurious output [nfc]
[llvm-project.git] / openmp / libomptarget / plugins-nextgen / common / elf_common / elf_common.cpp
blob43ad4477c0cabf5443ea08764641f756fd636d83
1 //===-- elf_common.cpp - Common ELF functionality -------------------------===//
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-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 // Common ELF functionality for target plugins.
11 //===----------------------------------------------------------------------===//
12 #include "elf_common.h"
13 #include "Debug.h"
15 #include "llvm/BinaryFormat/Magic.h"
16 #include "llvm/Object/Binary.h"
17 #include "llvm/Object/ELFObjectFile.h"
18 #include "llvm/Object/ELFTypes.h"
19 #include "llvm/Object/ObjectFile.h"
20 #include "llvm/Support/MemoryBuffer.h"
22 #ifndef TARGET_NAME
23 #define TARGET_NAME ELF Common
24 #endif
25 #define DEBUG_PREFIX "TARGET " GETNAME(TARGET_NAME)
27 using namespace llvm;
28 using namespace llvm::ELF;
29 using namespace llvm::object;
31 /// If the given range of bytes [\p BytesBegin, \p BytesEnd) represents
32 /// a valid ELF, then invoke \p Callback on the ELFObjectFileBase
33 /// created from this range, otherwise, return 0.
34 /// If \p Callback is invoked, then return whatever value \p Callback returns.
35 template <typename F>
36 static int32_t withBytesAsElf(char *BytesBegin, char *BytesEnd, F Callback) {
37 size_t Size = BytesEnd - BytesBegin;
38 StringRef StrBuf(BytesBegin, Size);
40 auto Magic = identify_magic(StrBuf);
41 if (Magic != file_magic::elf && Magic != file_magic::elf_relocatable &&
42 Magic != file_magic::elf_executable &&
43 Magic != file_magic::elf_shared_object && Magic != file_magic::elf_core) {
44 DP("Not an ELF image!\n");
45 return 0;
48 std::unique_ptr<MemoryBuffer> MemBuf =
49 MemoryBuffer::getMemBuffer(StrBuf, "", false);
50 Expected<std::unique_ptr<ObjectFile>> BinOrErr =
51 ObjectFile::createELFObjectFile(MemBuf->getMemBufferRef(),
52 /*InitContent=*/false);
53 if (!BinOrErr) {
54 DP("Unable to get ELF handle: %s!\n",
55 toString(BinOrErr.takeError()).c_str());
56 return 0;
59 auto *Object = dyn_cast<const ELFObjectFileBase>(BinOrErr->get());
61 if (!Object) {
62 DP("Unknown ELF format!\n");
63 return 0;
66 return Callback(Object);
69 // Check whether an image is valid for execution on target_id
70 int32_t elf_check_machine(__tgt_device_image *Image, uint16_t TargetId) {
71 auto CheckMachine = [TargetId](const ELFObjectFileBase *Object) {
72 return TargetId == Object->getEMachine();
74 return withBytesAsElf(reinterpret_cast<char *>(Image->ImageStart),
75 reinterpret_cast<char *>(Image->ImageEnd),
76 CheckMachine);
79 int32_t elf_is_dynamic(__tgt_device_image *Image) {
80 auto CheckDynType = [](const ELFObjectFileBase *Object) {
81 uint16_t Type = Object->getEType();
82 DP("ELF Type: %d\n", Type);
83 return Type == ET_DYN;
85 return withBytesAsElf(reinterpret_cast<char *>(Image->ImageStart),
86 reinterpret_cast<char *>(Image->ImageEnd),
87 CheckDynType);