Skip to content

Commit 0a71db8

Browse files
committed
* vm_core.h: remove lfp (local frame pointer) and rename
dfp (dynamic frame pointer) to ep (environment pointer). This change make VM `normal' (similar to other interpreters). Before this commit: Each frame has two env pointers lfp and dfp. lfp points local environment which is method/class/toplevel frame. lfp[0] is block pointer. dfp is block local frame. dfp[0] points previous (parent) environment pointer. lfp == dfp when frame is method/class/toplevel. You can get lfp from dfp by traversing previous environment pointers. After this commit: Each frame has only `ep' to point respective enviornoment. If there is parent environment, then ep[0] points parent envioenment (as dfp). If there are no more environment, then ep[0] points block pointer (as lfp). We call such ep as `LEP' (local EP). We add some macros to get LEP and to detect LEP or not. In short, we replace dfp and lfp with ep and LEP. rb_block_t and rb_binding_t member `lfp' and `dfp' are removed and member `ep' is added. rename rb_thread_t's member `local_lfp' and `local_svar' to `root_lep' and `root_svar'. (VM_EP_PREV_EP(ep)): get previous environment pointer. This macro assume that ep is not LEP. (VM_EP_BLOCK_PTR(ep)): get block pointer. This macro assume that ep is LEP. (VM_EP_LEP_P(ep)): detect ep is LEP or not. (VM_ENVVAL_BLOCK_PTR(ptr)): make block pointer. (VM_ENVVAL_BLOCK_PTR_P(v)): detect v is block pointer. (VM_ENVVAL_PREV_EP_PTR(ptr)): make prev environment pointer. (VM_ENVVAL_PREV_EP_PTR_P(v)): detect v is prev env pointer. * vm.c: apply above changes. (VM_EP_LEP(ep)): get LEP. (VM_CF_LEP(cfp)): get LEP of cfp->ep. (VM_CF_PREV_EP(cfp)): utility function VM_EP_PREV_EP(cfp->ep). (VM_CF_BLOCK_PTR(cfp)): utility function VM_EP_BLOCK_PTR(cfp->ep). * vm.c, vm_eval.c, vm_insnhelper.c, vm_insnhelper.h, insns.def: apply above changes. * cont.c: ditto. * eval.c, eval_intern.h: ditto. * proc.c: ditto. * thread.c: ditto. * vm_dump.c: ditto. * vm_exec.h: fix function name (on vm debug mode). git-svn-id: svn+ssh://ci.ruby-lang.org/ruby/trunk@36030 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
1 parent 9b29e5f commit 0a71db8

14 files changed

+413
-334
lines changed

ChangeLog

+57
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,60 @@
1+
Mon Jun 11 12:14:37 2012 Koichi Sasada <ko1@atdot.net>
2+
3+
* vm_core.h: remove lfp (local frame pointer) and rename
4+
dfp (dynamic frame pointer) to ep (environment pointer).
5+
This change make VM `normal' (similar to other interpreters).
6+
Before this commit:
7+
Each frame has two env pointers lfp and dfp. lfp points
8+
local environment which is method/class/toplevel frame.
9+
lfp[0] is block pointer.
10+
dfp is block local frame. dfp[0] points previous (parent)
11+
environment pointer.
12+
lfp == dfp when frame is method/class/toplevel.
13+
You can get lfp from dfp by traversing previous environment
14+
pointers.
15+
After this commit:
16+
Each frame has only `ep' to point respective enviornoment.
17+
If there is parent environment, then ep[0] points parent
18+
envioenment (as dfp). If there are no more environment,
19+
then ep[0] points block pointer (as lfp). We call such ep
20+
as `LEP' (local EP). We add some macros to get LEP and to
21+
detect LEP or not.
22+
In short, we replace dfp and lfp with ep and LEP.
23+
rb_block_t and rb_binding_t member `lfp' and `dfp' are removed
24+
and member `ep' is added.
25+
rename rb_thread_t's member `local_lfp' and `local_svar' to
26+
`root_lep' and `root_svar'.
27+
(VM_EP_PREV_EP(ep)): get previous environment pointer. This macro
28+
assume that ep is not LEP.
29+
(VM_EP_BLOCK_PTR(ep)): get block pointer. This macro assume
30+
that ep is LEP.
31+
(VM_EP_LEP_P(ep)): detect ep is LEP or not.
32+
(VM_ENVVAL_BLOCK_PTR(ptr)): make block pointer.
33+
(VM_ENVVAL_BLOCK_PTR_P(v)): detect v is block pointer.
34+
(VM_ENVVAL_PREV_EP_PTR(ptr)): make prev environment pointer.
35+
(VM_ENVVAL_PREV_EP_PTR_P(v)): detect v is prev env pointer.
36+
37+
* vm.c: apply above changes.
38+
(VM_EP_LEP(ep)): get LEP.
39+
(VM_CF_LEP(cfp)): get LEP of cfp->ep.
40+
(VM_CF_PREV_EP(cfp)): utility function VM_EP_PREV_EP(cfp->ep).
41+
(VM_CF_BLOCK_PTR(cfp)): utility function VM_EP_BLOCK_PTR(cfp->ep).
42+
43+
* vm.c, vm_eval.c, vm_insnhelper.c, vm_insnhelper.h, insns.def:
44+
apply above changes.
45+
46+
* cont.c: ditto.
47+
48+
* eval.c, eval_intern.h: ditto.
49+
50+
* proc.c: ditto.
51+
52+
* thread.c: ditto.
53+
54+
* vm_dump.c: ditto.
55+
56+
* vm_exec.h: fix function name (on vm debug mode).
57+
158
Mon Jun 11 11:52:18 2012 URABE Shyouhei <shyouhei@ruby-lang.org>
259

