Coverage Report

Created: 2017-04-15 07:07

/home/travis/build/MoarVM/MoarVM/src/core/frame.h
Line
Count
Source (jump to first uncovered line)
1
/* Frame flags; provide some HLLs can alias. */
2
#define MVM_FRAME_FLAG_STATE_INIT       1 << 0
3
0
#define MVM_FRAME_FLAG_EXIT_HAND_RUN    1 << 1
4
#define MVM_FRAME_FLAG_HLL_1            1 << 3
5
#define MVM_FRAME_FLAG_HLL_2            1 << 4
6
#define MVM_FRAME_FLAG_HLL_3            1 << 5
7
#define MVM_FRAME_FLAG_HLL_4            1 << 6
8
9
/* Lexical hash entry for ->lexical_names on a frame. */
10
struct MVMLexicalRegistry {
11
    /* key string */
12
    MVMString *key;
13
14
    /* index of the lexical entry. */
15
    MVMuint32 value;
16
17
    /* the uthash hash handle inline struct. */
18
    UT_hash_handle hash_handle;
19
};
20
21
/* Entry in the linked list of continuation tags for the frame. */
22
struct MVMContinuationTag {
23
    /* The tag itself. */
24
    MVMObject *tag;
25
26
    /* The active exception handler at the point the tag was taken. */
27
    MVMActiveHandler *active_handlers;
28
29
    /* The next continuation tag entry. */
30
    MVMContinuationTag *next;
31
};
32
33
/* Function pointer type of special return handler. These are used to allow
34
 * return to be intercepted in some way, for things that need to do multiple
35
 * calls into the runloop in some C-managed process. Essentially, instead of
36
 * nested runloops, you just re-work the C code in question into CPS. */
37
typedef void (* MVMSpecialReturn)(MVMThreadContext *tc, void *data);
38
39
/* Function pointer for marking the special return handler data. */
40
typedef void (* MVMSpecialReturnDataMark)(MVMThreadContext *tc, MVMFrame *frame,
41
                                          MVMGCWorklist *worklist);
42
43
/* This represents an call frame, aka invocation record. It may exist either on
44
 * the heap, in which case its header will have the MVM_CF_FRAME flag set, or
45
 * in on a thread-local stack, in which case the collectable header will be
46
 * fully zeroed. */
