parent
b0f715fa3b
commit
5dfba84cff
@ -984,8 +984,14 @@ rb_iseq_compile_prism_node(rb_iseq_t * iseq, pm_scope_node_t *scope_node, pm_par
|
|||||||
constants[index] = rb_intern3((const char *) constant->start, constant->length, encoding);
|
constants[index] = rb_intern3((const char *) constant->start, constant->length, encoding);
|
||||||
}
|
}
|
||||||
|
|
||||||
scope_node->constants = constants;
|
st_table *index_lookup_table = st_init_numtable();
|
||||||
|
pm_constant_id_list_t *locals = &scope_node->locals;
|
||||||
|
for (size_t i = 0; i < locals->size; i++) {
|
||||||
|
st_insert(index_lookup_table, locals->ids[i], i);
|
||||||
|
}
|
||||||
|
|
||||||
|
scope_node->constants = (void *)constants;
|
||||||
|
scope_node->index_lookup_table = index_lookup_table;
|
||||||
CHECK(rb_translate_prism(iseq, scope_node, ret));
|
CHECK(rb_translate_prism(iseq, scope_node, ret));
|
||||||
free(constants);
|
free(constants);
|
||||||
|
|
||||||
|
@ -48,6 +48,8 @@
|
|||||||
#define PM_SWAP_UNLESS_POPPED \
|
#define PM_SWAP_UNLESS_POPPED \
|
||||||
if (!popped) PM_SWAP;
|
if (!popped) PM_SWAP;
|
||||||
|
|
||||||
|
#define TEMP_CONSTANT_IDENTIFIER ((pm_constant_id_t)(1 << 31))
|
||||||
|
|
||||||
rb_iseq_t *
|
rb_iseq_t *
|
||||||
pm_iseq_new_with_opt(pm_scope_node_t *scope_node, pm_parser_t *parser, VALUE name, VALUE path, VALUE realpath,
|
pm_iseq_new_with_opt(pm_scope_node_t *scope_node, pm_parser_t *parser, VALUE name, VALUE path, VALUE realpath,
|
||||||
int first_lineno, const rb_iseq_t *parent, int isolated_depth,
|
int first_lineno, const rb_iseq_t *parent, int isolated_depth,
|
||||||
@ -2006,6 +2008,48 @@ pm_compile_node(rb_iseq_t *iseq, const pm_node_t *node, LINK_ANCHOR *const ret,
|
|||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
case PM_FOR_NODE: {
|
||||||
|
pm_for_node_t *for_node = (pm_for_node_t *)node;
|
||||||
|
|
||||||
|
const rb_iseq_t *child_iseq;
|
||||||
|
const rb_iseq_t *prevblock = ISEQ_COMPILE_DATA(iseq)->current_block;
|
||||||
|
|
||||||
|
LABEL *retry_label = NEW_LABEL(lineno);
|
||||||
|
LABEL *retry_end_l = NEW_LABEL(lineno);
|
||||||
|
|
||||||
|
pm_scope_node_t next_scope_node;
|
||||||
|
pm_scope_node_init((pm_node_t *)for_node, &next_scope_node, scope_node, parser);
|
||||||
|
|
||||||
|
pm_constant_id_list_t locals;
|
||||||
|
pm_constant_id_list_init(&locals);
|
||||||
|
pm_constant_id_list_append(&locals, TEMP_CONSTANT_IDENTIFIER);
|
||||||
|
next_scope_node.locals = locals;
|
||||||
|
|
||||||
|
ADD_LABEL(ret, retry_label);
|
||||||
|
|
||||||
|
PM_COMPILE(for_node->collection);
|
||||||
|
child_iseq = NEW_CHILD_ISEQ(next_scope_node, make_name_for_block(iseq), ISEQ_TYPE_BLOCK, lineno);
|
||||||
|
ISEQ_COMPILE_DATA(iseq)->current_block = child_iseq;
|
||||||
|
ADD_SEND_WITH_BLOCK(ret, &dummy_line_node, idEach, INT2FIX(0), child_iseq);
|
||||||
|
|
||||||
|
INSN *iobj;
|
||||||
|
LINK_ELEMENT *last_elem = LAST_ELEMENT(ret);
|
||||||
|
iobj = IS_INSN(last_elem) ? (INSN *)last_elem : (INSN *)get_prev_insn((INSN*)last_elem);
|
||||||
|
while (INSN_OF(iobj) != BIN(send) &&
|
||||||
|
INSN_OF(iobj) != BIN(invokesuper)) {
|
||||||
|
iobj = (INSN *)get_prev_insn(iobj);
|
||||||
|
}
|
||||||
|
ELEM_INSERT_NEXT(&iobj->link, (LINK_ELEMENT*)retry_end_l);
|
||||||
|
|
||||||
|
if (popped) {
|
||||||
|
ADD_INSN(ret, &dummy_line_node, pop);
|
||||||
|
}
|
||||||
|
|
||||||
|
ISEQ_COMPILE_DATA(iseq)->current_block = prevblock;
|
||||||
|
ADD_CATCH_ENTRY(CATCH_TYPE_BREAK, retry_label, retry_end_l, child_iseq, retry_end_l);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
case PM_GLOBAL_VARIABLE_AND_WRITE_NODE: {
|
case PM_GLOBAL_VARIABLE_AND_WRITE_NODE: {
|
||||||
pm_global_variable_and_write_node_t *global_variable_and_write_node = (pm_global_variable_and_write_node_t*) node;
|
pm_global_variable_and_write_node_t *global_variable_and_write_node = (pm_global_variable_and_write_node_t*) node;
|
||||||
|
|
||||||
@ -2494,6 +2538,7 @@ pm_compile_node(rb_iseq_t *iseq, const pm_node_t *node, LINK_ANCHOR *const ret,
|
|||||||
pm_local_variable_target_node_t *local_write_node = (pm_local_variable_target_node_t *) node;
|
pm_local_variable_target_node_t *local_write_node = (pm_local_variable_target_node_t *) node;
|
||||||
|
|
||||||
pm_constant_id_t constant_id = local_write_node->name;
|
pm_constant_id_t constant_id = local_write_node->name;
|
||||||
|
for (size_t index = 0; index < local_write_node->depth; index++) scope_node = scope_node->previous;
|
||||||
int index = pm_lookup_local_index(iseq, scope_node, constant_id);
|
int index = pm_lookup_local_index(iseq, scope_node, constant_id);
|
||||||
|
|
||||||
ADD_SETLOCAL(ret, &dummy_line_node, (int)index, local_write_node->depth);
|
ADD_SETLOCAL(ret, &dummy_line_node, (int)index, local_write_node->depth);
|
||||||
@ -2879,12 +2924,18 @@ pm_compile_node(rb_iseq_t *iseq, const pm_node_t *node, LINK_ANCHOR *const ret,
|
|||||||
pm_constant_id_list_t locals = scope_node->locals;
|
pm_constant_id_list_t locals = scope_node->locals;
|
||||||
|
|
||||||
pm_parameters_node_t *parameters_node = (pm_parameters_node_t *)scope_node->parameters;
|
pm_parameters_node_t *parameters_node = (pm_parameters_node_t *)scope_node->parameters;
|
||||||
pm_node_list_t requireds_list = PM_EMPTY_NODE_LIST;
|
|
||||||
pm_node_list_t optionals_list = PM_EMPTY_NODE_LIST;
|
pm_node_list_t optionals_list = PM_EMPTY_NODE_LIST;
|
||||||
|
|
||||||
if (parameters_node) {
|
if (parameters_node) {
|
||||||
requireds_list = parameters_node->requireds;
|
|
||||||
optionals_list = parameters_node->optionals;
|
optionals_list = parameters_node->optionals;
|
||||||
|
ISEQ_BODY(iseq)->param.lead_num = (int) parameters_node->requireds.size;
|
||||||
|
ISEQ_BODY(iseq)->param.opt_num = (int) optionals_list.size;
|
||||||
|
} else if (PM_NODE_TYPE_P(scope_node->ast_node, PM_FOR_NODE)) {
|
||||||
|
ISEQ_BODY(iseq)->param.lead_num = 1;
|
||||||
|
ISEQ_BODY(iseq)->param.opt_num = 0;
|
||||||
|
} else {
|
||||||
|
ISEQ_BODY(iseq)->param.lead_num = 0;
|
||||||
|
ISEQ_BODY(iseq)->param.opt_num = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
size_t size = locals.size;
|
size_t size = locals.size;
|
||||||
@ -2898,15 +2949,18 @@ pm_compile_node(rb_iseq_t *iseq, const pm_node_t *node, LINK_ANCHOR *const ret,
|
|||||||
|
|
||||||
for (size_t i = 0; i < size; i++) {
|
for (size_t i = 0; i < size; i++) {
|
||||||
pm_constant_id_t constant_id = locals.ids[i];
|
pm_constant_id_t constant_id = locals.ids[i];
|
||||||
ID local = pm_constant_id_lookup(scope_node, constant_id);
|
ID local;
|
||||||
|
if (constant_id & TEMP_CONSTANT_IDENTIFIER) {
|
||||||
|
local = rb_make_temporary_id(i);
|
||||||
|
} else {
|
||||||
|
local = pm_constant_id_lookup(scope_node, constant_id);
|
||||||
|
}
|
||||||
tbl->ids[i] = local;
|
tbl->ids[i] = local;
|
||||||
st_insert(index_lookup_table, constant_id, i);
|
st_insert(index_lookup_table, constant_id, i);
|
||||||
}
|
}
|
||||||
|
|
||||||
scope_node->index_lookup_table = index_lookup_table;
|
scope_node->index_lookup_table = index_lookup_table;
|
||||||
|
|
||||||
ISEQ_BODY(iseq)->param.lead_num = (int)requireds_list.size;
|
|
||||||
ISEQ_BODY(iseq)->param.opt_num = (int)optionals_list.size;
|
|
||||||
// TODO: Set all the other nums (good comment by lead_num illustrating what they are)
|
// TODO: Set all the other nums (good comment by lead_num illustrating what they are)
|
||||||
ISEQ_BODY(iseq)->param.size = (unsigned int)size;
|
ISEQ_BODY(iseq)->param.size = (unsigned int)size;
|
||||||
|
|
||||||
@ -2951,7 +3005,15 @@ pm_compile_node(rb_iseq_t *iseq, const pm_node_t *node, LINK_ANCHOR *const ret,
|
|||||||
ADD_LABEL(ret, start);
|
ADD_LABEL(ret, start);
|
||||||
|
|
||||||
if (scope_node->body) {
|
if (scope_node->body) {
|
||||||
PM_COMPILE((pm_node_t *)scope_node->body);
|
if (PM_NODE_TYPE_P(scope_node->ast_node, PM_FOR_NODE)) {
|
||||||
|
pm_for_node_t *for_node = (pm_for_node_t *)scope_node->ast_node;
|
||||||
|
|
||||||
|
ADD_GETLOCAL(ret, &dummy_line_node, 1, 0);
|
||||||
|
pm_compile_node(iseq, for_node->index, ret, src, popped, scope_node);
|
||||||
|
ADD_INSN(ret, &dummy_line_node, nop);
|
||||||
|
}
|
||||||
|
|
||||||
|
pm_compile_node(iseq, (pm_node_t *)(scope_node->body), ret, src, popped, scope_node);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
PM_PUTNIL;
|
PM_PUTNIL;
|
||||||
|
Loading…
x
Reference in New Issue
Block a user