360
* compile.c (iseq_set_sequence): nonstatic initializer of an

cont.c

+4-5
Original file line numberDiff line numberDiff line change
@@ -1059,9 +1059,8 @@ fiber_init(VALUE fibval, VALUE proc)
10591059
th->cfp->pc = 0;
10601060
th->cfp->sp = th->stack + 1;
10611061
th->cfp->bp = 0;
1062-
th->cfp->lfp = th->stack;
1063-
*th->cfp->lfp = 0;
1064-
th->cfp->dfp = th->stack;
1062+
th->cfp->ep = th->stack;
1063+
*th->cfp->ep = VM_ENVVAL_BLOCK_PTR(0);
10651064
th->cfp->self = Qnil;
10661065
th->cfp->flag = 0;
10671066
th->cfp->iseq = 0;
@@ -1155,8 +1154,8 @@ rb_fiber_start(void)
11551154
argv = (argc = cont->argc) > 1 ? RARRAY_PTR(args) : &args;
11561155
cont->value = Qnil;
11571156
th->errinfo = Qnil;
1158-
th->local_lfp = proc->block.lfp;
1159-
th->local_svar = Qnil;
1157+
th->root_lep = rb_vm_ep_local_ep(proc->block.ep);
1158+
th->root_svar = Qnil;
11601159

11611160
fib->status = RUNNING;
11621161
cont->value = rb_vm_invoke_proc(th, proc, proc->block.self, argc, argv, 0);

eval.c