47
struct MVMFrame {
48
    /* Commonalities that all collectable entities have. */
49
    MVMCollectable header;
50
51
    /* The environment for this frame, which lives beyond its execution.
52
     * Has space for, for instance, lexicals. */
53
    MVMRegister *env;
54
55
    /* The temporary work space for this frame. After a call is over, this
56
     * can be freed up. Must be NULLed out when this happens. */
57
    MVMRegister *work;
58
59
    /* The args buffer. Actually a pointer into an area inside of *work, to
60
     * decrease number of allocations. */
61
    MVMRegister *args;
62
63
    /* Callsite that indicates how the current args buffer is being used, if
64
     * it is. */
65
    MVMCallsite *cur_args_callsite;
66
67
    /* The outer frame, thus forming the static chain. */
68
    MVMFrame *outer;
69
70
    /* The caller frame, thus forming the dynamic chain. */
71
    MVMFrame *caller;
72
73
    /* The static frame information. Holds all we statically know about
74
     * this kind of frame, including information needed to GC-trace it. */
75
    MVMStaticFrame *static_info;
76
77
    /* The code ref object for this frame. */
78
    MVMObject *code_ref;
79
80
    /* Parameters received by this frame. */
81
    MVMArgProcContext params;
82
83
    /* Effective bytecode for the frame (either the original bytecode or a
84
     * specialization of it). */
85
    MVMuint8 *effective_bytecode;
86
87
    /* Effective set of frame handlers (to go with the effective bytecode). */
88
    MVMFrameHandler *effective_handlers;
89
90
    /* Effective set of spesh slots, if any. */
91
    MVMCollectable **effective_spesh_slots;
92
93
    /* Effective set of spesh logging slots, if any. */
94
    MVMCollectable **spesh_log_slots;
95
96
    /* The spesh candidate information, if we're in one. */
97
    MVMSpeshCandidate *spesh_cand;
98
99
    /* Address of the next op to execute if we return to this frame. */
100
    MVMuint8 *return_address;
101
102
    /* The register we should store the return value in, if any. */
103
    MVMRegister *return_value;
104
105
    /* The type of return value that is expected. */
106
    MVMReturnType return_type;
107
108
    /* If we want to invoke a special handler upon a return to this
109
     * frame, this function pointer is set. */
110
    MVMSpecialReturn special_return;
111
112
    /* If we want to invoke a special handler upon unwinding past a
113
     * frame, this function pointer is set. */
114
    MVMSpecialReturn special_unwind;
115
116
    /* Data slot for the special return handler function. */
117
    void *special_return_data;
118
119
    /* Flag for if special_return_data need to be GC marked. */
120
    MVMSpecialReturnDataMark mark_special_return_data;
121
122
    /* Address of the last op executed that threw an exeption; used just
123
     * for error reporting. */
124
    MVMuint8 *throw_address;
125
126
    /* Linked list of any continuation tags we have. */
127
    MVMContinuationTag *continuation_tags;
128
129
    /* Cache for dynlex lookup; if the name is non-null, the cache is valid
130
     * and the register can be accessed directly to find the contextual. */
131
    MVMString   *dynlex_cache_name;
132
    MVMRegister *dynlex_cache_reg;
133
    MVMuint16    dynlex_cache_type;
134
135
    /* The allocated work/env sizes. */
136
    MVMuint16 allocd_work;
137
    MVMuint16 allocd_env;
138
139
    /* Assorted frame flags. */
140
    MVMuint8 flags;
141
142
    /* If we're in a logging spesh run, the index to log at in this
143
     * invocation. -1 if we're not in a logging spesh run, junk if no
144
     * spesh_cand is set in this frame at all. */
145
    MVMint8 spesh_log_idx;
146
147
    /* On Stack Replacement iteration counter; incremented in loops, and will
148
     * trigger if the limit is hit. */
149
    MVMuint8 osr_counter;
150
151
    /* A sequence number to indicate our place in the call stack */
152
    MVMint32 sequence_nr;
153
    /* The 'entry label' is a sort of indirect return address for the JIT */
154
    void * jit_entry_label;
155
};
156
157
/* How do we invoke this thing? Specifies either an attribute to look at for
158
 * an invokable thing, a method to call, and maybe a multi-dispatch cache to
159
 * look in first for an answer. */
160
struct MVMInvocationSpec {
161
    /* Class handle, name and hint for attribute holding code to invoke. */
162
    MVMObject *class_handle;
163
    MVMString *attr_name;
164
    MVMint64   hint;
165
166
    /* Thing that handles invocation. */
167
    MVMObject *invocation_handler;
168
169
    /* Multi-dispatch info class handle, and name/hint of attribute that
170
     * holds the cache itself and a flag to check if it's allowed to
171
     * consider the cache. */
172
    MVMObject *md_class_handle;
173
    MVMString *md_cache_attr_name;
174
    MVMint64   md_cache_hint;
175
    MVMint64   md_valid_hint;
176
    MVMString *md_valid_attr_name;
177
};
178
179
MVMRegister * MVM_frame_initial_work(MVMThreadContext *tc, MVMuint16 *local_types,
180
                                     MVMuint16 num_locals);
181
void MVM_frame_invoke_code(MVMThreadContext *tc, MVMCode *code,
182
                           MVMCallsite *callsite, MVMint32 spesh_cand);
183
void MVM_frame_invoke(MVMThreadContext *tc, MVMStaticFrame *static_frame,
184
                      MVMCallsite *callsite, MVMRegister *args,
185
                      MVMFrame *outer, MVMObject *code_ref, MVMint32 spesh_cand);
