-
Notifications
You must be signed in to change notification settings - Fork 0
/
local_context.hh
135 lines (109 loc) · 3.54 KB
/
local_context.hh
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
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
#ifndef LOCAL_CONTEXT_HH
#define LOCAL_CONTEXT_HH
#include "types.hh"
#include "var_desc.hh"
#include "method_desc.hh"
class local_context {
public:
enum context_cmd {
cmd_pop_var, // start of local variable scope
cmd_push_var, // end of local variable scope
cmd_merge_ctx, // forward jump label
cmd_reset_ctx, // backward jump label
cmd_enter_ctx, // entry point
cmd_case_ctx, // switch case label
cmd_update_ctx, // backward jump
cmd_save_ctx // forward jump
} cmd;
local_context* next;
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop) = 0;
local_context(context_cmd ctx_cmd, local_context** chain) {
cmd = ctx_cmd;
while (*chain != NULL && (*chain)->cmd < ctx_cmd) {
chain = &(*chain)->next;
}
next = *chain;
*chain = this;
}
};
class ctx_entry_point : public local_context {
public:
ctx_entry_point(local_context** chain)
: local_context(cmd_enter_ctx, chain) {}
virtual vbm_operand* transfer(method_desc* method,
vbm_operand* sp, byte cop, byte& prev_cop);
};
class ctx_split : public local_context {
public:
var_desc* vars;
vbm_operand* stack_pointer;
vbm_operand stack_top[2];
int switch_var_index;
int n_branches;
int in_monitor;
enum jmp_type { jmp_forward, jmp_backward };
ctx_split(local_context** chain, jmp_type type = jmp_forward)
: local_context(type == jmp_forward ? cmd_save_ctx : cmd_update_ctx, chain)
{
n_branches = 1;
}
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop);
};
class ctx_merge : public local_context {
public:
ctx_split* come_from;
int case_value;
ctx_merge(local_context** chain, ctx_split* come_from_ctx)
: local_context(cmd_merge_ctx, chain)
{
come_from = come_from_ctx;
}
ctx_merge(local_context** chain, ctx_split* come_from_ctx, int value)
: local_context(cmd_case_ctx, chain)
{
come_from = come_from_ctx;
case_value = value;
}
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop);
};
class ctx_pop_var : public local_context {
public:
int var_index;
ctx_pop_var(local_context** chain, int index)
: local_context(cmd_pop_var, chain), var_index(index) {}
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop);
};
class ctx_push_var : public local_context {
public:
utf_string* var_name;
int var_type;
int var_index;
int var_start_pc;
ctx_push_var(local_context** chain,
utf_string* name, int type, int index, int start_pc)
: local_context(cmd_push_var, chain) {
var_name = name;
var_type = type;
var_index = index;
var_start_pc = start_pc;
}
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop);
};
class ctx_reset : public local_context {
public:
int* var_store_count;
ctx_reset(local_context** chain, int* counts, int n_vars)
: local_context(cmd_reset_ctx, chain)
{
var_store_count = new int[n_vars];
memcpy(var_store_count, counts, n_vars*sizeof(int));
}
virtual vbm_operand* transfer(method_desc* method, vbm_operand* sp,
byte cop, byte& prev_cop);
};
#endif