Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(90)

Side by Side Diff: src/IceAssembler.h

Issue 1179563004: Renames the assembler* files. (Closed) Base URL: https://chromium.googlesource.com/native_client/pnacl-subzero.git@master
Patch Set: Changes the top comment for IceAssemblerX8632.cpp Created 5 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « Makefile.standalone ('k') | src/IceAssembler.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 //===- subzero/src/assembler.h - Integrated assembler -----------*- C++ -*-===// 1 //===- subzero/src/IceAssembler.h - Integrated assembler --------*- C++ -*-===//
2 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file 2 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file
3 // for details. All rights reserved. Use of this source code is governed by a 3 // for details. All rights reserved. Use of this source code is governed by a
4 // BSD-style license that can be found in the LICENSE file. 4 // BSD-style license that can be found in the LICENSE file.
5 // 5 //
6 // Modified by the Subzero authors. 6 // Modified by the Subzero authors.
7 // 7 //
8 //===----------------------------------------------------------------------===// 8 //===----------------------------------------------------------------------===//
9 // 9 //
10 // The Subzero Code Generator 10 // The Subzero Code Generator
11 // 11 //
12 // This file is distributed under the University of Illinois Open Source 12 // This file is distributed under the University of Illinois Open Source
13 // License. See LICENSE.TXT for details. 13 // License. See LICENSE.TXT for details.
14 // 14 //
15 //===----------------------------------------------------------------------===// 15 //===----------------------------------------------------------------------===//
16 // 16 //
17 // This file declares the Assembler base class. Instructions are assembled 17 // This file declares the Assembler base class. Instructions are assembled
18 // by architecture-specific assemblers that derive from this base class. 18 // by architecture-specific assemblers that derive from this base class.
19 // This base class manages buffers and fixups for emitting code, etc. 19 // This base class manages buffers and fixups for emitting code, etc.
20 // 20 //
21 //===----------------------------------------------------------------------===// 21 //===----------------------------------------------------------------------===//
22 22
23 #ifndef SUBZERO_SRC_ASSEMBLER_H 23 #ifndef SUBZERO_SRC_ICEASSEMBLER_H
24 #define SUBZERO_SRC_ASSEMBLER_H 24 #define SUBZERO_SRC_ICEASSEMBLER_H
25 25
26 #include "IceDefs.h" 26 #include "IceDefs.h"
27 #include "IceFixups.h" 27 #include "IceFixups.h"
28 28
29 namespace Ice { 29 namespace Ice {
30 30
31 // Assembler buffers are used to emit binary code. They grow on demand. 31 // Assembler buffers are used to emit binary code. They grow on demand.
32 class AssemblerBuffer { 32 class AssemblerBuffer {
33 AssemblerBuffer(const AssemblerBuffer &) = delete; 33 AssemblerBuffer(const AssemblerBuffer &) = delete;
34 AssemblerBuffer &operator=(const AssemblerBuffer &) = delete; 34 AssemblerBuffer &operator=(const AssemblerBuffer &) = delete;
35 35
36 public: 36 public:
37 AssemblerBuffer(Assembler &); 37 AssemblerBuffer(Assembler &);
38 ~AssemblerBuffer(); 38 ~AssemblerBuffer();
39 39
40 // Basic support for emitting, loading, and storing. 40 // Basic support for emitting, loading, and storing.
41 template <typename T> void Emit(T value) { 41 template <typename T> void emit(T Value) {
42 assert(HasEnsuredCapacity()); 42 assert(hasEnsuredCapacity());
43 *reinterpret_cast<T *>(cursor_) = value; 43 *reinterpret_cast<T *>(Cursor) = Value;
44 cursor_ += sizeof(T); 44 Cursor += sizeof(T);
45 } 45 }
46 46
47 template <typename T> T Load(intptr_t position) const { 47 template <typename T> T load(intptr_t Position) const {
48 assert(position >= 0 && 48 assert(Position >= 0 &&
49 position <= (Size() - static_cast<intptr_t>(sizeof(T)))); 49 Position <= (size() - static_cast<intptr_t>(sizeof(T))));
50 return *reinterpret_cast<T *>(contents_ + position); 50 return *reinterpret_cast<T *>(Contents + Position);
51 } 51 }
52 52
53 template <typename T> void Store(intptr_t position, T value) { 53 template <typename T> void store(intptr_t Position, T Value) {
54 assert(position >= 0 && 54 assert(Position >= 0 &&
55 position <= (Size() - static_cast<intptr_t>(sizeof(T)))); 55 Position <= (size() - static_cast<intptr_t>(sizeof(T))));
56 *reinterpret_cast<T *>(contents_ + position) = value; 56 *reinterpret_cast<T *>(Contents + Position) = Value;
57 } 57 }
58 58
59 // Emit a fixup at the current location. 59 // Emit a fixup at the current location.
60 void EmitFixup(AssemblerFixup *fixup) { fixup->set_position(Size()); } 60 void emitFixup(AssemblerFixup *Fixup) { Fixup->set_position(size()); }
61 61
62 // Get the size of the emitted code. 62 // Get the size of the emitted code.
63 intptr_t Size() const { return cursor_ - contents_; } 63 intptr_t size() const { return Cursor - Contents; }
64 uintptr_t contents() const { return contents_; } 64 uintptr_t contents() const { return Contents; }
65 65
66 // To emit an instruction to the assembler buffer, the EnsureCapacity helper 66 // To emit an instruction to the assembler buffer, the EnsureCapacity helper
67 // must be used to guarantee that the underlying data area is big enough to 67 // must be used to guarantee that the underlying data area is big enough to
68 // hold the emitted instruction. Usage: 68 // hold the emitted instruction. Usage:
69 // 69 //
70 // AssemblerBuffer buffer; 70 // AssemblerBuffer buffer;
71 // AssemblerBuffer::EnsureCapacity ensured(&buffer); 71 // AssemblerBuffer::EnsureCapacity ensured(&buffer);
72 // ... emit bytes for single instruction ... 72 // ... emit bytes for single instruction ...
73 73
74 #ifndef NDEBUG 74 #ifndef NDEBUG
75 class EnsureCapacity { 75 class EnsureCapacity {
76 EnsureCapacity(const EnsureCapacity &) = delete; 76 EnsureCapacity(const EnsureCapacity &) = delete;
77 EnsureCapacity &operator=(const EnsureCapacity &) = delete; 77 EnsureCapacity &operator=(const EnsureCapacity &) = delete;
78 78
79 public: 79 public:
80 explicit EnsureCapacity(AssemblerBuffer *buffer); 80 explicit EnsureCapacity(AssemblerBuffer *Buffer);
81 ~EnsureCapacity(); 81 ~EnsureCapacity();
82 82
83 private: 83 private:
84 AssemblerBuffer *buffer_; 84 AssemblerBuffer *Buffer;
85 intptr_t gap_; 85 intptr_t Gap;
86 86
87 intptr_t ComputeGap() { return buffer_->Capacity() - buffer_->Size(); } 87 intptr_t computeGap() { return Buffer->capacity() - Buffer->size(); }
88 }; 88 };
89 89
90 bool has_ensured_capacity_; 90 bool HasEnsuredCapacity;
91 bool HasEnsuredCapacity() const { return has_ensured_capacity_; } 91 bool hasEnsuredCapacity() const { return HasEnsuredCapacity; }
92 #else // NDEBUG 92 #else // NDEBUG
93 class EnsureCapacity { 93 class EnsureCapacity {
94 EnsureCapacity(const EnsureCapacity &) = delete; 94 EnsureCapacity(const EnsureCapacity &) = delete;
95 EnsureCapacity &operator=(const EnsureCapacity &) = delete; 95 EnsureCapacity &operator=(const EnsureCapacity &) = delete;
96 96
97 public: 97 public:
98 explicit EnsureCapacity(AssemblerBuffer *buffer) { 98 explicit EnsureCapacity(AssemblerBuffer *Buffer) {
99 if (buffer->cursor() >= buffer->limit()) 99 if (Buffer->cursor() >= buffer->limit())
100 buffer->ExtendCapacity(); 100 buffer->extendCapacity();
101 } 101 }
102 }; 102 };
103 103
104 // When building the C++ tests, assertion code is enabled. To allow 104 // When building the C++ tests, assertion code is enabled. To allow
105 // asserting that the user of the assembler buffer has ensured the 105 // asserting that the user of the assembler buffer has ensured the
106 // capacity needed for emitting, we add a dummy method in non-debug mode. 106 // capacity needed for emitting, we add a dummy method in non-debug mode.
107 bool HasEnsuredCapacity() const { return true; } 107 bool hasEnsuredCapacity() const { return true; }
108 #endif // NDEBUG 108 #endif // NDEBUG
109 109
110 // Returns the position in the instruction stream. 110 // Returns the position in the instruction stream.
111 intptr_t GetPosition() const { return cursor_ - contents_; } 111 intptr_t getPosition() const { return Cursor - Contents; }
112 112
113 // Create and track a fixup in the current function. 113 // Create and track a fixup in the current function.
114 AssemblerFixup *createFixup(FixupKind Kind, const Constant *Value); 114 AssemblerFixup *createFixup(FixupKind Kind, const Constant *Value);
115 115
116 const FixupRefList &fixups() const { return fixups_; } 116 const FixupRefList &fixups() const { return Fixups; }
117 117
118 void setSize(intptr_t NewSize) { 118 void setSize(intptr_t NewSize) {
119 assert(NewSize <= Size()); 119 assert(NewSize <= size());
120 cursor_ = contents_ + NewSize; 120 Cursor = Contents + NewSize;
121 } 121 }
122 122
123 private: 123 private:
124 // The limit is set to kMinimumGap bytes before the end of the data area. 124 // The limit is set to kMinimumGap bytes before the end of the data area.
125 // This leaves enough space for the longest possible instruction and allows 125 // This leaves enough space for the longest possible instruction and allows
126 // for a single, fast space check per instruction. 126 // for a single, fast space check per instruction.
127 static const intptr_t kMinimumGap = 32; 127 static const intptr_t kMinimumGap = 32;
128 128
129 uintptr_t contents_; 129 uintptr_t Contents;
130 uintptr_t cursor_; 130 uintptr_t Cursor;
131 uintptr_t limit_; 131 uintptr_t Limit;
132 Assembler &assembler_; 132 // The member variable is named Assemblr to avoid hiding the class Assembler.
133 Assembler &Assemblr;
133 // List of pool-allocated fixups relative to the current function. 134 // List of pool-allocated fixups relative to the current function.
134 FixupRefList fixups_; 135 FixupRefList Fixups;
135 136
136 uintptr_t cursor() const { return cursor_; } 137 uintptr_t cursor() const { return Cursor; }
137 uintptr_t limit() const { return limit_; } 138 uintptr_t limit() const { return Limit; }
138 intptr_t Capacity() const { 139 intptr_t capacity() const {
139 assert(limit_ >= contents_); 140 assert(Limit >= Contents);
140 return (limit_ - contents_) + kMinimumGap; 141 return (Limit - Contents) + kMinimumGap;
141 } 142 }
142 143
143 // Compute the limit based on the data area and the capacity. See 144 // Compute the limit based on the data area and the capacity. See
144 // description of kMinimumGap for the reasoning behind the value. 145 // description of kMinimumGap for the reasoning behind the value.
145 static uintptr_t ComputeLimit(uintptr_t data, intptr_t capacity) { 146 static uintptr_t computeLimit(uintptr_t Data, intptr_t Capacity) {
146 return data + capacity - kMinimumGap; 147 return Data + Capacity - kMinimumGap;
147 } 148 }
148 149
149 void ExtendCapacity(); 150 void extendCapacity();
150 }; 151 };
151 152
152 class Assembler { 153 class Assembler {
153 Assembler(const Assembler &) = delete; 154 Assembler(const Assembler &) = delete;
154 Assembler &operator=(const Assembler &) = delete; 155 Assembler &operator=(const Assembler &) = delete;
155 156
156 public: 157 public:
157 Assembler() 158 Assembler()
158 : FunctionName(""), IsInternal(false), Preliminary(false), 159 : Buffer(*this), FunctionName(""), IsInternal(false),
159 buffer_(*this) {} 160 Preliminary(false) {}
160 virtual ~Assembler() {} 161 virtual ~Assembler() = default;
161 162
162 // Allocate a chunk of bytes using the per-Assembler allocator. 163 // Allocate a chunk of bytes using the per-Assembler allocator.
163 uintptr_t AllocateBytes(size_t bytes) { 164 uintptr_t allocateBytes(size_t bytes) {
164 // For now, alignment is not related to NaCl bundle alignment, since 165 // For now, alignment is not related to NaCl bundle alignment, since
165 // the buffer's GetPosition is relative to the base. So NaCl bundle 166 // the buffer's GetPosition is relative to the base. So NaCl bundle
166 // alignment checks can be relative to that base. Later, the buffer 167 // alignment checks can be relative to that base. Later, the buffer
167 // will be copied out to a ".text" section (or an in memory-buffer 168 // will be copied out to a ".text" section (or an in memory-buffer
168 // that can be mprotect'ed with executable permission), and that 169 // that can be mprotect'ed with executable permission), and that
169 // second buffer should be aligned for NaCl. 170 // second buffer should be aligned for NaCl.
170 const size_t Alignment = 16; 171 const size_t Alignment = 16;
171 return reinterpret_cast<uintptr_t>(Allocator.Allocate(bytes, Alignment)); 172 return reinterpret_cast<uintptr_t>(Allocator.Allocate(bytes, Alignment));
172 } 173 }
173 174
174 // Allocate data of type T using the per-Assembler allocator. 175 // Allocate data of type T using the per-Assembler allocator.
175 template <typename T> T *Allocate() { return Allocator.Allocate<T>(); } 176 template <typename T> T *allocate() { return Allocator.Allocate<T>(); }
176 177
177 // Align the tail end of the function to the required target alignment. 178 // Align the tail end of the function to the required target alignment.
178 virtual void alignFunction() = 0; 179 virtual void alignFunction() = 0;
179 180
180 // Add nop padding of a particular width to the current bundle. 181 // Add nop padding of a particular width to the current bundle.
181 virtual void padWithNop(intptr_t Padding) = 0; 182 virtual void padWithNop(intptr_t Padding) = 0;
182 183
183 virtual SizeT getBundleAlignLog2Bytes() const = 0; 184 virtual SizeT getBundleAlignLog2Bytes() const = 0;
184 185
185 virtual const char *getNonExecPadDirective() const = 0; 186 virtual const char *getNonExecPadDirective() const = 0;
186 virtual llvm::ArrayRef<uint8_t> getNonExecBundlePadding() const = 0; 187 virtual llvm::ArrayRef<uint8_t> getNonExecBundlePadding() const = 0;
187 188
188 // Mark the current text location as the start of a CFG node 189 // Mark the current text location as the start of a CFG node
189 // (represented by NodeNumber). 190 // (represented by NodeNumber).
190 virtual void BindCfgNodeLabel(SizeT NodeNumber) = 0; 191 virtual void bindCfgNodeLabel(SizeT NodeNumber) = 0;
191 192
192 virtual bool fixupIsPCRel(FixupKind Kind) const = 0; 193 virtual bool fixupIsPCRel(FixupKind Kind) const = 0;
193 194
194 // Return a view of all the bytes of code for the current function. 195 // Return a view of all the bytes of code for the current function.
195 llvm::StringRef getBufferView() const; 196 llvm::StringRef getBufferView() const;
196 197
197 const FixupRefList &fixups() const { return buffer_.fixups(); } 198 const FixupRefList &fixups() const { return Buffer.fixups(); }
198 199
199 AssemblerFixup *createFixup(FixupKind Kind, const Constant *Value) { 200 AssemblerFixup *createFixup(FixupKind Kind, const Constant *Value) {
200 return buffer_.createFixup(Kind, Value); 201 return Buffer.createFixup(Kind, Value);
201 } 202 }
202 203
203 void emitIASBytes(GlobalContext *Ctx) const; 204 void emitIASBytes(GlobalContext *Ctx) const;
204 bool getInternal() const { return IsInternal; } 205 bool getInternal() const { return IsInternal; }
205 void setInternal(bool Internal) { IsInternal = Internal; } 206 void setInternal(bool Internal) { IsInternal = Internal; }
206 const IceString &getFunctionName() { return FunctionName; } 207 const IceString &getFunctionName() { return FunctionName; }
207 void setFunctionName(const IceString &NewName) { FunctionName = NewName; } 208 void setFunctionName(const IceString &NewName) { FunctionName = NewName; }
208 intptr_t getBufferSize() const { return buffer_.Size(); } 209 intptr_t getBufferSize() const { return Buffer.size(); }
209 // Roll back to a (smaller) size. 210 // Roll back to a (smaller) size.
210 void setBufferSize(intptr_t NewSize) { buffer_.setSize(NewSize); } 211 void setBufferSize(intptr_t NewSize) { Buffer.setSize(NewSize); }
211 void setPreliminary(bool Value) { Preliminary = Value; } 212 void setPreliminary(bool Value) { Preliminary = Value; }
212 bool getPreliminary() const { return Preliminary; } 213 bool getPreliminary() const { return Preliminary; }
213 214
215 protected:
216 AssemblerBuffer Buffer;
217
214 private: 218 private:
215 ArenaAllocator<32 * 1024> Allocator; 219 ArenaAllocator<32 * 1024> Allocator;
216 // FunctionName and IsInternal are transferred from the original Cfg 220 // FunctionName and IsInternal are transferred from the original Cfg
217 // object, since the Cfg object may be deleted by the time the 221 // object, since the Cfg object may be deleted by the time the
218 // assembler buffer is emitted. 222 // assembler buffer is emitted.
219 IceString FunctionName; 223 IceString FunctionName;
220 bool IsInternal; 224 bool IsInternal;
221 // Preliminary indicates whether a preliminary pass is being made 225 // Preliminary indicates whether a preliminary pass is being made
222 // for calculating bundle padding (Preliminary=true), versus the 226 // for calculating bundle padding (Preliminary=true), versus the
223 // final pass where all changes to label bindings, label links, and 227 // final pass where all changes to label bindings, label links, and
224 // relocation fixups are fully committed (Preliminary=false). 228 // relocation fixups are fully committed (Preliminary=false).
225 bool Preliminary; 229 bool Preliminary;
226
227 protected:
228 AssemblerBuffer buffer_;
229 }; 230 };
230 231
231 } // end of namespace Ice 232 } // end of namespace Ice
232 233
233 #endif // SUBZERO_SRC_ASSEMBLER_H_ 234 #endif // SUBZERO_SRC_ICEASSEMBLER_H_
OLDNEW
« no previous file with comments | « Makefile.standalone ('k') | src/IceAssembler.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698