+5-5
Original file line numberDiff line numberDiff line change
@@ -604,7 +604,7 @@ rb_block_given_p(void)
604604
{
605605
rb_thread_t *th = GET_THREAD();
606606

607-
if (RUBY_VM_GET_BLOCK_PTR(th->cfp)) {
607+
if (rb_vm_control_frame_block_ptr(th->cfp)) {
608608
return TRUE;
609609
}
610610
else {
@@ -1054,12 +1054,12 @@ errinfo_place(rb_thread_t *th)
10541054
while (RUBY_VM_VALID_CONTROL_FRAME_P(cfp, end_cfp)) {
10551055
if (RUBY_VM_NORMAL_ISEQ_P(cfp->iseq)) {
10561056
if (cfp->iseq->type == ISEQ_TYPE_RESCUE) {
1057-
return &cfp->dfp[-2];
1057+
return &cfp->ep[-2];
10581058
}
10591059
else if (cfp->iseq->type == ISEQ_TYPE_ENSURE &&
1060-
!RB_TYPE_P(cfp->dfp[-2], T_NODE) &&
1061-
!FIXNUM_P(cfp->dfp[-2])) {
1062-
return &cfp->dfp[-2];
1060+
!RB_TYPE_P(cfp->ep[-2], T_NODE) &&
1061+
!FIXNUM_P(cfp->ep[-2])) {
1062+
return &cfp->ep[-2];
10631063
}
10641064
}
10651065
cfp = RUBY_VM_PREVIOUS_CONTROL_FRAME(cfp);

eval_intern.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
#include "vm_core.h"
66

77
#define PASS_PASSED_BLOCK_TH(th) do { \
8-
(th)->passed_block = GC_GUARDED_PTR_REF((rb_block_t *)(th)->cfp->lfp[0]); \
8+
(th)->passed_block = rb_vm_control_frame_block_ptr(th->cfp); \
99
(th)->cfp->flag |= VM_FRAME_FLAG_PASSED; \
1010
} while (0)
1111

insns.def

+24-24
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ getlocal
5555
()
5656
(VALUE val)
5757
{
58-
val = *(GET_LFP() - idx);
58+
val = *(GET_LEP() - idx);
5959
}
6060

6161
/**
@@ -69,7 +69,7 @@ setlocal
6969
(VALUE val)
7070
()
7171
{
72-
(*(GET_LFP() - idx)) = val;
72+
*(GET_LEP() - idx) = val;
7373
}
7474

7575
/**
@@ -83,7 +83,7 @@ getspecial
8383
()
8484
(VALUE val)
8585
{
86-
val = vm_getspecial(th, GET_LFP(), key, type);
86+
val = vm_getspecial(th, GET_LEP(), key, type);
8787
}
8888

8989
/**
@@ -97,7 +97,7 @@ setspecial
9797
(VALUE obj)
9898
()
9999
{
100-
lfp_svar_set(th, GET_LFP(), key, obj);
100+
lep_svar_set(th, GET_LEP(), key, obj);
101101
}
102102

103103
/**
@@ -114,11 +114,11 @@ getdynamic
114114
(VALUE val)
115115
{
116116
rb_num_t i;
117-
VALUE *dfp2 = GET_DFP();
117+
VALUE *ep = GET_EP();
118118
for (i = 0; i < level; i++) {
119-
dfp2 = GET_PREV_DFP(dfp2);
119+
ep = GET_PREV_EP(ep);
120120
}
121-
val = *(dfp2 - idx);
121+
val = *(ep - idx);
122122
}
123123

124124
/**
@@ -135,11 +135,11 @@ setdynamic
135135
()
136136
{
137137
rb_num_t i;
138-
VALUE *dfp2 = GET_DFP();
138+
VALUE *ep = GET_EP();
139139
for (i = 0; i < level; i++) {
140-
dfp2 = GET_PREV_DFP(dfp2);
140+
ep = GET_PREV_EP(ep);
141141
}
142-
*(dfp2 - idx) = val;
142+
*(ep - idx) = val;
143143
}
144144

145145
/**
@@ -183,7 +183,7 @@ getclassvariable
183183
()
184184
(VALUE val)
185185
{
186-
NODE * const cref = vm_get_cref(GET_ISEQ(), GET_LFP(), GET_DFP());
186+
NODE *cref = vm_get_cref(GET_ISEQ(), GET_EP());
187187
val = rb_cvar_get(vm_get_cvar_base(cref), id);
188188
}
189189

@@ -198,7 +198,7 @@ setclassvariable
198198
(VALUE val)
199199
()
200200
{
201-
NODE * const cref = vm_get_cref(GET_ISEQ(), GET_LFP(), GET_DFP());
201+
NODE *cref = vm_get_cref(GET_ISEQ(), GET_EP());
202202
rb_cvar_set(vm_get_cvar_base(cref), id, val);
203203
}
204204

@@ -343,10 +343,10 @@ putspecialobject
343343
val = rb_mRubyVMFrozenCore;
344344
break;
345345
case VM_SPECIAL_OBJECT_CBASE:
346-
val = vm_get_cbase(GET_ISEQ(), GET_LFP(), GET_DFP());
346+
val = vm_get_cbase(GET_ISEQ(), GET_EP());
347347
break;
348348
case VM_SPECIAL_OBJECT_CONST_BASE:
349-
val = vm_get_const_base(GET_ISEQ(), GET_LFP(), GET_DFP());
349+
val = vm_get_const_base(GET_ISEQ(), GET_EP());
350350
break;
351351
default:
352352
rb_bug("putspecialobject insn: unknown value_type");
@@ -768,7 +768,7 @@ defined
768768
}
769769
break;
770770
case DEFINED_IVAR2:
771-
klass = vm_get_cbase(GET_ISEQ(), GET_LFP(), GET_DFP());
771+
klass = vm_get_cbase(GET_ISEQ(), GET_EP());
772772
break;
773773
case DEFINED_GVAR:
774774
if (rb_gvar_defined(rb_global_entry(SYM2ID(obj)))) {
@@ -777,7 +777,7 @@ defined
777777
break;
778778
case DEFINED_CVAR:
779779
{
780-
NODE *cref = vm_get_cref(GET_ISEQ(), GET_LFP(), GET_DFP());
780+
NODE *cref = vm_get_cref(GET_ISEQ(), GET_EP());
781781
klass = vm_get_cvar_base(cref);
782782
if (rb_cvar_defined(klass, SYM2ID(obj))) {
783783
expr_type = "class variable";
@@ -842,7 +842,7 @@ defined
842842
break;
843843
}
844844
case DEFINED_REF:{
845-
val = vm_getspecial(th, GET_LFP(), Qfalse, FIX2INT(obj));
845+
val = vm_getspecial(th, GET_LEP(), Qfalse, FIX2INT(obj));
846846
if (val != Qnil) {
847847
expr_type = "global-variable";
848848
}
@@ -971,9 +971,9 @@ defineclass
971971
COPY_CREF(class_iseq->cref_stack, vm_cref_push(th, klass, NOEX_PUBLIC, NULL));
972972

973973
/* enter scope */
974-
vm_push_frame(th, class_iseq,
975-
VM_FRAME_MAGIC_CLASS, klass, (VALUE) GET_BLOCK_PTR(),
976-
class_iseq->iseq_encoded, GET_SP(), 0,
974+
vm_push_frame(th, class_iseq, VM_FRAME_MAGIC_CLASS,
975+
klass, VM_ENVVAL_BLOCK_PTR(GET_BLOCK_PTR()),
976+
class_iseq->iseq_encoded, GET_SP(),
977977
class_iseq->local_size);
978978
RESTORE_REGS();
979979

@@ -1315,11 +1315,11 @@ opt_checkenv
13151315
()
13161316
()
13171317
{
1318-
if (GET_CFP()->bp != GET_DFP() + 1) {
1319-
VALUE *new_dfp = GET_CFP()->bp - 1;
1318+
if (GET_CFP()->bp != GET_EP() + 1) {
1319+
VALUE *ep = GET_CFP()->bp - 1;
13201320
/* TODO: copy env and clean stack at creating env? */
1321-
*new_dfp = *GET_DFP();
1322-
SET_DFP(new_dfp);
1321+
*ep = *GET_EP();
1322+
SET_EP(ep);
13231323
}
13241324
}
13251325

proc.c

+5-9
Original file line numberDiff line numberDiff line change
@@ -383,17 +383,13 @@ proc_new(VALUE klass, int is_lambda)
383383
rb_control_frame_t *cfp = th->cfp;
384384
rb_block_t *block;
385385

386-
if ((GC_GUARDED_PTR_REF(cfp->lfp[0])) != 0) {
387-
388-
block = GC_GUARDED_PTR_REF(cfp->lfp[0]);
386+
if ((block = rb_vm_control_frame_block_ptr(cfp)) != 0) {
387+
/* block found */
389388
}
390389
else {
391390
cfp = RUBY_VM_PREVIOUS_CONTROL_FRAME(cfp);
392391

393-
if ((GC_GUARDED_PTR_REF(cfp->lfp[0])) != 0) {
394-
395-
block = GC_GUARDED_PTR_REF(cfp->lfp[0]);
396-
392+
if ((block = rb_vm_control_frame_block_ptr(cfp)) != 0) {
397393
if (is_lambda) {
398394
rb_warn("tried to create Proc object without a block");
399395
}
@@ -418,7 +414,7 @@ proc_new(VALUE klass, int is_lambda)
418414
}
419415

420416
procval = rb_vm_make_proc(th, block, klass);
421-
rb_vm_rewrite_dfp_in_errinfo(th, cfp);
417+
rb_vm_rewrite_ep_in_errinfo(th, cfp);
422418

423419
if (is_lambda) {
424420
rb_proc_t *proc;
@@ -801,7 +797,7 @@ rb_hash_proc(st_index_t hash, VALUE prc)
801797
GetProcPtr(prc, proc);
802798
hash = rb_hash_uint(hash, (st_index_t)proc->block.iseq);
803799
hash = rb_hash_uint(hash, (st_index_t)proc->envval);
804-
return rb_hash_uint(hash, (st_index_t)proc->block.lfp >> 16);
800+
return rb_hash_uint(hash, (st_index_t)proc->block.ep >> 16);
805801
}
806802

807803
/*

thread.c

+2-2
Original file line numberDiff line numberDiff line change
@@ -454,8 +454,8 @@ thread_start_func_2(rb_thread_t *th, VALUE *stack_start, VALUE *register_stack_s
454454
if (!th->first_func) {
455455
GetProcPtr(th->first_proc, proc);
456456
th->errinfo = Qnil;
457-
th->local_lfp = proc->block.lfp;
458-
th->local_svar = Qnil;
457+
th->root_lep = rb_vm_ep_local_ep(proc->block.ep);
458+
th->root_svar = Qnil;
459459
th->value = rb_vm_invoke_proc(th, proc, proc->block.self,
460460
(int)RARRAY_LEN(args), RARRAY_PTR(args), 0);
461461
}

0 commit comments

Comments
 (0)