summaryrefslogtreecommitdiffstats
path: root/lld/lib/ReaderWriter/MachO/MachOPasses.h
blob: d55fdf5fac8917f838eb93553baefcf3f774e017 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
//===- lib/ReaderWriter/MachO/MachOPasses.h -------------------------------===//
//
//                             The LLVM Linker
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//

#ifndef LLD_READER_WRITER_MACHO_PASSES_H
#define LLD_READER_WRITER_MACHO_PASSES_H

#include "lld/Core/Atom.h"
#include "lld/Core/File.h"
#include "lld/Core/Pass.h"
#include "lld/Core/range.h"
#include "lld/Core/Reference.h"

#include <vector>

namespace lld {
class DefinedAtom;
class MutableFile;


/// Pass for adding stubs (PLT entries) for calls to functions
/// outside the linkage unit.  This class is subclassed by each
/// file format Writer which implements the pure virtual methods.
class StubsPass : public Pass {
public:
  StubsPass() : Pass() {}

  /// Scans all Atoms looking for call-site uses of SharedLibraryAtoms
  /// and transfroms the call-site to call a stub instead using the
  /// helper methods below.
  void perform(std::unique_ptr<MutableFile> &mergedFile) override;

  /// If true, the pass should use stubs for references
  /// to shared library symbols. If false, the pass
  /// will generate relocations on the text segment which the
  /// runtime loader will use to patch the program at runtime.
  virtual bool noTextRelocs() = 0;

  /// Returns whether the Reference kind is for a call site.  The pass
  /// uses this to find calls that need to be indirected through a stub.
  virtual bool isCallSite(const Reference &) = 0;

  /// Returns a file format specific atom for a stub/PLT entry which contains
  /// instructions which jump to the specified atom.  May be called multiple
  /// times for the same target atom, in which case this method should return
  /// the same stub atom.
  virtual const DefinedAtom *getStub(const Atom &target) = 0;

  /// After the default implementation of perform() is done calling getStub(),
  /// it will call this method to add all the stub (and support) atoms to the
  /// master file object.
  virtual void addStubAtoms(MutableFile &masterFile) = 0;

private:
  void replaceCalleeWithStub(const Atom *target, const Reference *ref);
};

/// Pass for adding GOT entries for pointers to functions/data
/// outside the linkage unit. This class is subclassed by each
/// file format Writer which implements the pure virtual methods.
class GOTPass : public Pass {
public:
  GOTPass() : Pass() {}

  /// Scans all Atoms looking for pointer to SharedLibraryAtoms
  /// and transfroms them to a pointer to a GOT entry using the
  /// helper methods below.
  void perform(std::unique_ptr<MutableFile> &mergedFile) override;

  /// If true, the pass will use GOT entries for references
  /// to shared library symbols. If false, the pass
  /// will generate relocations on the text segment which the
  /// runtime loader will use to patch the program at runtime.
  virtual bool noTextRelocs() = 0;

  /// Returns whether the Reference kind is a pre-instantiated GOT access.
  /// The default implementation of perform() uses this to figure out
  /// what GOT entries to instantiate.
  virtual bool isGOTAccess(const Reference &, bool &canBypassGOT) = 0;

  /// The file format Writer needs to alter the reference kind from a
  /// pre-instantiated GOT access to an actual access.  If targetIsNowGOT is
  /// true, the pass has instantiated a GOT atom and altered the reference's
  /// target to point to that atom.  If targetIsNowGOT is false, the pass
  /// determined a GOT entry is not needed because the reference site can
  /// directly access the target.
  virtual void updateReferenceToGOT(const Reference*, bool targetIsNowGOT) = 0;

  /// Returns a file format specific atom for a GOT entry targeting
  /// the specified atom.
  virtual const DefinedAtom *makeGOTEntry(const Atom &target) = 0;
};

} // namespace lld

#endif // LLD_READER_WRITER_MACHO_PASSES_H
OpenPOWER on IntegriCloud