Clean up irgen.h a bit
[hiphop-php.git] / hphp / runtime / vm / jit / vasm-gen.h
blob3d825d0e4134168e695691f691fc0081092f5be1
1 /*
2 +----------------------------------------------------------------------+
3 | HipHop for PHP |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 2010-2016 Facebook, Inc. (http://www.facebook.com) |
6 +----------------------------------------------------------------------+
7 | This source file is subject to version 3.01 of the PHP license, |
8 | that is bundled with this package in the file LICENSE, and is |
9 | available through the world-wide-web at the following url: |
10 | http://www.php.net/license/3_01.txt |
11 | If you did not receive a copy of the PHP license and are unable to |
12 | obtain it through the world-wide-web, please send a note to |
13 | license@php.net so we can mail you a copy immediately. |
14 +----------------------------------------------------------------------+
17 #ifndef incl_HPHP_JIT_VASM_GEN_H_
18 #define incl_HPHP_JIT_VASM_GEN_H_
20 #include "hphp/runtime/vm/jit/cg-meta.h"
21 #include "hphp/runtime/vm/jit/containers.h"
22 #include "hphp/runtime/vm/jit/types.h"
23 #include "hphp/runtime/vm/jit/vasm-text.h"
24 #include "hphp/runtime/vm/jit/vasm-unit.h"
25 #include "hphp/runtime/vm/jit/vasm.h"
27 #include "hphp/util/data-block.h"
29 #include <boost/type_traits.hpp>
31 namespace HPHP { namespace jit {
32 ///////////////////////////////////////////////////////////////////////////////
34 struct IRInstruction;
35 struct Vinstr;
36 struct Vreg;
38 ///////////////////////////////////////////////////////////////////////////////
41 * Writer stream for adding instructions to a Vblock.
43 struct Vout {
44 Vout(Vunit& u, Vlabel b, const IRInstruction* origin = nullptr)
45 : m_unit(u)
46 , m_block(b)
47 , m_origin(origin)
50 Vout(Vout&&) = default;
51 Vout(const Vout&) = delete;
53 Vout& operator=(const Vout&);
54 Vout& operator=(Vlabel);
57 * Implicit cast to label for initializing branch instructions.
59 /* implicit */ operator Vlabel() const;
62 * Instruction emitter.
64 Vout& operator<<(const Vinstr& inst);
67 * Create a stream connected to a new empty block.
69 Vout makeBlock();
71 /////////////////////////////////////////////////////////////////////////////
74 * Whether the stream is empty or terminated (because a block-terminating
75 * instruction has been emitted).
77 bool empty() const;
78 bool closed() const;
81 * Return the managed Vunit.
83 Vunit& unit() { return m_unit; }
86 * Return the code area of the currently-managed block.
88 AreaIndex area() const;
91 * Set the current block and Vinstr origin.
93 void use(Vlabel b) { m_block = b; }
94 void setOrigin(const IRInstruction* i) { m_origin = i; }
97 * Vunit delegations.
99 Vreg makeReg();
100 Vtuple makeTuple(const VregList& regs) const;
101 Vtuple makeTuple(VregList&& regs) const;
102 VcallArgsId makeVcallArgs(VcallArgs&& args) const;
103 template<class T> Vreg cns(T v);
105 private:
106 Vunit& m_unit;
107 Vlabel m_block;
108 const IRInstruction* m_origin;
111 ///////////////////////////////////////////////////////////////////////////////
114 * Vasm assembler.
116 * A Vasm manages Vout streams for a Vunit.
118 struct Vasm {
119 Vasm() { m_outs.reserve(kNumAreas); }
122 * Obtain the managed Vunit.
124 Vunit& unit() { return m_unit; }
127 * Get or create the stream for the corresponding Varea.
129 Vout& main() { return out(AreaIndex::Main); }
130 Vout& cold() { return out(AreaIndex::Cold); }
131 Vout& frozen() { return out(AreaIndex::Frozen); }
133 private:
134 Vout& out(AreaIndex i);
136 private:
137 Vunit m_unit;
138 jit::vector<Vout> m_outs; // one for each AreaIndex
141 ///////////////////////////////////////////////////////////////////////////////
144 * Helper for emitting small amounts of machine code using vasm.
146 * Vauto manages a Vunit with a single area. When the Vauto goes out of scope,
147 * it will finalize and emit any code it contains.
149 struct Vauto {
150 explicit Vauto(CodeBlock& code, CGMeta& fixups,
151 CodeKind kind = CodeKind::Helper)
152 : m_text{code, code}
153 , m_fixups(fixups)
154 , m_main{m_unit, m_unit.makeBlock(AreaIndex::Main)}
155 , m_cold{m_unit, m_unit.makeBlock(AreaIndex::Cold)}
156 , m_kind{kind}
158 m_unit.entry = Vlabel(main());
161 Vunit& unit() { return m_unit; }
162 Vout& main() { return m_main; }
163 Vout& cold() { return m_cold; }
165 ~Vauto();
167 private:
168 Vunit m_unit;
169 Vtext m_text;
170 CGMeta& m_fixups;
171 Vout m_main;
172 Vout m_cold;
173 CodeKind m_kind;
176 namespace detail {
177 template<class GenFunc>
178 TCA vwrap_impl(CodeBlock& cb, CGMeta* meta, GenFunc gen, CodeKind kind);
182 * Convenience wrappers around Vauto for cross-trace or helper code.
184 template<class GenFunc>
185 TCA vwrap(CodeBlock& cb, CGMeta& meta, GenFunc gen,
186 CodeKind kind = CodeKind::CrossTrace) {
187 return detail::vwrap_impl(cb, &meta, [&] (Vout& v, Vout&) { gen(v); }, kind);
189 template<class GenFunc>
190 TCA vwrap(CodeBlock& cb, GenFunc gen) {
191 return detail::vwrap_impl(cb, nullptr, [&] (Vout& v, Vout&) { gen(v); },
192 CodeKind::CrossTrace);
194 template<class GenFunc>
195 TCA vwrap2(CodeBlock& cb, GenFunc gen) {
196 return detail::vwrap_impl(cb, nullptr, gen, CodeKind::CrossTrace);
199 ///////////////////////////////////////////////////////////////////////////////
202 #include "hphp/runtime/vm/jit/vasm-gen-inl.h"
204 #endif