blob: b67ecfa455b3666533b87b8e254a1e5f725e68cb [file] [log] [blame]
Dan Gohman05ac43f2015-12-17 01:39:00 +00001//===-- WebAssemblyELFObjectWriter.cpp - WebAssembly ELF Writer -----------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9///
10/// \file
11/// \brief This file handles ELF-specific object emission, converting LLVM's
12/// internal fixups into the appropriate relocations.
13///
14//===----------------------------------------------------------------------===//
15
16#include "MCTargetDesc/WebAssemblyMCTargetDesc.h"
17#include "llvm/MC/MCELFObjectWriter.h"
18#include "llvm/MC/MCFixup.h"
Derek Schuff669300d2017-10-10 17:31:43 +000019#include "llvm/MC/MCObjectWriter.h"
Dan Gohman05ac43f2015-12-17 01:39:00 +000020#include "llvm/Support/ErrorHandling.h"
21using namespace llvm;
22
23namespace {
24class WebAssemblyELFObjectWriter final : public MCELFObjectTargetWriter {
25public:
26 WebAssemblyELFObjectWriter(bool Is64Bit, uint8_t OSABI);
27
Dan Gohman05ac43f2015-12-17 01:39:00 +000028protected:
JF Bastien664fd462016-01-13 23:36:00 +000029 unsigned getRelocType(MCContext &Ctx, const MCValue &Target,
30 const MCFixup &Fixup, bool IsPCRel) const override;
Dan Gohman05ac43f2015-12-17 01:39:00 +000031};
32} // end anonymous namespace
33
Dan Gohman05ac43f2015-12-17 01:39:00 +000034WebAssemblyELFObjectWriter::WebAssemblyELFObjectWriter(bool Is64Bit,
35 uint8_t OSABI)
Dan Gohman46350172016-01-12 20:56:01 +000036 : MCELFObjectTargetWriter(Is64Bit, OSABI, ELF::EM_WEBASSEMBLY,
37 /*HasRelocationAddend=*/false) {}
Dan Gohman05ac43f2015-12-17 01:39:00 +000038
JF Bastien664fd462016-01-13 23:36:00 +000039unsigned WebAssemblyELFObjectWriter::getRelocType(MCContext &Ctx,
40 const MCValue &Target,
Dan Gohman05ac43f2015-12-17 01:39:00 +000041 const MCFixup &Fixup,
42 bool IsPCRel) const {
Dan Gohman26c67652016-01-11 23:38:05 +000043 // WebAssembly functions are not allocated in the address space. To resolve a
44 // pointer to a function, we must use a special relocation type.
45 if (const MCSymbolRefExpr *SyExp =
46 dyn_cast<MCSymbolRefExpr>(Fixup.getValue()))
47 if (SyExp->getKind() == MCSymbolRefExpr::VK_WebAssembly_FUNCTION)
48 return ELF::R_WEBASSEMBLY_FUNCTION;
49
50 switch (Fixup.getKind()) {
51 case FK_Data_4:
52 assert(!is64Bit() && "4-byte relocations only supported on wasm32");
53 return ELF::R_WEBASSEMBLY_DATA;
54 case FK_Data_8:
55 assert(is64Bit() && "8-byte relocations only supported on wasm64");
56 return ELF::R_WEBASSEMBLY_DATA;
57 default:
58 llvm_unreachable("unimplemented fixup kind");
59 }
Dan Gohman05ac43f2015-12-17 01:39:00 +000060}
61
Derek Schuff669300d2017-10-10 17:31:43 +000062std::unique_ptr<MCObjectWriter>
63llvm::createWebAssemblyELFObjectWriter(raw_pwrite_stream &OS,
64 bool Is64Bit,
65 uint8_t OSABI) {
Reid Klecknera11b9832017-10-10 00:52:40 +000066 auto MOTW = llvm::make_unique<WebAssemblyELFObjectWriter>(Is64Bit, OSABI);
67 return createELFObjectWriter(std::move(MOTW), OS, /*IsLittleEndian=*/true);
Dan Gohman05ac43f2015-12-17 01:39:00 +000068}