emit file/line with ud2
[hiphop-php.git] / hphp / runtime / vm / jit / types.h
blobb5d72acdc75914917e62e1764d23a9d95ede5fe6
1 /*
2 +----------------------------------------------------------------------+
3 | HipHop for PHP |
4 +----------------------------------------------------------------------+
5 | Copyright (c) 2010-present 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_TRANSL_TYPES_H_
18 #define incl_HPHP_TRANSL_TYPES_H_
20 #include <vector>
22 #include "hphp/runtime/base/runtime-option.h"
23 #include "hphp/runtime/base/types.h"
25 #include "hphp/util/assertions.h"
26 #include "hphp/util/hash-map-typedefs.h"
28 namespace HPHP { namespace jit {
30 ///////////////////////////////////////////////////////////////////////////////
33 * Core types.
35 typedef unsigned char* TCA; // "Translation cache address."
36 typedef const unsigned char* CTCA;
38 using LowTCA = LowPtr<uint8_t>;
39 using AtomicLowTCA = AtomicLowPtr<uint8_t,
40 std::memory_order_acquire,
41 std::memory_order_release>;
43 struct ctca_identity_hash {
44 size_t operator()(CTCA val) const {
45 // Experiments show that this is a sufficient "hash function" on
46 // TCAs for now; using stronger functions didn't help given current
47 // data. Patterns of code emission in the translator could invalidate
48 // this finding going forward, though; e.g., if we frequently emit
49 // a call instruction N bytes into a cache-aligned region.
50 return uintptr_t(val);
54 ///////////////////////////////////////////////////////////////////////////////
56 using TransIDSet = hphp_hash_set<TransID>;
57 using TransIDVec = std::vector<TransID>;
59 using Annotation = std::pair<std::string, std::string>;
60 using Annotations = std::vector<Annotation>;
62 ///////////////////////////////////////////////////////////////////////////////
64 /**
65 * The different kinds of translations that the JIT generates:
67 * - Anchor : a service request for retranslating
68 * - Interp : a service request to interpret at least one instruction
69 * - Live : translate one tracelet by inspecting live VM state
70 * - Profile : translate one block by inspecting live VM state and
71 * inserting profiling counters
72 * - Optimize : translate one region performing optimizations that may
73 * leverage data collected by Profile translations
74 * - LivePrologue : prologue for a function being JITed in Live mode
75 * - ProfPrologue : prologue for a function being JITed in Profile mode
76 * - OptPrologue : prologue for a function being JITed in Optimize mode
78 #define TRANS_KINDS \
79 DO(Anchor) \
80 DO(Interp) \
81 DO(Live) \
82 DO(Profile) \
83 DO(Optimize) \
84 DO(LivePrologue)\
85 DO(ProfPrologue)\
86 DO(OptPrologue) \
87 DO(Invalid) \
89 enum class TransKind {
90 #define DO(KIND) KIND,
91 TRANS_KINDS
92 #undef DO
95 constexpr size_t NumTransKinds =
96 #define DO(KIND) + 1
97 TRANS_KINDS
98 #undef DO
101 inline std::string show(TransKind k) {
102 #define DO(name) case TransKind::name: return "Trans" #name;
103 switch (k) { TRANS_KINDS }
104 #undef DO
105 not_reached();
108 inline bool isProfiling(TransKind k) {
109 switch (k) {
110 case TransKind::Profile:
111 case TransKind::ProfPrologue:
112 return true;
114 case TransKind::Anchor:
115 case TransKind::Interp:
116 case TransKind::Live:
117 case TransKind::LivePrologue:
118 case TransKind::Optimize:
119 case TransKind::OptPrologue:
120 case TransKind::Invalid:
121 return false;
123 always_assert(false);
126 inline bool isPrologue(TransKind k) {
127 switch (k) {
128 case TransKind::LivePrologue:
129 case TransKind::ProfPrologue:
130 case TransKind::OptPrologue:
131 return true;
133 case TransKind::Anchor:
134 case TransKind::Interp:
135 case TransKind::Live:
136 case TransKind::Profile:
137 case TransKind::Optimize:
138 case TransKind::Invalid:
139 return false;
141 always_assert(false);
145 * Compact flags which may be threaded through a service request to provide
146 * hints or demands for retranslations.
148 struct TransFlags {
149 /* implicit */ TransFlags(uint64_t flags = 0) : packed(flags) {}
151 union {
152 struct {
153 bool noinlineSingleton : 1;
154 bool noProfiledFPush : 1;
156 uint64_t packed;
160 static_assert(sizeof(TransFlags) <= sizeof(uint64_t), "Too many TransFlags!");
162 ///////////////////////////////////////////////////////////////////////////////
165 * The "kind" of code being generated.
167 * Different contexts of code generation constrain codegen differently; e.g.,
168 * cross-trace code has fewer available registers.
170 enum class CodeKind : uint8_t {
172 * Normal PHP code in the TC.
174 Trace,
177 * Code at the TC boundaries, e.g., service requests, unique stubs.
179 CrossTrace,
182 * Helper code that uses native scratch registers only.
184 * This roughly means unreserved, caller-saved, non-argument registers---but
185 * best to just look at the helper ABI in the appropriate abi-*.cpp file.
187 Helper,
191 * Enumeration representing the various areas that we emit code.
193 * kNumAreas must be kept up to date.
195 enum class AreaIndex : uint8_t { Main, Cold, Frozen };
196 constexpr size_t kNumAreas = 3;
198 inline std::string areaAsString(AreaIndex area) {
199 switch (area) {
200 case AreaIndex::Main:
201 return "Main";
202 case AreaIndex::Cold:
203 return "Cold";
204 case AreaIndex::Frozen:
205 return "Frozen";
207 always_assert(false);
211 * Multiplying factors used to compute the block weights for each code area.
212 * We multiply the corresponding IR block's profile counter by the following
213 * factors, depending on the code area the block is assigned to.
215 inline uint64_t areaWeightFactor(AreaIndex area) {
216 switch (area) {
217 case AreaIndex::Main: return RuntimeOption::EvalJitLayoutMainFactor;
218 case AreaIndex::Cold: return RuntimeOption::EvalJitLayoutColdFactor;
219 case AreaIndex::Frozen: return 1;
221 always_assert(false);
224 ///////////////////////////////////////////////////////////////////////////////
227 * Some data structures are accessed often enough from translated code that we
228 * have shortcuts for getting offsets into them.
230 #define TVOFF(nm) int(offsetof(TypedValue, nm))
231 #define AROFF(nm) int(offsetof(ActRec, nm))
232 #define AFWHOFF(nm) int(offsetof(c_AsyncFunctionWaitHandle, nm))
233 #define GENDATAOFF(nm) int(offsetof(Generator, nm))
235 ///////////////////////////////////////////////////////////////////////////////
238 * Generalization of Status Flag bits encoded in Vinstr and used by the
239 * annotateSFUses() pass and platform-specific lowerers/emitters.
241 * In order for a platform to utilize the pass, they'll need to implement
242 * mappings between ConditionCodes and an operator|-able bit sequence held in a
243 * Vflags byte. This implies that the platform will need to define their
244 * status flag bits as well. See required_flags() in abi-arm.h for an example.
246 using Vflags = uint8_t;
248 ///////////////////////////////////////////////////////////////////////////////
251 * Information attached to an assertion in emitted code.
253 struct Reason {
254 const char* file;
255 unsigned line;
258 inline std::string show(const Reason &r) {
259 return folly::sformat("{}:{}", r.file, r.line);
264 #endif