186
MVM_PUBLIC MVMFrame * MVM_frame_force_to_heap(MVMThreadContext *tc, MVMFrame *frame);
187
MVMFrame * MVM_frame_create_context_only(MVMThreadContext *tc, MVMStaticFrame *static_frame,
188
        MVMObject *code_ref);
189
MVMFrame * MVM_frame_create_for_deopt(MVMThreadContext *tc, MVMStaticFrame *static_frame,
190
                                      MVMCode *code_ref);
191
MVM_PUBLIC MVMuint64 MVM_frame_try_return(MVMThreadContext *tc);
192
MVM_PUBLIC MVMuint64 MVM_frame_try_return_no_exit_handlers(MVMThreadContext *tc);
193
void MVM_frame_unwind_to(MVMThreadContext *tc, MVMFrame *frame, MVMuint8 *abs_addr,
194
                         MVMuint32 rel_addr, MVMObject *return_value);
195
MVM_PUBLIC void MVM_frame_destroy(MVMThreadContext *tc, MVMFrame *frame);
196
MVM_PUBLIC MVMObject * MVM_frame_get_code_object(MVMThreadContext *tc, MVMCode *code);
197
MVM_PUBLIC void MVM_frame_capturelex(MVMThreadContext *tc, MVMObject *code);
198
MVM_PUBLIC void MVM_frame_capture_inner(MVMThreadContext *tc, MVMObject *code);
199
MVM_PUBLIC MVMObject * MVM_frame_takeclosure(MVMThreadContext *tc, MVMObject *code);
200
MVM_PUBLIC MVMObject * MVM_frame_vivify_lexical(MVMThreadContext *tc, MVMFrame *f, MVMuint16 idx);
201
MVM_PUBLIC MVMRegister * MVM_frame_find_lexical_by_name(MVMThreadContext *tc, MVMString *name, MVMuint16 type);
202
MVM_PUBLIC void MVM_frame_bind_lexical_by_name(MVMThreadContext *tc, MVMString *name, MVMuint16 type, MVMRegister *value);
203
MVMObject * MVM_frame_find_lexical_by_name_outer(MVMThreadContext *tc, MVMString *name);
204
MVM_PUBLIC MVMRegister * MVM_frame_find_lexical_by_name_rel(MVMThreadContext *tc, MVMString *name, MVMFrame *cur_frame);
205
MVM_PUBLIC MVMRegister * MVM_frame_find_lexical_by_name_rel_caller(MVMThreadContext *tc, MVMString *name, MVMFrame *cur_caller_frame);
206
MVMRegister * MVM_frame_find_contextual_by_name(MVMThreadContext *tc, MVMString *name, MVMuint16 *type, MVMFrame *cur_frame, MVMint32 vivify, MVMFrame **found_frame);
207
MVMObject * MVM_frame_getdynlex(MVMThreadContext *tc, MVMString *name, MVMFrame *cur_frame);
208
void MVM_frame_binddynlex(MVMThreadContext *tc, MVMString *name, MVMObject *value, MVMFrame *cur_frame);
209
MVMRegister * MVM_frame_lexical(MVMThreadContext *tc, MVMFrame *f, MVMString *name);
210
MVM_PUBLIC MVMRegister * MVM_frame_try_get_lexical(MVMThreadContext *tc, MVMFrame *f, MVMString *name, MVMuint16 type);
211
MVMuint16 MVM_frame_lexical_primspec(MVMThreadContext *tc, MVMFrame *f, MVMString *name);
212
MVM_PUBLIC MVMObject * MVM_frame_find_invokee(MVMThreadContext *tc, MVMObject *code, MVMCallsite **tweak_cs);
213
MVMObject * MVM_frame_find_invokee_multi_ok(MVMThreadContext *tc, MVMObject *code, MVMCallsite **tweak_cs, MVMRegister *args);
214
MVM_PUBLIC MVMObject * MVM_frame_context_wrapper(MVMThreadContext *tc, MVMFrame *f);